gear_subxt/constants/
constants_client.rs1use super::ConstantAddress;
6use crate::{
7 client::OfflineClientT,
8 error::{Error, MetadataError},
9 metadata::DecodeWithMetadata,
10 Config,
11};
12use derivative::Derivative;
13
14#[derive(Derivative)]
16#[derivative(Clone(bound = "Client: Clone"))]
17pub struct ConstantsClient<T, Client> {
18 client: Client,
19 _marker: std::marker::PhantomData<T>,
20}
21
22impl<T, Client> ConstantsClient<T, Client> {
23 pub fn new(client: Client) -> Self {
25 Self {
26 client,
27 _marker: std::marker::PhantomData,
28 }
29 }
30}
31
32impl<T: Config, Client: OfflineClientT<T>> ConstantsClient<T, Client> {
33 pub fn validate<Address: ConstantAddress>(&self, address: &Address) -> Result<(), Error> {
38 if let Some(actual_hash) = address.validation_hash() {
39 let expected_hash = self
40 .client
41 .metadata()
42 .pallet_by_name_err(address.pallet_name())?
43 .constant_hash(address.constant_name())
44 .ok_or_else(|| {
45 MetadataError::ConstantNameNotFound(address.constant_name().to_owned())
46 })?;
47 if actual_hash != expected_hash {
48 return Err(MetadataError::IncompatibleCodegen.into());
49 }
50 }
51 Ok(())
52 }
53
54 pub fn at<Address: ConstantAddress>(
58 &self,
59 address: &Address,
60 ) -> Result<Address::Target, Error> {
61 let metadata = self.client.metadata();
62
63 self.validate(address)?;
65
66 let constant = metadata
68 .pallet_by_name_err(address.pallet_name())?
69 .constant_by_name(address.constant_name())
70 .ok_or_else(|| {
71 MetadataError::ConstantNameNotFound(address.constant_name().to_owned())
72 })?;
73 let value = <Address::Target as DecodeWithMetadata>::decode_with_metadata(
74 &mut constant.value(),
75 constant.ty(),
76 &metadata,
77 )?;
78 Ok(value)
79 }
80}