Skip to main content

jmap_filenode_types/
capability.rs

1//! draft-ietf-jmap-filenode-13 §2.1 — account-level capability object.
2//!
3//! Provides [`FileNodeCapability`] and the capability URI constant
4//! [`JMAP_FILENODE_URI`].
5
6use serde::{Deserialize, Serialize};
7
8/// The JMAP capability URI for the FileNode extension.
9///
10/// Present as a key in both the session-level `capabilities` object (value:
11/// empty object) and in each account's `accountCapabilities` object (value:
12/// a [`FileNodeCapability`]).
13pub const JMAP_FILENODE_URI: &str = "urn:ietf:params:jmap:filenode";
14
15/// Account-level capability for the JMAP FileNode extension
16/// (draft-ietf-jmap-filenode-13 §2.1).
17///
18/// The value of the `urn:ietf:params:jmap:filenode` key in `accountCapabilities`.
19///
20/// ## Nullable fields
21///
22/// Fields typed `Option<T>` with no `skip_serializing_if` are **required-and-nullable**:
23/// they MUST appear in wire JSON even when the value is `null` (e.g. `"maxFileNodeDepth":null`
24/// means no limit).  Fields with `skip_serializing_if = "Option::is_none"` are absent when
25/// `None`, but none exist on this struct — all optional fields here are nullable.
26///
27/// ## `maxSizeFileNodeName` constraint
28///
29/// Per §2.1 the server MUST set this to at least 100.  This crate does not enforce
30/// the constraint at the type level (that would require a newtype); the server
31/// implementation is responsible for the invariant.
32#[non_exhaustive]
33#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
34#[serde(rename_all = "camelCase")]
35pub struct FileNodeCapability {
36    /// Maximum depth of the FileNode hierarchy (one more than the max ancestor count),
37    /// or `null` for no limit.
38    ///
39    /// Always serialized (as `null` when `None`).
40    pub max_file_node_depth: Option<u64>,
41
42    /// Maximum length, in UTF-8 octets, for a FileNode name.  MUST be ≥ 100.
43    pub max_size_file_node_name: u64,
44
45    /// Characters forbidden in FileNode names, each character individually forbidden.
46    /// `null` means the server imposes no character restrictions beyond Net-Unicode.
47    ///
48    /// Always serialized (as `null` when `None`).
49    pub forbidden_name_chars: Option<String>,
50
51    /// Complete names the server will not accept (compared case-insensitively).
52    /// `null` means no specific names are forbidden.
53    ///
54    /// Always serialized (as `null` when `None`).
55    pub forbidden_node_names: Option<Vec<String>>,
56
57    /// All sort property values supported for the `"property"` field of a Comparator
58    /// object in `FileNode/query`.
59    pub file_node_query_sort_options: Vec<String>,
60
61    /// If `true`, the user may create a FileNode with a null `parentId` in this account.
62    pub may_create_top_level_file_node: bool,
63
64    /// Web URL for the folder with the `"trash"` role, or `null` if unavailable.
65    ///
66    /// Always serialized (as `null` when `None`).
67    pub web_trash_url: Option<String>,
68
69    /// If `true`, the server treats file names as case-insensitive for all name
70    /// collision checks (including the sibling uniqueness constraint and `onExists`
71    /// handling).  The server preserves the original case as provided by the client.
72    pub case_insensitive_names: bool,
73
74    /// URI Template (level 1) for viewing a node on the web, with `{id}` variable.
75    /// `null` if no web URL is available.
76    ///
77    /// Always serialized (as `null` when `None`).
78    pub web_url_template: Option<String>,
79
80    /// URI Template (level 1) for direct HTTP writes to a file node, with `{id}`
81    /// variable.  `null` if direct HTTP writes are not supported.
82    ///
83    /// Always serialized (as `null` when `None`).
84    pub web_write_url_template: Option<String>,
85}