1use crate::address_funds::PlatformAddress;
2use crate::identity::v0::IdentityV0;
3use crate::identity::{IdentityPublicKey, KeyID};
4use crate::prelude::{AddressNonce, Revision};
5#[cfg(feature = "json-conversion")]
6use crate::serialization::json_safe_fields;
7#[cfg(feature = "value-conversion")]
8use crate::serialization::ValueConvertible;
9
10#[cfg(feature = "identity-hashing")]
11use crate::serialization::PlatformSerializable;
12#[cfg(feature = "identity-hashing")]
13use crate::util::hash;
14use crate::version::PlatformVersion;
15
16use crate::ProtocolError;
17#[cfg(feature = "identity-serialization")]
18use bincode::{Decode, Encode};
19use derive_more::From;
20#[cfg(feature = "identity-serialization")]
21use platform_serialization_derive::{PlatformDeserialize, PlatformSerialize};
22use platform_value::Identifier;
23
24use crate::fee::Credits;
25use std::collections::{BTreeMap, BTreeSet};
26
27#[derive(Debug, Clone, PartialEq, From)]
31#[cfg_attr(
32 any( feature = "serde-conversion" ,feature = "serde-conversion",),
33 derive(serde::Serialize, serde::Deserialize),
34 serde(tag = "$formatVersion"),
35 )]
37#[cfg_attr(
38 feature = "identity-serialization",
39 derive(Encode, Decode, PlatformDeserialize, PlatformSerialize),
40 platform_serialize(limit = 15000, unversioned)
41)]
42#[cfg_attr(feature = "value-conversion", derive(ValueConvertible))]
43pub enum Identity {
44 #[cfg_attr(
45 any(feature = "serde-conversion", feature = "serde-conversion"),
46 serde(rename = "0")
47 )]
48 V0(IdentityV0),
49}
50
51#[cfg_attr(feature = "json-conversion", json_safe_fields)]
53#[derive(Debug, Clone, Eq, PartialEq)]
54#[cfg_attr(
55 any(feature = "serde-conversion", feature = "serde-conversion",),
56 derive(serde::Serialize, serde::Deserialize),
57 serde(rename_all = "camelCase")
58)]
59pub struct PartialIdentity {
60 pub id: Identifier,
61 pub loaded_public_keys: BTreeMap<KeyID, IdentityPublicKey>,
62 pub balance: Option<Credits>,
63 pub revision: Option<Revision>,
64 pub not_found_public_keys: BTreeSet<KeyID>,
66}
67
68impl Identity {
69 #[cfg(feature = "identity-hashing")]
70 pub fn hash(&self) -> Result<Vec<u8>, ProtocolError> {
72 Ok(hash::hash_double_to_vec(
73 PlatformSerializable::serialize_to_bytes(self)?,
74 ))
75 }
76
77 pub fn default_versioned(
78 platform_version: &PlatformVersion,
79 ) -> Result<Identity, ProtocolError> {
80 match platform_version
81 .dpp
82 .identity_versions
83 .identity_structure_version
84 {
85 0 => Ok(Identity::V0(IdentityV0::default())),
86 version => Err(ProtocolError::UnknownVersionMismatch {
87 method: "Identity::default_versioned".to_string(),
88 known_versions: vec![0],
89 received: version,
90 }),
91 }
92 }
93
94 pub fn new_with_id_and_keys(
96 id: Identifier,
97 public_keys: BTreeMap<KeyID, IdentityPublicKey>,
98 platform_version: &PlatformVersion,
99 ) -> Result<Identity, ProtocolError> {
100 match platform_version
101 .dpp
102 .identity_versions
103 .identity_structure_version
104 {
105 0 => {
106 let identity_v0 = IdentityV0 {
107 id,
108 public_keys,
109 balance: 0,
110 revision: 0,
111 };
112 Ok(identity_v0.into())
113 }
114 version => Err(ProtocolError::UnknownVersionMismatch {
115 method: "Identity::new_with_id_and_keys".to_string(),
116 known_versions: vec![0],
117 received: version,
118 }),
119 }
120 }
121
122 #[cfg(feature = "state-transitions")]
138 pub fn new_with_input_addresses_and_keys(
139 inputs: &BTreeMap<PlatformAddress, (AddressNonce, Credits)>,
140 public_keys: BTreeMap<KeyID, IdentityPublicKey>,
141 platform_version: &PlatformVersion,
142 ) -> Result<Identity, ProtocolError> {
143 use crate::state_transition::identity_id_from_input_addresses;
144
145 let identity_id = identity_id_from_input_addresses(inputs)?;
146 Self::new_with_id_and_keys(identity_id, public_keys, platform_version)
147 }
148
149 pub fn into_partial_identity_info(self) -> PartialIdentity {
151 match self {
152 Identity::V0(v0) => v0.into_partial_identity_info(),
153 }
154 }
155
156 pub fn into_partial_identity_info_no_balance(self) -> PartialIdentity {
158 match self {
159 Identity::V0(v0) => v0.into_partial_identity_info_no_balance(),
160 }
161 }
162}