dpp/document/serialization_traits/platform_value_conversion/
mod.rs1mod v0;
2
3pub use v0::*;
4
5use crate::document::{Document, DocumentV0};
6use crate::version::PlatformVersion;
7use crate::ProtocolError;
8use platform_value::Value;
9use std::collections::BTreeMap;
10
11impl DocumentPlatformValueMethodsV0<'_> for Document {
12 fn to_map_value(&self) -> Result<BTreeMap<String, Value>, ProtocolError> {
14 match self {
15 Document::V0(v0) => v0.to_map_value(),
16 }
17 }
18
19 fn into_map_value(self) -> Result<BTreeMap<String, Value>, ProtocolError> {
21 match self {
22 Document::V0(v0) => v0.into_map_value(),
23 }
24 }
25
26 fn into_value(self) -> Result<Value, ProtocolError> {
28 match self {
29 Document::V0(v0) => v0.into_value(),
30 }
31 }
32
33 fn to_object(&self) -> Result<Value, ProtocolError> {
35 match self {
36 Document::V0(v0) => v0.to_object(),
37 }
38 }
39
40 fn from_platform_value(
42 document_value: Value,
43 platform_version: &PlatformVersion,
44 ) -> Result<Self, ProtocolError> {
45 match platform_version
46 .dpp
47 .document_versions
48 .document_structure_version
49 {
50 0 => Ok(Document::V0(DocumentV0::from_platform_value(
51 document_value,
52 platform_version,
53 )?)),
54 version => Err(ProtocolError::UnknownVersionError(format!(
55 "version {version} not known for document for call from_platform_value"
56 ))),
57 }
58 }
59}
60
61#[cfg(test)]
62mod tests {
63 use super::*;
64 use crate::data_contract::accessors::v0::DataContractV0Getters;
65 use crate::data_contract::document_type::random_document::CreateRandomDocument;
66 use crate::document::DocumentV0Getters;
67 use crate::tests::json_document::json_document_to_contract;
68 use platform_value::Identifier;
69 use platform_version::version::PlatformVersion;
70
71 #[test]
76 fn round_trip_document_to_value_and_back() {
77 let platform_version = PlatformVersion::latest();
78 let contract = json_document_to_contract(
79 "../rs-drive/tests/supporting_files/contract/dashpay/dashpay-contract.json",
80 false,
81 platform_version,
82 )
83 .expect("expected to load dashpay contract");
84
85 let document_type = contract
86 .document_type_for_name("profile")
87 .expect("expected profile document type");
88
89 for seed in 0..10u64 {
90 let document = document_type
91 .random_document(Some(seed), platform_version)
92 .expect("expected random document");
93
94 let value = Document::into_value(document.clone()).expect("into_value should succeed");
95
96 let recovered = Document::from_platform_value(value, platform_version)
97 .expect("from_platform_value should succeed");
98
99 assert_eq!(document.id(), recovered.id(), "id mismatch for seed {seed}");
100 assert_eq!(
101 document.owner_id(),
102 recovered.owner_id(),
103 "owner_id mismatch for seed {seed}"
104 );
105 assert_eq!(
106 document.revision(),
107 recovered.revision(),
108 "revision mismatch for seed {seed}"
109 );
110 assert_eq!(
111 document.properties(),
112 recovered.properties(),
113 "properties mismatch for seed {seed}"
114 );
115 }
116 }
117
118 #[test]
123 fn to_map_value_contains_id_and_owner_id() {
124 let platform_version = PlatformVersion::latest();
125 let contract = json_document_to_contract(
126 "../rs-drive/tests/supporting_files/contract/dashpay/dashpay-contract.json",
127 false,
128 platform_version,
129 )
130 .expect("expected to load dashpay contract");
131
132 let document_type = contract
133 .document_type_for_name("profile")
134 .expect("expected profile document type");
135
136 let document = document_type
137 .random_document(Some(42), platform_version)
138 .expect("expected random document");
139
140 let map = document
141 .to_map_value()
142 .expect("to_map_value should succeed");
143 assert!(map.contains_key("$id"), "map should contain $id");
144 assert!(map.contains_key("$ownerId"), "map should contain $ownerId");
145 }
146
147 #[test]
152 fn to_object_returns_map_value() {
153 let platform_version = PlatformVersion::latest();
154 let contract = json_document_to_contract(
155 "../rs-drive/tests/supporting_files/contract/dashpay/dashpay-contract.json",
156 false,
157 platform_version,
158 )
159 .expect("expected to load dashpay contract");
160
161 let document_type = contract
162 .document_type_for_name("profile")
163 .expect("expected profile document type");
164
165 let document = document_type
166 .random_document(Some(7), platform_version)
167 .expect("expected random document");
168
169 let obj = document.to_object().expect("to_object should succeed");
170 assert!(obj.is_map(), "to_object should return a Map value");
171 }
172
173 #[test]
178 fn into_map_value_consumes_and_returns_correct_data() {
179 let platform_version = PlatformVersion::latest();
180 let contract = json_document_to_contract(
181 "../rs-drive/tests/supporting_files/contract/dashpay/dashpay-contract.json",
182 false,
183 platform_version,
184 )
185 .expect("expected to load dashpay contract");
186
187 let document_type = contract
188 .document_type_for_name("profile")
189 .expect("expected profile document type");
190
191 let document = document_type
192 .random_document(Some(55), platform_version)
193 .expect("expected random document");
194
195 let original_id = document.id();
196 let map = document
197 .into_map_value()
198 .expect("into_map_value should succeed");
199
200 let id_val = map.get("$id").expect("should have $id");
202 match id_val {
203 Value::Identifier(bytes) => {
204 assert_eq!(
205 Identifier::new(*bytes),
206 original_id,
207 "id in map should match original"
208 );
209 }
210 _ => panic!("$id should be an Identifier value"),
211 }
212 }
213
214 #[test]
219 fn from_platform_value_with_minimal_data() {
220 let platform_version = PlatformVersion::latest();
221 let id = Identifier::new([1u8; 32]);
222 let owner_id = Identifier::new([2u8; 32]);
223
224 let doc_v0 = DocumentV0 {
225 id,
226 owner_id,
227 properties: std::collections::BTreeMap::new(),
228 revision: None,
229 created_at: None,
230 updated_at: None,
231 transferred_at: None,
232 created_at_block_height: None,
233 updated_at_block_height: None,
234 transferred_at_block_height: None,
235 created_at_core_block_height: None,
236 updated_at_core_block_height: None,
237 transferred_at_core_block_height: None,
238 creator_id: None,
239 };
240
241 let value = DocumentV0::into_value(doc_v0).expect("into_value should succeed");
242 let recovered = Document::from_platform_value(value, platform_version)
243 .expect("from_platform_value should succeed");
244
245 assert_eq!(recovered.id(), id);
246 assert_eq!(recovered.owner_id(), owner_id);
247 }
248}