ethereum / web3.py

A python interface for interacting with the Ethereum blockchain and ecosystem.
http://web3py.readthedocs.io
MIT License
4.96k stars 1.69k forks source link

Raise custom exception instead of ValueError when a method is unavailable at the node #2448

Closed LefterisJP closed 1 year ago

LefterisJP commented 2 years ago
aiohttp==3.8.1
aiosignal==1.2.0
alabaster==0.7.12
altgraph==0.17.2
aniso8601==9.0.1
asn1crypto==1.5.1
astroid==2.11.3
astunparse==1.6.3
async-timeout==4.0.2
attrs==21.4.0
Babel==2.9.1
base58==2.1.1
base58check==1.0.2
beautifulsoup4==4.11.1
bech32==1.2.0
bitarray==1.2.2
bump2version==1.0.1
cachetools==5.0.0
certifi==2021.10.8
cffi==1.15.0
charset-normalizer==2.0.12
click==8.0.4
coincurve==17.0.0
colorama==0.4.4
coverage==6.3.2
cryptography==36.0.1
cytoolz==0.11.2
dill==0.3.4
docutils==0.17.1
ecdsa==0.17.0
elpy==1.999
eth-abi==2.1.1
eth-account==0.5.7
eth-hash==0.3.2
eth-keyfile==0.5.1
eth-keys==0.3.4
eth-rlp==0.2.1
eth-typing==2.3.0
eth-utils==1.10.0
fancycompleter==0.9.1
flake8==4.0.1
flake8-bugbear==22.3.23
flake8-commas==2.1.0
flake8-comprehensions==3.8.0
flake8-debugger==4.0.0
flake8-executable==2.1.1
flake8-mutable==1.2.0
flake8-polyfill==1.0.2
flake8-tuple==0.4.1
flaky==3.7.0
Flask==2.1.1
Flask-Cors==3.0.10
Flask-RESTful==0.3.9
freezegun==1.2.1
frozenlist==1.3.0
gevent==21.12.0
gevent-websocket==0.10.1
google-api-core==2.7.2
google-api-python-client==2.45.0
google-auth==2.6.5
google-auth-httplib2==0.1.0
googleapis-common-protos==1.56.0
gql==2.0.0
graphql-core==2.3.2
greenlet==1.1.2
hexbytes==0.2.2
httplib2==0.20.4
idna==3.3
imagesize==1.3.0
importlib-metadata==4.11.3
iniconfig==1.1.1
ipfshttpclient==0.8.0a2
isort==5.10.1
itsdangerous==2.1.1
jedi==0.17.2
Jinja2==3.0.3
jsonschema==3.2.0
lazy-object-proxy==1.7.1
livereload==2.6.3
lru-dict==1.1.7
MarkupSafe==2.1.1
marshmallow==3.15.0
maxminddb==2.2.0
mccabe==0.6.1
miniupnpc==2.0.2
more-itertools==8.12.0
multiaddr==0.0.9
multidict==6.0.2
mypy==0.942
mypy-extensions==0.4.3
netaddr==0.8.0
oauthlib==3.2.0
packaging==21.3
parsimonious==0.8.1
parso==0.7.1
pdbpp==0.10.3
pep8-naming==0.12.1
pipdeptree==2.2.1
platformdirs==2.5.1
pluggy==1.0.0
promise==2.3
protobuf==3.19.4
psutil==5.9.0
py==1.11.0
py-bip39-bindings==0.1.8
py-ed25519-bindings==1.0.1
py-sr25519-bindings==0.1.4
pyasn1==0.4.8
pyasn1-modules==0.2.8
pycodestyle==2.8.0
pycparser==2.21
pycryptodome==3.14.1
pyflakes==2.4.0
Pygments==2.11.2
pyinstaller==4.8
pyinstaller-hooks-contrib==2022.3
pylint==2.13.7
pyparsing==3.0.7
pyrepl==0.9.0
pyrsistent==0.18.1
pysqlcipher3==1.0.4
pytest==7.1.1
pytest-cov==3.0.0
pytest-freezegun==0.4.2
python-dateutil==2.8.2
pytz==2022.1
requests==2.27.1
requests-oauthlib==1.3.1
rlp==2.0.1
-e git+ssh://git@github.com/LefterisJP/rotkehlchen.git@033970e26f80fe51eab4b2fd9d9e3396ed33cb1c#egg=rotkehlchen
rotki-releases==2.0.1
rsa==4.8
Rx==1.6.1
scalecodec==1.0.34
semantic-version==2.6.0
six==1.16.0
snowballstemmer==2.2.0
soupsieve==2.3.1
Sphinx==4.4.0
sphinx-autobuild==2021.3.14
sphinx-rtd-theme==1.0.0
sphinxcontrib-applehelp==1.0.2
sphinxcontrib-devhelp==1.0.2
sphinxcontrib-htmlhelp==2.0.0
sphinxcontrib-httpdomain==1.8.0
sphinxcontrib-httpexample==1.1
sphinxcontrib-jsmath==1.0.1
sphinxcontrib-qthelp==1.0.3
sphinxcontrib-serializinghtml==1.1.5
substrate-interface==1.2.2
toml==0.10.2
tomli==2.0.1
toolz==0.11.2
tornado==6.1
types-chardet==4.0.3
types-cryptography==3.3.19
types-enum34==1.1.8
types-ipaddress==1.0.8
types-pkg-resources==0.1.3
types-requests==2.27.16
types-toml==0.10.4
types-urllib3==1.26.11
typing_extensions==4.1.1
uritemplate==4.1.1
urllib3==1.26.9
varint==1.0.2
vulture==2.3
web3==5.28.0
webargs==8.1.0
websocket-client==1.3.1
websockets==9.1
Werkzeug==2.0.3
wmctrl==0.4
wrapt==1.13.3
wsaccel==0.6.3
xxhash==2.0.2
yarl==1.7.2
zipp==3.8.0
zope.event==4.5.0
zope.interface==5.4.0

