dpp/document/serialization_traits/cbor_conversion/
mod.rs

1mod v0;
2
3use crate::document::{Document, DocumentV0};
4use crate::util::deserializer;
5use crate::util::deserializer::SplitFeatureVersionOutcome;
6use crate::version::PlatformVersion;
7use crate::ProtocolError;
8use ciborium::Value as CborValue;
9pub use v0::*;
10
11impl DocumentCborMethodsV0 for Document {
12    fn from_cbor(
13        document_cbor: &[u8],
14        document_id: Option<[u8; 32]>,
15        owner_id: Option<[u8; 32]>,
16        platform_version: &PlatformVersion,
17    ) -> Result<Self, ProtocolError>
18    where
19        Self: Sized,
20    {
21        let SplitFeatureVersionOutcome {
22            main_message_bytes: read_document_cbor,
23            feature_version,
24            ..
25        } = deserializer::split_cbor_feature_version(document_cbor)?;
26
27        if !platform_version
28            .dpp
29            .document_versions
30            .document_cbor_serialization_version
31            .check_version(feature_version)
32        {
33            return Err(ProtocolError::UnsupportedVersionMismatch {
34                method: "Document::from_cbor (for document structure)".to_string(),
35                allowed_versions: vec![0],
36                received: feature_version,
37            });
38        }
39
40        match feature_version {
41            0 => DocumentV0::from_cbor(read_document_cbor, document_id, owner_id, platform_version)
42                .map(|document| document.into()),
43            version => Err(ProtocolError::UnknownVersionMismatch {
44                method: "Document::from_cbor (for document structure)".to_string(),
45                known_versions: vec![0],
46                received: version,
47            }),
48        }
49    }
50
51    fn to_cbor_value(&self) -> Result<CborValue, ProtocolError> {
52        match self {
53            Document::V0(v0) => v0.to_cbor_value(),
54        }
55    }
56
57    fn to_cbor(&self) -> Result<Vec<u8>, ProtocolError> {
58        match self {
59            Document::V0(v0) => v0.to_cbor(),
60        }
61    }
62}
63
64#[cfg(test)]
65mod tests {
66    use super::*;
67    use crate::data_contract::accessors::v0::DataContractV0Getters;
68    use crate::data_contract::document_type::random_document::CreateRandomDocument;
69    use crate::document::serialization_traits::DocumentCborMethodsV0;
70    use crate::tests::json_document::json_document_to_contract;
71    use platform_version::version::LATEST_PLATFORM_VERSION;
72
73    #[test]
74    fn test_document_cbor_serialization() {
75        let contract = json_document_to_contract(
76            "../rs-drive/tests/supporting_files/contract/dashpay/dashpay-contract.json",
77            false,
78            LATEST_PLATFORM_VERSION,
79        )
80        .expect("expected to get cbor contract");
81
82        let document_type = contract
83            .document_type_for_name("profile")
84            .expect("expected to get profile document type");
85        let document = document_type
86            .random_document(Some(3333), LATEST_PLATFORM_VERSION)
87            .expect("expected to get a random document");
88
89        let document_cbor = document.to_cbor().expect("expected to encode to cbor");
90
91        let recovered_document = Document::from_cbor(
92            document_cbor.as_slice(),
93            None,
94            None,
95            LATEST_PLATFORM_VERSION,
96        )
97        .expect("expected to get document");
98
99        assert_eq!(recovered_document, document);
100    }
101}