notionrs_schema/object/database/
relation.rs

1use serde::{Deserialize, Serialize};
2
3#[derive(Deserialize, Serialize, Debug, Default, Clone, PartialEq, Eq, notionrs_macro::Setter)]
4pub struct DatabaseRelationProperty {
5    /// Property Identifier
6    #[serde(skip_serializing)]
7    pub id: Option<String>,
8
9    /// Modify the value of this field when updating the column name of the property.
10    #[serde(skip_serializing)]
11    pub name: String,
12
13    /// Although it is not explicitly stated in the official documentation,
14    /// you can add a description to the property by specifying this.
15    #[serde(skip_serializing)]
16    pub description: Option<String>,
17
18    pub relation: DatabaseRelationDetail,
19}
20
21#[derive(Deserialize, Serialize, Debug, Default, Clone, PartialEq, Eq, notionrs_macro::Setter)]
22pub struct DatabaseRelationDetail {
23    /// The database that the relation property refers to.
24    /// The corresponding linked page values must belong to the database in order to be valid.
25    pub database_id: String,
26
27    /// Used when creating a one-way relation.
28    #[serde(skip_serializing_if = "Option::is_none")]
29    pub single_property: Option<std::collections::HashMap<(), ()>>,
30
31    /// Used when creating a two-way relation.
32    #[serde(skip_serializing_if = "Option::is_none")]
33    pub dual_property: Option<DatabaseRelationDualProperty>,
34}
35
36#[derive(Deserialize, Serialize, Debug, Default, Clone, PartialEq, Eq, notionrs_macro::Setter)]
37pub struct DatabaseRelationDualProperty {
38    /// The ID of the property for creating a two-way relation.
39    pub synced_property_id: String,
40
41    /// The database column name of the property for creating a two-way relation.
42    pub synced_property_name: String,
43}
44
45impl DatabaseRelationProperty {
46    pub fn create_one_way_relation<T>(database_id: T) -> Self
47    where
48        T: AsRef<str>,
49    {
50        Self {
51            relation: DatabaseRelationDetail {
52                database_id: database_id.as_ref().to_string(),
53                single_property: Some(std::collections::HashMap::new()),
54                ..Default::default()
55            },
56            ..Default::default()
57        }
58    }
59
60    pub fn create_tow_way_relation<S, T, U>(
61        database_id: S,
62        synced_property_id: T,
63        synced_property_name: U,
64    ) -> Self
65    where
66        S: AsRef<str>,
67        T: AsRef<str>,
68        U: AsRef<str>,
69    {
70        Self {
71            relation: DatabaseRelationDetail {
72                database_id: database_id.as_ref().to_string(),
73                dual_property: Some(DatabaseRelationDualProperty {
74                    synced_property_id: synced_property_id.as_ref().to_string(),
75                    synced_property_name: synced_property_name.as_ref().to_string(),
76                }),
77                ..Default::default()
78            },
79            ..Default::default()
80        }
81    }
82}
83
84// # --------------------------------------------------------------------------------
85//
86// unit test
87//
88// # --------------------------------------------------------------------------------
89#[cfg(test)]
90mod unit_tests {
91
92    use super::*;
93
94    #[test]
95    fn deserialize_database_relation_property() {
96        let json_data = r#"
97        {
98            "id": "VGw%7B",
99            "name": "Relation",
100            "type": "relation",
101            "relation": {
102                "database_id": "12aa03d7-9b26-8158-b34b-d0e7ceec0d15",
103                "type": "dual_property",
104                "dual_property": {
105                    "synced_property_name": "Related to Untitled Database (Relation)",
106                    "synced_property_id": "csu%5B"
107                }
108            }
109        }
110        "#;
111
112        let relation = serde_json::from_str::<DatabaseRelationProperty>(json_data).unwrap();
113
114        assert_eq!(relation.id, Some("VGw%7B".to_string()));
115        assert_eq!(relation.name, "Relation");
116        assert_eq!(
117            relation.relation.database_id,
118            "12aa03d7-9b26-8158-b34b-d0e7ceec0d15"
119        );
120        assert_eq!(
121            relation
122                .relation
123                .dual_property
124                .clone()
125                .unwrap()
126                .synced_property_name,
127            "Related to Untitled Database (Relation)"
128        );
129        assert_eq!(
130            relation.relation.dual_property.unwrap().synced_property_id,
131            "csu%5B"
132        );
133    }
134}