What was wrong?

Please include any of the following that are applicable:

Make this call via web3.py

curl -s --data '{"jsonrpc":"2.0","method":"eth_getTransactionByHash","params":["0xb2fea9c4b24775af6990237aa90228e5e092c56bdaee74496992a53c208da1ee"],"id":"1"}' -H "Content-Type: application/json" -X POST https://nodes.mewapi.io/rpc/eth
[28/04/2022 17:43:22 CEST] DEBUG web3.providers.HTTPProvider Getting response HTTP. URI: https://nodes.mewapi.io/rpc/eth, Method: eth_getTransactionByHash, Response: {'jsonrpc': '2.0', 'id': 42, 'error': {'code': -32601, 'message': 'the method eth_getTransactionByHash does not exist/is not available'}}
[28/04/2022 17:43:22 CEST] ERROR rotkehlchen.greenlets Greenlet with id 140152317009056: Query ethereum transactions for 0x9ba961989Dd6609Ed091f512bE947118c40F2291 died with exception: {'code': -32601, 'message': 'the method eth_getTransactionByHash does not exist/is not available'}.
Exception Name: <class 'ValueError'>
Exception Info: {'code': -32601, 'message': 'the method eth_getTransactionByHash does not exist/is not available'}
Traceback:
   File "src/gevent/greenlet.py", line 906, in gevent._gevent_cgreenlet.Greenlet.run
  File "/home/yabirgb/work/rotkib/rotkehlchen/chain/ethereum/transactions.py", line 87, in single_address_query_transactions
    self._get_erc20_transfers_for_ranges(address=address, ranges_to_query=ranges_to_query)
  File "/home/yabirgb/work/rotkib/rotkehlchen/chain/ethereum/transactions.py", line 223, in _get_erc20_transfers_for_ranges
    transaction = self.ethereum.get_transaction_by_hash(tx_hash_bytes)
  File "/home/yabirgb/work/rotkib/rotkehlchen/chain/ethereum/manager.py", line 933, in get_transaction_by_hash
    return self.query(
  File "/home/yabirgb/work/rotkib/rotkehlchen/chain/ethereum/manager.py", line 444, in query
    result = method(web3, **kwargs)
  File "/home/yabirgb/work/rotkib/rotkehlchen/chain/ethereum/manager.py", line 917, in _get_transaction_by_hash
    tx_data = web3.eth.get_transaction(tx_hash)  # type: ignore
  File "/home/yabirgb/work/rotkib/.venv/lib/python3.9/site-packages/web3/eth.py", line 724, in get_transaction
    return self._get_transaction(transaction_hash)
  File "/home/yabirgb/work/rotkib/.venv/lib/python3.9/site-packages/web3/module.py", line 57, in caller
    result = w3.manager.request_blocking(method_str,
  File "/home/yabirgb/work/rotkib/.venv/lib/python3.9/site-packages/web3/manager.py", line 198, in request_blocking
    return self.formatted_response(response,
  File "/home/yabirgb/work/rotkib/.venv/lib/python3.9/site-packages/web3/manager.py", line 171, in formatted_response
    raise ValueError(response["error"])

https://nodes.mewapi.io/rpc/eth

How can it be fixed?

I think it would be much better if we, the users of web3, have a different exception to catch when a method is not available in the node, rather than raising a generic ValueError.

How about MethodUnavailable ?

kclowes commented 2 years ago

I like this idea but we'll have to think about how to parse the error response to accommodate the most users. I can't remember if error code numbers are standardized across clients. I'll add this to our v6 breaking changes issue to discuss with the team. Eventually in v6 we're also planning on adding a Web3Exception class that all of our custom exceptions will inherit from which should make things nicer too.

LefterisJP commented 2 years ago

Eventually in v6 we're also planning on adding a Web3Exception class that all of our custom exceptions will inherit from which should make things nicer too.

Understood! That would be a really cool change.

Will be looking at the issue to see how it progresses :heart: