account.rs

Overview

This file defines the WrappedAccount structure, which encapsulates an account identifier (AccountAddress) alongside the account state data (tvm_block::ShardAccount). It provides serialization and deserialization support for WrappedAccount instances by leveraging a helper struct, WrappedAccountData, to convert the account data to and from a byte representation. This enables safe transmission and storage of account data in serialized formats such as JSON or binary.

Structures and Implementations

WrappedAccount

pub struct WrappedAccount {
    pub account_id: AccountAddress,
    pub account: tvm_block::ShardAccount,
}

Traits Implemented

Debug Implementation

The Debug trait is implemented to display only the hexadecimal string representation of the account_id, providing a concise debug output without exposing the entire account data.

impl Debug for WrappedAccount {
    fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
        write!(f, "{}", self.account_id.to_hex_string())
    }
}

Serialization and Deserialization

To facilitate serialization and deserialization, two helper methods are defined:

These methods rely on the Serializable and Deserializable traits implemented by tvm_block::ShardAccount for byte-level conversion.

impl WrappedAccount {
    fn wrap_serialize(&self) -> WrappedAccountData {
        WrappedAccountData {
            account_id: self.account_id.clone(),
            data: self.account.write_to_bytes().unwrap(),
        }
    }

    fn wrap_deserialize(data: WrappedAccountData) -> Self {
        Self {
            account_id: data.account_id.clone(),
            account: tvm_block::ShardAccount::construct_from_bytes(&data.data).unwrap(),
        }
    }
}
Serialize Trait Implementation

The Serialize trait is implemented by delegating serialization to the WrappedAccountData structure:

impl Serialize for WrappedAccount {
    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
    where
        S: Serializer,
    {
        self.wrap_serialize().serialize(serializer)
    }
}
Deserialize Trait Implementation

Similarly, the Deserialize trait is implemented by first deserializing into WrappedAccountData and then reconstructing WrappedAccount:

impl<'de> Deserialize<'de> for WrappedAccount {
    fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
    where
        D: Deserializer<'de>,
    {
        let data = WrappedAccountData::deserialize(deserializer)?;
        let account = WrappedAccount::wrap_deserialize(data);
        Ok(account)
    }
}

WrappedAccountData

#[derive(Serialize, Deserialize)]
struct WrappedAccountData {
    account_id: AccountAddress,
    data: Vec<u8>,
}

This struct derives Serialize and Deserialize traits automatically, enabling straightforward (de)serialization with Serde.

Important Implementation Details

Interactions with Other Components

Usage Example

use crate::account::WrappedAccount;
use crate::types::AccountAddress;
use tvm_block::ShardAccount;

// Construct a WrappedAccount
let account_address = AccountAddress::from_hex("abcdef1234567890");
let shard_account = ShardAccount::new(...);  // assume some constructor
let wrapped_account = WrappedAccount {
    account_id: account_address,
    account: shard_account,
};

// Serialize the wrapped account
let serialized = serde_json::to_string(&wrapped_account).unwrap();

// Deserialize back
let deserialized: WrappedAccount = serde_json::from_str(&serialized).unwrap();

// Debug print
println!("{:?}", deserialized);

File Structure Diagram

classDiagram
class WrappedAccount {
+account_id: AccountAddress
+account: ShardAccount
+wrap_serialize()
+wrap_deserialize()
+serialize()
+deserialize()
}
class WrappedAccountData {
+account_id: AccountAddress
+data: Vec<u8>
}
WrappedAccount ..> WrappedAccountData : uses
WrappedAccount --> "ShardAccount" : contains
WrappedAccount --> "AccountAddress" : contains
WrappedAccountData --> "AccountAddress" : contains