Skip to main content

dpp/voting/votes/
mod.rs

1pub mod resource_vote;
2
3#[cfg(feature = "json-conversion")]
4use crate::serialization::JsonConvertible;
5#[cfg(feature = "value-conversion")]
6use crate::serialization::ValueConvertible;
7use crate::voting::votes::resource_vote::accessors::v0::ResourceVoteGettersV0;
8use crate::voting::votes::resource_vote::ResourceVote;
9use crate::ProtocolError;
10use bincode::{Decode, Encode};
11use derive_more::From;
12use platform_serialization_derive::{PlatformDeserialize, PlatformSerialize};
13use platform_value::Identifier;
14#[cfg(feature = "serde-conversion")]
15use serde::{Deserialize, Serialize};
16
17#[derive(Debug, Clone, Encode, Decode, PlatformSerialize, PlatformDeserialize, PartialEq, From)]
18#[cfg_attr(
19    feature = "serde-conversion",
20    derive(Serialize, Deserialize),
21    // Internal tagging with `$type` — system-field convention. Drops the
22    // `data` wrapper. Inner `ResourceVote` is `tag = "$formatVersion"`
23    // (different key, no collision).
24    serde(tag = "$type", rename_all = "camelCase")
25)]
26#[cfg_attr(feature = "value-conversion", derive(ValueConvertible))]
27#[platform_serialize(limit = 15000, unversioned)]
28pub enum Vote {
29    ResourceVote(ResourceVote),
30}
31
32// Manual impl because Vote is a flat enum (not versioned V0/V1).
33#[cfg(feature = "json-conversion")]
34impl JsonConvertible for Vote {}
35
36impl Default for Vote {
37    fn default() -> Self {
38        Vote::ResourceVote(ResourceVote::default())
39    }
40}
41
42impl Vote {
43    pub fn specialized_balance_id(&self) -> Result<Option<Identifier>, ProtocolError> {
44        match self {
45            Vote::ResourceVote(resource_vote) => resource_vote.vote_poll().specialized_balance_id(),
46        }
47    }
48    pub fn vote_poll_unique_id(&self) -> Result<Identifier, ProtocolError> {
49        match self {
50            Vote::ResourceVote(resource_vote) => resource_vote.vote_poll().unique_id(),
51        }
52    }
53}
54
55#[cfg(all(test, feature = "json-conversion"))]
56mod tests {
57    use super::*;
58    use crate::serialization::JsonConvertible;
59    use crate::voting::vote_choices::resource_vote_choice::ResourceVoteChoice;
60    use crate::voting::vote_polls::contested_document_resource_vote_poll::ContestedDocumentResourceVotePoll;
61    use crate::voting::vote_polls::VotePoll;
62    use crate::voting::votes::resource_vote::v0::ResourceVoteV0;
63    use crate::voting::votes::resource_vote::ResourceVote;
64
65    #[test]
66    fn vote_json_round_trip() {
67        let contract_id = Identifier::from([0x11u8; 32]);
68        let towards_id = Identifier::from([0x22u8; 32]);
69
70        let vote = Vote::ResourceVote(ResourceVote::V0(ResourceVoteV0 {
71            vote_poll: VotePoll::ContestedDocumentResourceVotePoll(
72                ContestedDocumentResourceVotePoll {
73                    contract_id,
74                    document_type_name: "domain".to_string(),
75                    index_name: "parentNameAndLabel".to_string(),
76                    index_values: vec![platform_value::Value::Text("dash".to_string())],
77                },
78            ),
79            resource_vote_choice: ResourceVoteChoice::TowardsIdentity(towards_id),
80        }));
81
82        let json = vote.to_json().expect("to_json should succeed");
83
84        // Verify it's a valid JSON object
85        assert!(json.is_object(), "Vote JSON should be an object");
86
87        // round-trip
88        let restored = Vote::from_json(json).expect("from_json should succeed");
89        assert_eq!(vote, restored);
90    }
91}
92
93#[cfg(all(
94    test,
95    feature = "json-conversion",
96    feature = "value-conversion",
97    feature = "serde-conversion"
98))]
99mod json_convertible_tests_vote {
100    use super::*;
101
102    #[test]
103    fn json_round_trip_vote() {
104        use crate::serialization::JsonConvertible;
105        let original = Vote::default();
106        let json = original.to_json().expect("to_json");
107        let recovered = Vote::from_json(json).expect("from_json");
108        assert_eq!(original, recovered);
109    }
110
111    #[test]
112    fn value_round_trip_vote() {
113        use crate::serialization::ValueConvertible;
114        let original = Vote::default();
115        let value = original.to_object().expect("to_object");
116        let recovered = Vote::from_object(value).expect("from_object");
117        assert_eq!(original, recovered);
118    }
119}