Pcd is BTreeMap<String, Vec<u8>>

This commit is contained in:
NicolasCantu 2025-06-03 18:04:27 +02:00 committed by Nicolas Cantu
parent 4f758d981c
commit b5c1c1ea79

View File

@ -1,8 +1,6 @@
use anyhow::{Error, Result}; use anyhow::{Error, Result};
use rs_merkle::{algorithms::Sha256, MerkleTree}; use rs_merkle::{algorithms::Sha256, MerkleTree};
use serde::de::{DeserializeOwned, Error as DeError};
use serde::ser::SerializeStruct; use serde::ser::SerializeStruct;
use wasm_bindgen::JsValue;
use std::collections::btree_map::Keys; use std::collections::btree_map::Keys;
use std::collections::{BTreeMap, HashSet}; use std::collections::{BTreeMap, HashSet};
use std::hash::{Hash as StdHash, Hasher}; use std::hash::{Hash as StdHash, Hasher};
@ -132,24 +130,37 @@ impl AnkPcdHash {
#[derive(Debug, Default, Clone, Serialize, Deserialize, PartialEq, Tsify)] #[derive(Debug, Default, Clone, Serialize, Deserialize, PartialEq, Tsify)]
#[tsify(into_wasm_abi, from_wasm_abi)] #[tsify(into_wasm_abi, from_wasm_abi)]
pub struct Pcd(BTreeMap<String, Value>); pub struct Pcd(BTreeMap<String, Vec<u8>>);
impl IntoIterator for Pcd { impl IntoIterator for Pcd {
type Item = (String, Value); type Item = (String, Vec<u8>);
type IntoIter = std::collections::btree_map::IntoIter<String, Value>; type IntoIter = std::collections::btree_map::IntoIter<String, Vec<u8>>;
fn into_iter(self) -> Self::IntoIter { fn into_iter(self) -> Self::IntoIter {
self.0.into_iter() self.0.into_iter()
} }
} }
impl TryFrom<Value> for Pcd {
type Error = Error;
fn try_from(value: Value) -> Result<Self> {
let as_object = value.as_object().ok_or_else(|| Error::msg("Pcd must be an object"))?;
let map: Result<BTreeMap<String, Vec<u8>>> = as_object.iter().map(|(key, value)| {
let serialized = crate::serialization::ciborium_serialize(value)?;
Ok((key.clone(), serialized))
}).collect();
Ok(Pcd(map?))
}
}
impl Pcd { impl Pcd {
pub fn new(map: BTreeMap<String, Value>) -> Self { pub fn new(map: BTreeMap<String, Vec<u8>>) -> Self {
Self(map) Self(map)
} }
pub fn get(&self, key: &str) -> Option<&Value> { pub fn get(&self, key: &str) -> Option<&Vec<u8>> {
self.0.get(key) self.0.get(key)
} }
@ -157,15 +168,15 @@ impl Pcd {
self.0.len() self.0.len()
} }
pub fn iter(&self) -> std::collections::btree_map::Iter<'_, String, Value> { pub fn iter(&self) -> std::collections::btree_map::Iter<'_, String, Vec<u8>> {
self.0.iter() self.0.iter()
} }
pub fn iter_mut(&mut self) -> std::collections::btree_map::IterMut<'_, String, Value> { pub fn iter_mut(&mut self) -> std::collections::btree_map::IterMut<'_, String, Vec<u8>> {
self.0.iter_mut() self.0.iter_mut()
} }
pub fn insert(&mut self, key: String, value: Value) -> Option<Value> { pub fn insert(&mut self, key: String, value: Vec<u8>) -> Option<Vec<u8>> {
self.0.insert(key, value) self.0.insert(key, value)
} }
} }
@ -206,16 +217,18 @@ impl PcdCommitments {
self.0.is_empty() self.0.is_empty()
} }
pub fn update_with_value(&mut self, outpoint: &OutPoint, field: &str, new_value: &Value) -> Result<()> { pub fn update_with_value(&mut self, outpoint: &OutPoint, field: &str, new_value: &[u8]) -> Result<()> {
let serialized_outpoint = serialize(outpoint); let serialized_outpoint = serialize(outpoint);
if let Some(old_hash) = self.get_mut(field) { if let Some(old_hash) = self.get_mut(field) {
// We hash the new_value // We hash the new_value
let mut value_bin = serde_json::to_string(new_value)?.into_bytes(); let mut value_bin = new_value.to_vec();
value_bin.extend_from_slice(field.as_bytes()); value_bin.extend_from_slice(field.as_bytes());
let tagged_hash = AnkPcdHash::from_value_with_outpoint(&value_bin, &serialized_outpoint); let tagged_hash = AnkPcdHash::from_value_with_outpoint(&value_bin, &serialized_outpoint);
*old_hash = tagged_hash.to_byte_array(); *old_hash = tagged_hash.to_byte_array();
Ok(())
} else {
Err(Error::msg("Field not found"))
} }
Ok(())
} }
pub fn contains_key(&self, key: &str) -> bool { pub fn contains_key(&self, key: &str) -> bool {