ethers-rs/examples/contract.rs

66 lines
2.5 KiB
Rust
Raw Normal View History

use ethabi::Token;
2020-05-25 10:05:00 +00:00
use ethers::{
contract::{Contract, Detokenize},
types::Address,
2020-05-25 15:35:38 +00:00
HttpProvider, MainnetWallet,
2020-05-25 10:05:00 +00:00
};
use serde::Serialize;
2020-05-25 10:05:00 +00:00
use std::convert::TryFrom;
const ABI: &'static str = r#"[{"inputs":[{"internalType":"string","name":"value","type":"string"}],"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"author","type":"address"},{"indexed":false,"internalType":"string","name":"oldValue","type":"string"},{"indexed":false,"internalType":"string","name":"newValue","type":"string"}],"name":"ValueChanged","type":"event"},{"inputs":[],"name":"getValue","outputs":[{"internalType":"string","name":"","type":"string"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"string","name":"value","type":"string"}],"name":"setValue","outputs":[],"stateMutability":"nonpayable","type":"function"}]"#;
#[derive(Clone, Debug, Serialize)]
// TODO: This should be `derive`-able on such types -> similar to how Zexe's Deserialize is done
struct ValueChanged {
author: Address,
old_value: String,
new_value: String,
}
impl Detokenize for ValueChanged {
fn from_tokens(
tokens: Vec<Token>,
) -> Result<ValueChanged, ethers::contract::InvalidOutputType> {
let author: Address = tokens[0].clone().to_address().unwrap();
let old_value = tokens[1].clone().to_string().unwrap();
let new_value = tokens[2].clone().to_string().unwrap();
Ok(Self {
author,
old_value,
new_value,
})
}
}
2020-05-25 10:05:00 +00:00
#[tokio::main]
async fn main() -> Result<(), failure::Error> {
// connect to the network
let provider = HttpProvider::try_from("http://localhost:8545")?;
// create a wallet and connect it to the provider
2020-05-25 15:35:38 +00:00
let client = "d22cf25d564c3c3f99677f8710b2f045045f16eccd31140c92d6feb18c1169e9"
2020-05-25 10:05:00 +00:00
.parse::<MainnetWallet>()?
.connect(&provider);
// Contract should take both provider or a signer
2020-05-25 15:35:38 +00:00
// get the contract's address
let addr = "683BEE23D79A1D8664dF70714edA966e1484Fd3d".parse::<Address>()?;
2020-05-25 10:05:00 +00:00
2020-05-25 15:35:38 +00:00
// instantiate it
let contract = Contract::new(&client, serde_json::from_str(ABI)?, addr);
2020-05-25 15:35:38 +00:00
// call the method
let _tx_hash = contract.method("setValue", "hi".to_owned())?.send().await?;
2020-05-25 15:35:38 +00:00
let logs: Vec<ValueChanged> = contract
.event("ValueChanged")?
.from_block(0u64)
.query()
.await?;
2020-05-25 15:35:38 +00:00
println!("{}", serde_json::to_string(&logs)?);
2020-05-25 10:05:00 +00:00
Ok(())
}