dpp/tests/
json_document.rs1use crate::data_contract::accessors::v0::DataContractV0Setters;
2#[cfg(feature = "json-conversion")]
3use crate::data_contract::config::DataContractConfig;
4#[cfg(feature = "json-conversion")]
5use crate::data_contract::conversion::json::DataContractJsonConversionMethodsV0;
6#[cfg(any(feature = "state-transitions", feature = "factories"))]
7use crate::data_contract::created_data_contract::v0::CreatedDataContractV0;
8#[cfg(any(feature = "state-transitions", feature = "factories"))]
9use crate::data_contract::created_data_contract::CreatedDataContract;
10use crate::data_contract::document_type::accessors::DocumentTypeV0Getters;
11use crate::data_contract::document_type::DocumentTypeRef;
12use crate::document::{Document, DocumentV0};
13use crate::prelude::{DataContract, IdentityNonce};
14#[cfg(feature = "data-contract-cbor-conversion")]
15use crate::util::cbor_serializer::serializable_value_to_cbor;
16use crate::version::PlatformVersion;
17use crate::ProtocolError;
18use platform_value::{Identifier, ReplacementType};
19use std::fs::File;
20use std::io::BufReader;
21use std::path::Path;
22
23#[cfg(feature = "json-conversion")]
25pub fn json_document_to_json_value(
26 path: impl AsRef<Path>,
27) -> Result<serde_json::Value, ProtocolError> {
28 let file = File::open(path.as_ref()).map_err(|_| {
29 ProtocolError::FileNotFound(format!(
30 "file not found at path {}",
31 path.as_ref().to_str().unwrap()
32 ))
33 })?;
34
35 let reader = BufReader::new(file);
36 serde_json::from_reader(reader)
37 .map_err(|_| ProtocolError::DecodingError("error decoding value from document".to_string()))
38}
39
40pub fn json_document_to_platform_value(
42 path: impl AsRef<Path>,
43) -> Result<platform_value::Value, ProtocolError> {
44 let file = File::open(path.as_ref()).map_err(|_| {
45 ProtocolError::FileNotFound(format!(
46 "file not found at path {}",
47 path.as_ref().to_str().unwrap()
48 ))
49 })?;
50
51 let reader = BufReader::new(file);
52 serde_json::from_reader(reader)
53 .map_err(|_| ProtocolError::DecodingError("error decoding value from document".to_string()))
54}
55
56#[cfg(feature = "data-contract-cbor-conversion")]
58pub fn json_document_to_cbor(
59 path: impl AsRef<Path>,
60 protocol_version: Option<u32>,
61) -> Result<Vec<u8>, ProtocolError> {
62 let json = json_document_to_json_value(path)?;
63 serializable_value_to_cbor(&json, protocol_version)
64}
65
66#[cfg(feature = "json-conversion")]
68pub fn json_document_to_contract(
69 path: impl AsRef<Path>,
70 full_validation: bool,
71 platform_version: &PlatformVersion,
72) -> Result<DataContract, ProtocolError> {
73 let value = json_document_to_json_value(path)?;
74
75 if full_validation {
76 DataContract::from_json(value, true, platform_version)
77 } else {
78 let format: crate::data_contract::serialized_version::DataContractInSerializationFormat =
85 serde_json::from_value(value)
86 .map_err(|e| ProtocolError::DecodingError(e.to_string()))?;
87 DataContract::try_from_platform_versioned(format, false, &mut vec![], platform_version)
88 }
89}
90
91#[cfg(all(
92 any(feature = "state-transitions", feature = "factories"),
93 feature = "json-conversion"
94))]
95pub fn json_document_to_created_contract(
97 path: impl AsRef<Path>,
98 identity_nonce: IdentityNonce,
99 full_validation: bool,
100 platform_version: &PlatformVersion,
101) -> Result<CreatedDataContract, ProtocolError> {
102 let mut data_contract = json_document_to_contract(path, full_validation, platform_version)?;
103
104 data_contract.set_config(DataContractConfig::default_for_version(platform_version)?);
108
109 Ok(CreatedDataContractV0 {
110 data_contract,
111 identity_nonce,
112 }
113 .into())
114}
115
116#[cfg(feature = "json-conversion")]
118pub fn json_document_to_contract_with_ids(
119 path: impl AsRef<Path>,
120 id: Option<Identifier>,
121 owner_id: Option<Identifier>,
122 full_validation: bool,
123 platform_version: &PlatformVersion,
124) -> Result<DataContract, ProtocolError> {
125 let value = json_document_to_json_value(path)?;
126
127 let mut contract = DataContract::from_json(value, full_validation, platform_version)?;
128
129 if let Some(id) = id {
130 contract.set_id(id);
131 }
132
133 if let Some(owner_id) = owner_id {
134 contract.set_owner_id(owner_id);
135 }
136
137 Ok(contract)
138}
139
140pub fn json_document_to_document(
142 path: impl AsRef<Path>,
143 owner_id: Option<Identifier>,
144 document_type: DocumentTypeRef,
145 _platform_version: &PlatformVersion,
146) -> Result<Document, ProtocolError> {
147 let mut data = json_document_to_platform_value(path)?;
148
149 if let Some(owner_id) = owner_id {
150 data.set_value(
151 "$ownerId",
152 platform_value::Value::Identifier(owner_id.into_buffer()),
153 )?;
154 }
155
156 let mut document: DocumentV0 = DocumentV0 {
157 id: data.remove_identifier("$id")?,
158 owner_id: data.remove_identifier("$ownerId")?,
159 properties: Default::default(),
160 revision: data.remove_optional_integer("$revision")?,
161 created_at: data.remove_optional_integer("$createdAt")?,
162 updated_at: data.remove_optional_integer("$updatedAt")?,
163 transferred_at: data.remove_optional_integer("$transferredAt")?,
164 created_at_block_height: data.remove_optional_integer("$createdAtBlockHeight")?,
165 updated_at_block_height: data.remove_optional_integer("$updatedAtBlockHeight")?,
166 transferred_at_block_height: data.remove_optional_integer("$transferredAtBlockHeight")?,
167 created_at_core_block_height: data.remove_optional_integer("$createdAtCoreBlockHeight")?,
168 updated_at_core_block_height: data.remove_optional_integer("$updatedAtCoreBlockHeight")?,
169 transferred_at_core_block_height: data
170 .remove_optional_integer("$transferredAtCoreBlockHeight")?,
171 creator_id: data.remove_optional_identifier("$creatorId")?,
172 };
173
174 data.replace_at_paths(
175 document_type.identifier_paths().iter().map(|s| s.as_str()),
176 ReplacementType::Identifier,
177 )?;
178
179 data.replace_at_paths(
180 document_type.binary_paths().iter().map(|s| s.as_str()),
181 ReplacementType::BinaryBytes,
182 )?;
183
184 document.properties = data
185 .into_btree_string_map()
186 .map_err(ProtocolError::ValueError)?;
187
188 Ok(document.into())
189}