请务必阅读解码的先决条件 。
解码是通过ABIDecoder
完成的:
use fuels::{
core::{
codec::ABIDecoder,
traits::{Parameterize, Tokenizable},
},
macros::{Parameterize, Tokenizable},
types::Token,
};
#[derive(Parameterize, Tokenizable)]
struct MyStruct {
field: u64,
}
let bytes: &[u8] = &[0, 0, 0, 0, 0, 0, 0, 101];
let token: Token = ABIDecoder::default().decode(&MyStruct::param_type(), bytes)?;
let _: MyStruct = MyStruct::from_token(token)?;
首先是转换为Token
,然后通过Tokenizable
特性,转换为所需的类型。
如果类型来自abigen!
(或使用::fuels::macros::TryFrom
派生),那么您也可以使用try_into
将字节转换为同时实现Parameterize
和Tokenizable
的类型:
use fuels::macros::{Parameterize, Tokenizable, TryFrom};
#[derive(Parameterize, Tokenizable, TryFrom)]
struct MyStruct {
field: u64,
}
let bytes: &[u8] = &[0, 0, 0, 0, 0, 0, 0, 101];
let _: MyStruct = bytes.try_into()?;
在内部,调用了try_from_bytes
,这与前面的示例所做的事情相同。
可以配置解码器以限制其资源消耗:
use fuels::core::codec::ABIDecoder;
ABIDecoder::new(DecoderConfig {
max_depth: 5,
max_tokens: 100,
});
有关每个配置值的解释,请访问DecoderConfig
。
DecoderConfig
的默认值为:
impl Default for DecoderConfig {
fn default() -> Self {
Self {
max_depth: 45,
max_tokens: 10_000,
}
}
}
您还可以配置用于解码合约方法返回值的解码器:
let _ = contract_instance
.methods()
.initialize_counter(42)
.with_decoder_config(DecoderConfig {
max_depth: 10,
max_tokens: 2_000,
})
.call()
.await?;
同样的方法也适用于脚本调用。