Skip to content

Commit

Permalink
Automatically determine chain id through web3 (#1416)
Browse files Browse the repository at this point in the history
instead of having to specify it on the command line.

For the contract using the chain id instead of network id is what was
intended anyway and for the gas station it doesn't matter whether we
match on network id or chain id because they are the same for mainnet
and rinkeby.

Based on Felix' suggestion.

### Test Plan
Added a debug print to the gas station to see which chain id is used and tried it with mainnet and rinkeby node url.
  • Loading branch information
e00E authored Sep 11, 2020
1 parent 7ecfb08 commit be798b3
Show file tree
Hide file tree
Showing 7 changed files with 27 additions and 36 deletions.
16 changes: 6 additions & 10 deletions driver/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -51,11 +51,6 @@ struct Options {
#[structopt(short, long, env = "ETHEREUM_NODE_URL")]
node_url: Url,

/// The network ID used for signing transactions (e.g. 1 for mainnet, 4 for
/// rinkeby, 5777 for ganache).
#[structopt(short = "i", long, env = "NETWORK_ID")]
network_id: u64,

/// Which style of solver to use. Can be one of:
/// 'NaiveSolver' for the naive solver;
/// 'StandardSolver' for mixed integer programming solver;
Expand Down Expand Up @@ -256,11 +251,11 @@ fn main() {

// Set up shared HTTP client and HTTP services.
let http_factory = HttpFactory::new(options.http_timeout, http_metrics);
let (web3, gas_station) = setup_http_services(&http_factory, &options);
let (web3, gas_station) = setup_http_services(&http_factory, &options).wait();

// Set up connection to exchange contract
let contract = Arc::new(
StableXContractImpl::new(&web3, options.private_key.clone(), options.network_id)
StableXContractImpl::new(&web3, options.private_key.clone())
.wait()
.unwrap(),
);
Expand Down Expand Up @@ -362,13 +357,14 @@ fn setup_monitoring() -> (
(stablex_metrics, http_metrics, solver_metrics, health)
}

fn setup_http_services(
async fn setup_http_services(
http_factory: &HttpFactory,
options: &Options,
) -> (Web3, Arc<dyn GasPriceEstimating + Send + Sync>) {
let web3 = web3_provider(http_factory, options.node_url.as_str(), options.rpc_timeout).unwrap();
let gas_station =
gas_price::create_estimator(options.network_id, &http_factory, &web3).unwrap();
let gas_station = gas_price::create_estimator(&http_factory, &web3)
.await
.unwrap();
(web3, gas_station)
}

Expand Down
16 changes: 4 additions & 12 deletions price-estimator/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -55,11 +55,6 @@ struct Options {
#[structopt(long, env = "ETHEREUM_NODE_URL")]
node_url: Url,

/// The network ID used for gas estimations.
/// For example 1 for mainnet, 4 for rinkeby.
#[structopt(long, env = "NETWORK_ID", default_value = "1")]
network_id: u64,

/// The timeout in seconds of web3 JSON RPC calls.
#[structopt(
long,
Expand Down Expand Up @@ -154,13 +149,10 @@ fn main() {
let web3 = web3_provider(&http_factory, options.node_url.as_str(), options.timeout).unwrap();
// The private key is not actually used but StableXContractImpl requires it.
let private_key = PrivateKey::from_raw([1u8; 32]).unwrap();
let contract = Arc::new(
StableXContractImpl::new(&web3, private_key, 0)
.wait()
.unwrap(),
);
let gas_station =
gas_price::create_estimator(options.network_id, &http_factory, &web3).unwrap();
let contract = Arc::new(StableXContractImpl::new(&web3, private_key).wait().unwrap());
let gas_station = gas_price::create_estimator(&http_factory, &web3)
.wait()
.unwrap();

let cache: HashMap<_, _> = options.token_data.clone().into();
let token_info = TokenInfoCache::with_cache(contract.clone(), cache);
Expand Down
4 changes: 2 additions & 2 deletions services-core/src/contracts.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@ pub fn web3_provider(http_factory: &HttpFactory, url: &str, timeout: Duration) -
Ok(web3)
}

fn method_defaults(key: PrivateKey, network_id: u64) -> Result<MethodDefaults> {
let account = Account::Offline(key, Some(network_id));
fn method_defaults(key: PrivateKey, chain_id: u64) -> Result<MethodDefaults> {
let account = Account::Offline(key, Some(chain_id));
let defaults = MethodDefaults {
from: Some(account),
gas: None,
Expand Down
13 changes: 8 additions & 5 deletions services-core/src/contracts/stablex_contract.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,11 @@ use ethcontract::{
transaction::{confirm::ConfirmParams, Account, GasPrice, ResolveCondition, TransactionResult},
Address, BlockNumber, PrivateKey, U256,
};
use futures::future::{BoxFuture, FutureExt as _};
use futures::{
compat::Future01CompatExt as _,
future::{BoxFuture, FutureExt as _},
};

use lazy_static::lazy_static;
use std::collections::HashMap;
use std::time::Duration;
Expand All @@ -33,8 +37,9 @@ pub struct StableXContractImpl {
}

impl StableXContractImpl {
pub async fn new(web3: &contracts::Web3, key: PrivateKey, network_id: u64) -> Result<Self> {
let defaults = contracts::method_defaults(key, network_id)?;
pub async fn new(web3: &contracts::Web3, key: PrivateKey) -> Result<Self> {
let chain_id = web3.eth().chain_id().compat().await?.as_u64();
let defaults = contracts::method_defaults(key, chain_id)?;

let viewer = BatchExchangeViewer::deployed(&web3).await?;
let mut instance = BatchExchange::deployed(&web3).await?;
Expand Down Expand Up @@ -324,8 +329,6 @@ impl StableXContract for StableXContractImpl {
}

async fn get_transaction_count(&self) -> Result<U256> {
use futures::compat::Future01CompatExt as _;

let web3 = self.instance.raw_instance().web3();
let account = self.account().ok_or_else(|| anyhow!("no account"))?;
let address = account.address();
Expand Down
7 changes: 4 additions & 3 deletions services-core/src/gas_price.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ pub use self::gas_station::GnosisSafeGasStation;
use crate::{contracts::Web3, http::HttpFactory};
use anyhow::Result;
use ethcontract::U256;
use futures::compat::Future01CompatExt as _;
use std::sync::Arc;

#[cfg_attr(test, mockall::automock)]
Expand All @@ -15,12 +16,12 @@ pub trait GasPriceEstimating {
}

/// Creates the default gas price estimator for the given network.
pub fn create_estimator(
network_id: u64,
pub async fn create_estimator(
http_factory: &HttpFactory,
web3: &Web3,
) -> Result<Arc<dyn GasPriceEstimating + Send + Sync>> {
Ok(match gas_station::api_url_from_network_id(network_id) {
let network_id = web3.net().version().compat().await?;
Ok(match gas_station::api_url_from_network_id(&network_id) {
Some(url) => Arc::new(GnosisSafeGasStation::new(http_factory, url)?),
None => Arc::new(web3.clone()),
})
Expand Down
6 changes: 3 additions & 3 deletions services-core/src/gas_price/gas_station.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,10 +12,10 @@ use uint::FromDecStrErr;
const DEFAULT_MAINNET_URI: &str = "https://safe-relay.gnosis.io/api/v1/gas-station/";
const DEFAULT_RINKEBY_URI: &str = "https://safe-relay.rinkeby.gnosis.io/api/v1/gas-station/";

pub fn api_url_from_network_id(network_id: u64) -> Option<&'static str> {
pub fn api_url_from_network_id(network_id: &str) -> Option<&'static str> {
match network_id {
1 => Some(DEFAULT_MAINNET_URI),
4 => Some(DEFAULT_RINKEBY_URI),
"1" => Some(DEFAULT_MAINNET_URI),
"4" => Some(DEFAULT_RINKEBY_URI),
_ => None,
}
}
Expand Down
1 change: 0 additions & 1 deletion services-core/src/token_info/onchain.rs
Original file line number Diff line number Diff line change
Expand Up @@ -44,7 +44,6 @@ mod tests {
"0x0102030405060708091011121314151617181920212223242526272829303132",
)
.expect("Invalid private key"),
1,
)
.wait()
.expect("Error creating contract")
Expand Down

0 comments on commit be798b3

Please sign in to comment.