1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
pub mod web3_adapter;

use std::str::FromStr;
use std::string::ToString;
use super::error::ConnectionError;
use web3_adapter::Web3Adapter;
use web3::futures::Future;
use jsonrpc_core as rpc;


pub type CallFuture = web3::helpers::CallFuture<Vec<web3::types::Address>, Box<dyn Future<Item = rpc::Value, Error = web3::Error>>>;

#[derive(Serialize, Deserialize, Debug)]
pub struct BlockchainConnectorConfig {
  pub protocol: String,
  pub host: String,
  pub port: String,
}

impl Default for BlockchainConnectorConfig {
  fn default() -> Self {
    BlockchainConnectorConfig {
      protocol: SupportedProtocols::Rpc.to_string(),
      host: "localhost".to_string(),
      port: "8545".to_string(),
    }
  }
}

pub enum SupportedProtocols {
  Rpc,
  Ws,
}

impl FromStr for SupportedProtocols {
  type Err = ConnectionError;
  fn from_str(s: &str) -> Result<Self, Self::Err> {
    match s {
      "rpc" => Ok(SupportedProtocols::Rpc),
      "ws" => Ok(SupportedProtocols::Ws),
      _ => Err(ConnectionError::UnsupportedProtocol),
    }
  }
}

impl ToString for SupportedProtocols {
  fn to_string(&self) -> String {
    match self {
      SupportedProtocols::Rpc => "rpc".to_string(),
      SupportedProtocols::Ws => "ws".to_string(),
    }
  }
}

pub struct BlockchainConnector {
  adapter: Web3Adapter,
}

impl BlockchainConnector {
  pub fn new(adapter: Web3Adapter) -> BlockchainConnector {
    BlockchainConnector {
      adapter,
    }
  }

  pub fn accounts(&self) -> Result<Vec<web3::types::Address>, ConnectionError> {
    self.adapter.accounts().wait().map_err(ConnectionError::Transport)
  }

  pub fn balance(&self, address: web3::types::Address, block_number: Option<web3::types::BlockNumber>) -> Result<web3::types::U256, ConnectionError> {
    self.adapter.balance(address, block_number).wait().map_err(ConnectionError::Transport)
  }

  pub fn gas_price(&self) -> Result<web3::types::U256, ConnectionError> {
    self.adapter.gas_price().wait().map_err(ConnectionError::Transport)
  }

  pub fn deploy(&self, bytes: &[u8]) -> Result<web3::contract::deploy::Builder<web3_adapter::Transports>, ethabi::Error> {
    self.adapter.deploy(bytes)
  }
}