diff --git a/ethcontract-derive/Cargo.toml b/ethcontract-derive/Cargo.toml index 3d3a5650..7100da58 100644 --- a/ethcontract-derive/Cargo.toml +++ b/ethcontract-derive/Cargo.toml @@ -11,13 +11,17 @@ description = """ Proc macro for generating type-safe bindings to Ethereum smart contracts. """ +[features] +default = ["http"] +http = ["ethcontract-generate/http"] + [lib] proc-macro = true [dependencies] anyhow = "1.0" ethcontract-common = { version = "0.16.0", path = "../ethcontract-common" } -ethcontract-generate = { version = "0.16.0", path = "../ethcontract-generate" } +ethcontract-generate = { version = "0.16.0", path = "../ethcontract-generate", default-features = false } proc-macro2 = "1.0" quote = "1.0" syn = "1.0.12" diff --git a/ethcontract-generate/Cargo.toml b/ethcontract-generate/Cargo.toml index fef7776d..af4ad331 100644 --- a/ethcontract-generate/Cargo.toml +++ b/ethcontract-generate/Cargo.toml @@ -11,9 +11,13 @@ description = """ Code generation for type-safe bindings to Ethereum smart contracts. """ +[features] +default = ["http"] +http = ["curl"] + [dependencies] anyhow = "1.0" -curl = "0.4" +curl = { version = "0.4", optional = true } ethcontract-common = { version = "0.16.0", path = "../ethcontract-common" } Inflector = "0.11" proc-macro2 = "1.0" diff --git a/ethcontract-generate/src/source.rs b/ethcontract-generate/src/source.rs index 060ae0ae..06cb7a1f 100644 --- a/ethcontract-generate/src/source.rs +++ b/ethcontract-generate/src/source.rs @@ -23,8 +23,10 @@ //! .expect("failed to load an artifact"); //! ``` +#[cfg(feature = "http")] use crate::util; use anyhow::{anyhow, Context, Error, Result}; +#[cfg(feature = "http")] use ethcontract_common::Address; use std::borrow::Cow; use std::env; @@ -40,6 +42,7 @@ pub enum Source { Local(PathBuf), /// Resource in the internet, available via HTTP(S). + #[cfg(feature = "http")] Http(Url), /// An address of a mainnet contract, available via [Etherscan]. @@ -53,12 +56,14 @@ pub enum Source { /// /// [Etherscan]: etherscan.io /// [truffle loader]: ethcontract_common::artifact::truffle::TruffleLoader + #[cfg(feature = "http")] Etherscan(Address), /// The package identifier of an NPM package with a path to an artifact /// or ABI to be retrieved from [unpkg]. /// /// [unpkg]: unpkg.io + #[cfg(feature = "http")] Npm(String), } @@ -106,6 +111,7 @@ impl Source { match url.scheme() { "file" => Ok(Source::local(url.path())), + #[cfg(feature = "http")] "http" | "https" => match url.host_str() { Some("etherscan.io") => Source::etherscan( url.path() @@ -115,7 +121,9 @@ impl Source { ), _ => Ok(Source::Http(url)), }, + #[cfg(feature = "http")] "etherscan" => Source::etherscan(url.path()), + #[cfg(feature = "http")] "npm" => Ok(Source::npm(url.path())), _ => Err(anyhow!("unsupported URL '{}'", url)), } @@ -127,6 +135,7 @@ impl Source { } /// Creates an HTTP source from a URL. + #[cfg(feature = "http")] pub fn http(url: &str) -> Result { Ok(Source::Http(Url::parse(url)?)) } @@ -134,6 +143,7 @@ impl Source { /// Creates an [Etherscan] source from contract address on mainnet. /// /// [Etherscan]: etherscan.io + #[cfg(feature = "http")] pub fn etherscan(address: &str) -> Result { util::parse_address(address) .context("failed to parse address for Etherscan source") @@ -141,6 +151,7 @@ impl Source { } /// Creates an NPM source from a package path. + #[cfg(feature = "http")] pub fn npm(package_path: impl Into) -> Self { Source::Npm(package_path.into()) } @@ -157,8 +168,11 @@ impl Source { pub fn artifact_json(&self) -> Result { match self { Source::Local(path) => get_local_contract(path), + #[cfg(feature = "http")] Source::Http(url) => get_http_contract(url), + #[cfg(feature = "http")] Source::Etherscan(address) => get_etherscan_contract(*address), + #[cfg(feature = "http")] Source::Npm(package) => get_npm_contract(package), } } @@ -192,12 +206,14 @@ fn get_local_contract(path: &Path) -> Result { Ok(abi_or_artifact(json)) } +#[cfg(feature = "http")] fn get_http_contract(url: &Url) -> Result { let json = util::http_get(url.as_str()) .with_context(|| format!("failed to retrieve JSON from {}", url))?; Ok(abi_or_artifact(json)) } +#[cfg(feature = "http")] fn get_etherscan_contract(address: Address) -> Result { // NOTE: We do not retrieve the bytecode since deploying contracts with the // same bytecode is unreliable as the libraries have already linked and @@ -225,6 +241,7 @@ fn get_etherscan_contract(address: Address) -> Result { Ok(json) } +#[cfg(feature = "http")] fn get_npm_contract(package: &str) -> Result { let unpkg_url = format!("https://unpkg.com/{}", package); let json = util::http_get(&unpkg_url) @@ -268,18 +285,22 @@ mod tests { "/absolute/Contract.json", Source::local("/absolute/Contract.json"), ), + #[cfg(feature = "http")] ( "https://my.domain.eth/path/to/Contract.json", Source::http("https://my.domain.eth/path/to/Contract.json").unwrap(), ), + #[cfg(feature = "http")] ( "etherscan:0x0001020304050607080910111213141516171819", Source::etherscan("0x0001020304050607080910111213141516171819").unwrap(), ), + #[cfg(feature = "http")] ( "https://etherscan.io/address/0x0001020304050607080910111213141516171819", Source::etherscan("0x0001020304050607080910111213141516171819").unwrap(), ), + #[cfg(feature = "http")] ( "npm:@openzeppelin/contracts@2.5.0/build/contracts/IERC20.json", Source::npm("@openzeppelin/contracts@2.5.0/build/contracts/IERC20.json"), diff --git a/ethcontract-generate/src/util.rs b/ethcontract-generate/src/util.rs index 1360faf3..52b846ca 100644 --- a/ethcontract-generate/src/util.rs +++ b/ethcontract-generate/src/util.rs @@ -1,4 +1,5 @@ use anyhow::{anyhow, Result}; +#[cfg(feature = "http")] use curl::easy::Easy; use ethcontract_common::Address; use inflector::Inflector; @@ -54,6 +55,7 @@ where } /// Performs an HTTP GET request and return the contents of the response. +#[cfg(feature = "http")] pub fn http_get(url: &str) -> Result { let mut buffer = Vec::new(); let mut handle = Easy::new(); diff --git a/ethcontract-mock/Cargo.toml b/ethcontract-mock/Cargo.toml index 822643c1..8ca2155a 100644 --- a/ethcontract-mock/Cargo.toml +++ b/ethcontract-mock/Cargo.toml @@ -12,12 +12,12 @@ Tools for mocking ethereum contracts. """ [dependencies] -ethcontract = { version = "0.16.0", path = "../ethcontract" } +ethcontract = { version = "0.16.0", path = "../ethcontract", default-features = false, features = ["derive"] } hex = "0.4" mockall = "0.11" rlp = "0.5" predicates = "2.0" [dev-dependencies] -tokio = { version = "1.6", features = ["macros"] } -ethcontract-derive = { version = "0.16.0", path = "../ethcontract-derive" } +tokio = { version = "1.6", features = ["macros", "rt"] } +ethcontract-derive = { version = "0.16.0", path = "../ethcontract-derive", default-featuers = false } diff --git a/ethcontract/Cargo.toml b/ethcontract/Cargo.toml index 97643f84..31c851af 100644 --- a/ethcontract/Cargo.toml +++ b/ethcontract/Cargo.toml @@ -17,8 +17,9 @@ to Ethereum smart contracts. name = "ethcontract" [features] -default = ["derive", "http-tls", "ws-tls-tokio"] +default = ["derive", "http-tls", "ws-tls-tokio", "derive-http"] derive = ["ethcontract-derive"] +derive-http = ["ethcontract-derive/http"] http = ["web3/http"] http-tls = ["http", "web3/http-tls"] http-native-tls = ["http", "web3/http-native-tls"] @@ -32,7 +33,7 @@ ipc-tokio = ["web3/ipc-tokio"] [dependencies] arrayvec = "0.7" ethcontract-common = { version = "0.16.0", path = "../ethcontract-common" } -ethcontract-derive = { version = "0.16.0", path = "../ethcontract-derive", optional = true} +ethcontract-derive = { version = "0.16.0", path = "../ethcontract-derive", optional = true, default-features = false } futures = "0.3" futures-timer = "3.0" hex = "0.4" diff --git a/examples/Cargo.toml b/examples/Cargo.toml index 3973f3e6..c177215e 100644 --- a/examples/Cargo.toml +++ b/examples/Cargo.toml @@ -7,6 +7,6 @@ license = "MIT OR Apache-2.0" autobins = false [dev-dependencies] -ethcontract = { path = "../ethcontract", features = ["derive"] } +ethcontract = { path = "../ethcontract" } futures = "0.3" tokio = { version = "1.6", features = ["macros"] } diff --git a/examples/generate/Cargo.toml b/examples/generate/Cargo.toml index cd957e24..af1952bd 100644 --- a/examples/generate/Cargo.toml +++ b/examples/generate/Cargo.toml @@ -12,4 +12,4 @@ futures = "0.3" tokio = { version = "1.6", features = ["macros"] } [build-dependencies] -ethcontract-generate = { path = "../../ethcontract-generate" } +ethcontract-generate = { path = "../../ethcontract-generate", default-features = false }