Skip to content

Commit

Permalink
Implements InfuraClient by adding an intermediate call to get the var…
Browse files Browse the repository at this point in the history
…iant of a web3 client.
  • Loading branch information
vepkenez authored and KPrasch committed Jul 6, 2019
1 parent 95543e0 commit 71cec9d
Show file tree
Hide file tree
Showing 3 changed files with 52 additions and 4 deletions.
25 changes: 23 additions & 2 deletions nucypher/blockchain/eth/clients.py
Expand Up @@ -83,6 +83,10 @@ def __init__(self,
self.backend = backend
self.log = Logger(self.__class__.__name__)

@classmethod
def _get_variant(cls, w3):
return cls

@classmethod
def from_w3(cls, w3: Web3) -> 'Web3Client':
"""
Expand Down Expand Up @@ -127,7 +131,7 @@ def from_w3(cls, w3: Web3) -> 'Web3Client':
'platform': client_data[2] if len(client_data) == 4 else None # Plaftorm is optional
}

instance = ClientSubclass(w3, **client_kwargs)
instance = ClientSubclass._get_variant(w3)(w3, **client_kwargs)
return instance

class ConnectionNotEstablished(RuntimeError):
Expand Down Expand Up @@ -253,6 +257,12 @@ def sign_message(self, account: str, message: bytes) -> str:

class GethClient(Web3Client):

@classmethod
def _get_variant(cls, w3):
if 'infura' in w3.provider.endpoint_uri:
return InfuraClient
return cls

@property
def is_local(self):
return int(self.w3.net.version) not in PUBLIC_CHAINS
Expand All @@ -262,7 +272,8 @@ def peers(self):
return self.w3.geth.admin.peers()

def unlock_account(self, address, password):
return self.w3.geth.personal.unlockAccount(address, password)
if not self.is_local:
return self.w3.geth.personal.unlockAccount(address, password)


class ParityClient(Web3Client):
Expand All @@ -289,6 +300,16 @@ def sync(self, *args, **kwargs):
return True


class InfuraClient(Web3Client):

is_local = False

def unlock_account(self, address, password):
return True

def sync(self, *args, **kwargs):
return True

class EthereumTesterClient(Web3Client):

is_local = True
Expand Down
3 changes: 1 addition & 2 deletions nucypher/blockchain/eth/interfaces.py
Expand Up @@ -256,8 +256,7 @@ def provider(self) -> Union[IPCProvider, WebsocketProvider, HTTPProvider]:

def _attach_provider(self,
provider: Web3Providers = None,
provider_uri: str = None,
remote: bool = False) -> None:
provider_uri: str = None) -> None:
"""
https://web3py.readthedocs.io/en/latest/providers.html#providers
"""
Expand Down
28 changes: 28 additions & 0 deletions tests/blockchain/eth/clients/test_mocked_clients.py
Expand Up @@ -2,6 +2,7 @@
GethClient,
ParityClient,
GanacheClient,
InfuraClient,
PUBLIC_CHAINS
)
from nucypher.blockchain.eth.interfaces import BlockchainInterface
Expand All @@ -12,17 +13,25 @@
#

class MockGethProvider:
endpoint_uri = 'file:///ipc.geth'
clientVersion = 'Geth/v1.4.11-stable-fed692f6/darwin/go1.7'


class MockParityProvider:
endpoint_uri = 'file:///ipc.parity'
clientVersion = 'Parity-Ethereum/v2.5.1-beta-e0141f8-20190510/x86_64-linux-gnu/rustc1.34.1'


class MockGanacheProvider:
endpoint_uri = 'http://ganache:8445'
clientVersion = 'EthereumJS TestRPC/v2.1.5/ethereum-js'


class MockInfuraProvider:
endpoint_uri = 'wss://:@goerli.infura.io/ws/v3/1234567890987654321abcdef'
clientVersion = 'Geth/v1.8.23-omnibus-2ad89aaa/linux-amd64/go1.11.1'


class ChainIdReporter:
# Support older and newer versions of web3 py in-test
version = 5
Expand Down Expand Up @@ -68,6 +77,9 @@ class GethClientTestBlockchain(BlockchainInterfaceTestBase):
def _attach_provider(self, *args, **kwargs) -> None:
super()._attach_provider(provider=MockGethProvider())

def _get_infura_provider(self):
return MockInfuraProvider()

@property
def is_local(self):
return int(self.w3.net.version) not in PUBLIC_CHAINS
Expand Down Expand Up @@ -97,6 +109,22 @@ def test_geth_web3_client():
assert interface.client.chain_id == 5


def test_infura_web3_client():
interface = GethClientTestBlockchain(
provider_uri='infura://1234567890987654321abcdef'
)
assert isinstance(interface.client, InfuraClient)
assert interface.node_technology == 'Geth'
assert interface.node_version == 'v1.8.23-omnibus-2ad89aaa'
assert interface.platform == 'linux-amd64'
assert interface.backend == 'go1.11.1'

assert interface.is_local is False
assert interface.chain_id == 5

assert interface.unlock_account('address', 'password') # should return True


def test_parity_web3_client():
interface = ParityClientTestInterface(provider_uri='file:///ipc.parity', sync_now=False)
assert isinstance(interface.client, ParityClient)
Expand Down

0 comments on commit 71cec9d

Please sign in to comment.