web3 7.0.0b1__py3-none-any.whl → 7.7.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (261) hide show
  1. ens/__init__.py +13 -2
  2. ens/_normalization.py +4 -4
  3. ens/async_ens.py +31 -21
  4. ens/base_ens.py +3 -1
  5. ens/contract_data.py +2 -2
  6. ens/ens.py +14 -11
  7. ens/exceptions.py +16 -29
  8. ens/specs/nf.json +1 -1
  9. ens/specs/normalization_spec.json +1 -1
  10. ens/utils.py +33 -41
  11. web3/__init__.py +23 -12
  12. web3/_utils/abi.py +162 -274
  13. web3/_utils/async_transactions.py +34 -20
  14. web3/_utils/batching.py +217 -0
  15. web3/_utils/blocks.py +6 -2
  16. web3/_utils/caching/__init__.py +12 -0
  17. web3/_utils/caching/caching_utils.py +433 -0
  18. web3/_utils/caching/request_caching_validation.py +287 -0
  19. web3/_utils/compat/__init__.py +2 -3
  20. web3/_utils/contract_sources/compile_contracts.py +1 -1
  21. web3/_utils/contract_sources/contract_data/ambiguous_function_contract.py +42 -0
  22. web3/_utils/contract_sources/contract_data/arrays_contract.py +3 -3
  23. web3/_utils/contract_sources/contract_data/bytes_contracts.py +5 -5
  24. web3/_utils/contract_sources/contract_data/constructor_contracts.py +7 -7
  25. web3/_utils/contract_sources/contract_data/contract_caller_tester.py +3 -3
  26. web3/_utils/contract_sources/contract_data/emitter_contract.py +3 -3
  27. web3/_utils/contract_sources/contract_data/event_contracts.py +50 -5
  28. web3/_utils/contract_sources/contract_data/extended_resolver.py +3 -3
  29. web3/_utils/contract_sources/contract_data/fallback_function_contract.py +3 -3
  30. web3/_utils/contract_sources/contract_data/function_name_tester_contract.py +3 -3
  31. web3/_utils/contract_sources/contract_data/math_contract.py +3 -3
  32. web3/_utils/contract_sources/contract_data/offchain_lookup.py +3 -3
  33. web3/_utils/contract_sources/contract_data/offchain_resolver.py +3 -3
  34. web3/_utils/contract_sources/contract_data/panic_errors_contract.py +3 -3
  35. web3/_utils/contract_sources/contract_data/payable_tester.py +3 -3
  36. web3/_utils/contract_sources/contract_data/receive_function_contracts.py +5 -5
  37. web3/_utils/contract_sources/contract_data/reflector_contracts.py +3 -3
  38. web3/_utils/contract_sources/contract_data/revert_contract.py +3 -3
  39. web3/_utils/contract_sources/contract_data/simple_resolver.py +3 -3
  40. web3/_utils/contract_sources/contract_data/storage_contract.py +3 -3
  41. web3/_utils/contract_sources/contract_data/string_contract.py +3 -3
  42. web3/_utils/contract_sources/contract_data/tuple_contracts.py +5 -5
  43. web3/_utils/contracts.py +172 -220
  44. web3/_utils/datatypes.py +5 -1
  45. web3/_utils/decorators.py +6 -1
  46. web3/_utils/empty.py +1 -1
  47. web3/_utils/encoding.py +16 -12
  48. web3/_utils/error_formatters_utils.py +5 -3
  49. web3/_utils/events.py +78 -72
  50. web3/_utils/fee_utils.py +1 -3
  51. web3/_utils/filters.py +24 -22
  52. web3/_utils/formatters.py +2 -2
  53. web3/_utils/http.py +8 -2
  54. web3/_utils/http_session_manager.py +314 -0
  55. web3/_utils/math.py +14 -15
  56. web3/_utils/method_formatters.py +161 -34
  57. web3/_utils/module.py +2 -1
  58. web3/_utils/module_testing/__init__.py +3 -2
  59. web3/_utils/module_testing/eth_module.py +736 -583
  60. web3/_utils/module_testing/go_ethereum_debug_module.py +128 -0
  61. web3/_utils/module_testing/module_testing_utils.py +81 -24
  62. web3/_utils/module_testing/persistent_connection_provider.py +702 -220
  63. web3/_utils/module_testing/utils.py +114 -33
  64. web3/_utils/module_testing/web3_module.py +438 -17
  65. web3/_utils/normalizers.py +13 -11
  66. web3/_utils/rpc_abi.py +10 -22
  67. web3/_utils/threads.py +8 -7
  68. web3/_utils/transactions.py +32 -25
  69. web3/_utils/type_conversion.py +5 -1
  70. web3/_utils/validation.py +20 -17
  71. web3/beacon/__init__.py +5 -0
  72. web3/beacon/api_endpoints.py +3 -0
  73. web3/beacon/async_beacon.py +29 -6
  74. web3/beacon/beacon.py +24 -6
  75. web3/contract/__init__.py +7 -0
  76. web3/contract/async_contract.py +285 -82
  77. web3/contract/base_contract.py +556 -258
  78. web3/contract/contract.py +295 -84
  79. web3/contract/utils.py +251 -55
  80. web3/datastructures.py +56 -41
  81. web3/eth/__init__.py +7 -0
  82. web3/eth/async_eth.py +89 -69
  83. web3/eth/base_eth.py +7 -3
  84. web3/eth/eth.py +43 -66
  85. web3/exceptions.py +158 -83
  86. web3/gas_strategies/time_based.py +8 -6
  87. web3/geth.py +53 -184
  88. web3/main.py +77 -43
  89. web3/manager.py +368 -101
  90. web3/method.py +43 -15
  91. web3/middleware/__init__.py +26 -8
  92. web3/middleware/attrdict.py +12 -22
  93. web3/middleware/base.py +55 -2
  94. web3/middleware/filter.py +45 -23
  95. web3/middleware/formatting.py +6 -3
  96. web3/middleware/names.py +4 -1
  97. web3/middleware/signing.py +15 -6
  98. web3/middleware/stalecheck.py +2 -1
  99. web3/module.py +62 -26
  100. web3/providers/__init__.py +21 -0
  101. web3/providers/async_base.py +93 -38
  102. web3/providers/base.py +85 -40
  103. web3/providers/eth_tester/__init__.py +5 -0
  104. web3/providers/eth_tester/defaults.py +2 -55
  105. web3/providers/eth_tester/main.py +57 -35
  106. web3/providers/eth_tester/middleware.py +16 -17
  107. web3/providers/ipc.py +42 -18
  108. web3/providers/legacy_websocket.py +27 -2
  109. web3/providers/persistent/__init__.py +7 -0
  110. web3/providers/persistent/async_ipc.py +61 -121
  111. web3/providers/persistent/persistent.py +324 -17
  112. web3/providers/persistent/persistent_connection.py +54 -5
  113. web3/providers/persistent/request_processor.py +136 -56
  114. web3/providers/persistent/subscription_container.py +56 -0
  115. web3/providers/persistent/subscription_manager.py +233 -0
  116. web3/providers/persistent/websocket.py +29 -92
  117. web3/providers/rpc/__init__.py +5 -0
  118. web3/providers/rpc/async_rpc.py +73 -18
  119. web3/providers/rpc/rpc.py +73 -30
  120. web3/providers/rpc/utils.py +1 -13
  121. web3/scripts/install_pre_releases.py +33 -0
  122. web3/scripts/parse_pygeth_version.py +16 -0
  123. web3/testing.py +4 -4
  124. web3/tracing.py +9 -5
  125. web3/types.py +141 -74
  126. web3/utils/__init__.py +64 -5
  127. web3/utils/abi.py +790 -10
  128. web3/utils/address.py +8 -0
  129. web3/utils/async_exception_handling.py +20 -11
  130. web3/utils/caching.py +34 -4
  131. web3/utils/exception_handling.py +9 -12
  132. web3/utils/subscriptions.py +285 -0
  133. {web3-7.0.0b1.dist-info → web3-7.7.0.dist-info}/LICENSE +1 -1
  134. web3-7.7.0.dist-info/METADATA +130 -0
  135. web3-7.7.0.dist-info/RECORD +171 -0
  136. {web3-7.0.0b1.dist-info → web3-7.7.0.dist-info}/WHEEL +1 -1
  137. {web3-7.0.0b1.dist-info → web3-7.7.0.dist-info}/top_level.txt +0 -1
  138. ethpm/__init__.py +0 -20
  139. ethpm/_utils/__init__.py +0 -0
  140. ethpm/_utils/backend.py +0 -93
  141. ethpm/_utils/cache.py +0 -44
  142. ethpm/_utils/chains.py +0 -119
  143. ethpm/_utils/contract.py +0 -35
  144. ethpm/_utils/deployments.py +0 -145
  145. ethpm/_utils/ipfs.py +0 -116
  146. ethpm/_utils/protobuf/__init__.py +0 -0
  147. ethpm/_utils/protobuf/ipfs_file_pb2.py +0 -33
  148. ethpm/_utils/registry.py +0 -29
  149. ethpm/assets/__init__.py +0 -0
  150. ethpm/assets/ens/v3.json +0 -1
  151. ethpm/assets/escrow/with_bytecode_v3.json +0 -1
  152. ethpm/assets/ipfs_file.proto +0 -32
  153. ethpm/assets/owned/output_v3.json +0 -1
  154. ethpm/assets/owned/with_contract_type_v3.json +0 -1
  155. ethpm/assets/registry/contracts/Authority.sol +0 -156
  156. ethpm/assets/registry/contracts/IndexedOrderedSetLib.sol +0 -106
  157. ethpm/assets/registry/contracts/PackageDB.sol +0 -225
  158. ethpm/assets/registry/contracts/PackageRegistry.sol +0 -361
  159. ethpm/assets/registry/contracts/PackageRegistryInterface.sol +0 -97
  160. ethpm/assets/registry/contracts/ReleaseDB.sol +0 -309
  161. ethpm/assets/registry/contracts/ReleaseValidator.sol +0 -152
  162. ethpm/assets/registry/solc_input.json +0 -1
  163. ethpm/assets/registry/solc_output.json +0 -1
  164. ethpm/assets/registry/v3.json +0 -1
  165. ethpm/assets/safe-math-lib/v3-strict-no-deployments.json +0 -1
  166. ethpm/assets/simple-registry/contracts/Ownable.sol +0 -63
  167. ethpm/assets/simple-registry/contracts/PackageRegistry.sol +0 -373
  168. ethpm/assets/simple-registry/contracts/PackageRegistryInterface.sol +0 -96
  169. ethpm/assets/simple-registry/solc_input.json +0 -33
  170. ethpm/assets/simple-registry/solc_output.json +0 -1
  171. ethpm/assets/simple-registry/v3.json +0 -1
  172. ethpm/assets/standard-token/output_v3.json +0 -1
  173. ethpm/assets/standard-token/with_bytecode_v3.json +0 -1
  174. ethpm/assets/vyper_registry/0.1.0.json +0 -1
  175. ethpm/assets/vyper_registry/registry.vy +0 -216
  176. ethpm/assets/vyper_registry/registry_with_delete.vy +0 -244
  177. ethpm/backends/__init__.py +0 -0
  178. ethpm/backends/base.py +0 -43
  179. ethpm/backends/http.py +0 -108
  180. ethpm/backends/ipfs.py +0 -219
  181. ethpm/backends/registry.py +0 -154
  182. ethpm/constants.py +0 -17
  183. ethpm/contract.py +0 -187
  184. ethpm/dependencies.py +0 -58
  185. ethpm/deployments.py +0 -80
  186. ethpm/ethpm-spec/examples/escrow/1.0.0-pretty.json +0 -146
  187. ethpm/ethpm-spec/examples/escrow/1.0.0.json +0 -1
  188. ethpm/ethpm-spec/examples/escrow/contracts/Escrow.sol +0 -32
  189. ethpm/ethpm-spec/examples/escrow/contracts/SafeSendLib.sol +0 -20
  190. ethpm/ethpm-spec/examples/escrow/v3-pretty.json +0 -171
  191. ethpm/ethpm-spec/examples/escrow/v3.json +0 -1
  192. ethpm/ethpm-spec/examples/owned/1.0.0-pretty.json +0 -21
  193. ethpm/ethpm-spec/examples/owned/1.0.0.json +0 -1
  194. ethpm/ethpm-spec/examples/owned/contracts/Owned.sol +0 -12
  195. ethpm/ethpm-spec/examples/owned/v3-pretty.json +0 -27
  196. ethpm/ethpm-spec/examples/owned/v3.json +0 -1
  197. ethpm/ethpm-spec/examples/piper-coin/1.0.0-pretty.json +0 -31
  198. ethpm/ethpm-spec/examples/piper-coin/1.0.0.json +0 -1
  199. ethpm/ethpm-spec/examples/piper-coin/v3-pretty.json +0 -21
  200. ethpm/ethpm-spec/examples/piper-coin/v3.json +0 -1
  201. ethpm/ethpm-spec/examples/safe-math-lib/1.0.0-pretty.json +0 -85
  202. ethpm/ethpm-spec/examples/safe-math-lib/1.0.0.json +0 -1
  203. ethpm/ethpm-spec/examples/safe-math-lib/contracts/SafeMathLib.sol +0 -24
  204. ethpm/ethpm-spec/examples/safe-math-lib/v3-pretty.json +0 -117
  205. ethpm/ethpm-spec/examples/safe-math-lib/v3.json +0 -1
  206. ethpm/ethpm-spec/examples/standard-token/1.0.0-pretty.json +0 -55
  207. ethpm/ethpm-spec/examples/standard-token/1.0.0.json +0 -1
  208. ethpm/ethpm-spec/examples/standard-token/contracts/AbstractToken.sol +0 -20
  209. ethpm/ethpm-spec/examples/standard-token/contracts/StandardToken.sol +0 -84
  210. ethpm/ethpm-spec/examples/standard-token/v3-pretty.json +0 -460
  211. ethpm/ethpm-spec/examples/standard-token/v3.json +0 -1
  212. ethpm/ethpm-spec/examples/transferable/1.0.0-pretty.json +0 -21
  213. ethpm/ethpm-spec/examples/transferable/1.0.0.json +0 -1
  214. ethpm/ethpm-spec/examples/transferable/contracts/Transferable.sol +0 -14
  215. ethpm/ethpm-spec/examples/transferable/v3-pretty.json +0 -27
  216. ethpm/ethpm-spec/examples/transferable/v3.json +0 -1
  217. ethpm/ethpm-spec/examples/wallet/1.0.0-pretty.json +0 -120
  218. ethpm/ethpm-spec/examples/wallet/1.0.0.json +0 -1
  219. ethpm/ethpm-spec/examples/wallet/contracts/Wallet.sol +0 -41
  220. ethpm/ethpm-spec/examples/wallet/v3-pretty.json +0 -181
  221. ethpm/ethpm-spec/examples/wallet/v3.json +0 -1
  222. ethpm/ethpm-spec/examples/wallet-with-send/1.0.0-pretty.json +0 -135
  223. ethpm/ethpm-spec/examples/wallet-with-send/1.0.0.json +0 -1
  224. ethpm/ethpm-spec/examples/wallet-with-send/contracts/WalletWithSend.sol +0 -18
  225. ethpm/ethpm-spec/examples/wallet-with-send/v3-pretty.json +0 -207
  226. ethpm/ethpm-spec/examples/wallet-with-send/v3.json +0 -1
  227. ethpm/ethpm-spec/spec/package.spec.json +0 -379
  228. ethpm/ethpm-spec/spec/v3.spec.json +0 -483
  229. ethpm/exceptions.py +0 -68
  230. ethpm/package.py +0 -438
  231. ethpm/tools/__init__.py +0 -4
  232. ethpm/tools/builder.py +0 -930
  233. ethpm/tools/checker.py +0 -312
  234. ethpm/tools/get_manifest.py +0 -19
  235. ethpm/uri.py +0 -141
  236. ethpm/validation/__init__.py +0 -0
  237. ethpm/validation/manifest.py +0 -146
  238. ethpm/validation/misc.py +0 -39
  239. ethpm/validation/package.py +0 -80
  240. ethpm/validation/uri.py +0 -163
  241. web3/_utils/caching.py +0 -155
  242. web3/_utils/contract_sources/contract_data/address_reflector.py +0 -29
  243. web3/_utils/module_testing/go_ethereum_personal_module.py +0 -300
  244. web3/_utils/request.py +0 -265
  245. web3/pm.py +0 -602
  246. web3/tools/__init__.py +0 -4
  247. web3/tools/benchmark/__init__.py +0 -0
  248. web3/tools/benchmark/main.py +0 -185
  249. web3/tools/benchmark/node.py +0 -126
  250. web3/tools/benchmark/reporting.py +0 -39
  251. web3/tools/benchmark/utils.py +0 -69
  252. web3/tools/pytest_ethereum/__init__.py +0 -0
  253. web3/tools/pytest_ethereum/_utils.py +0 -145
  254. web3/tools/pytest_ethereum/deployer.py +0 -48
  255. web3/tools/pytest_ethereum/exceptions.py +0 -22
  256. web3/tools/pytest_ethereum/linker.py +0 -128
  257. web3/tools/pytest_ethereum/plugins.py +0 -33
  258. web3-7.0.0b1.dist-info/METADATA +0 -114
  259. web3-7.0.0b1.dist-info/RECORD +0 -280
  260. web3-7.0.0b1.dist-info/entry_points.txt +0 -2
  261. /web3/_utils/{function_identifiers.py → abi_element_identifiers.py} +0 -0
ethpm/backends/ipfs.py DELETED
@@ -1,219 +0,0 @@
1
- from abc import (
2
- abstractmethod,
3
- )
4
- import os
5
- from pathlib import (
6
- Path,
7
- )
8
- from typing import (
9
- Dict,
10
- List,
11
- Type,
12
- )
13
-
14
- from eth_utils import (
15
- import_string,
16
- to_bytes,
17
- )
18
-
19
- from ethpm import (
20
- get_ethpm_spec_dir,
21
- )
22
- from ethpm._utils.ipfs import (
23
- dummy_ipfs_pin,
24
- extract_ipfs_path_from_uri,
25
- generate_file_hash,
26
- is_ipfs_uri,
27
- )
28
- from ethpm.backends.base import (
29
- BaseURIBackend,
30
- )
31
- from ethpm.constants import (
32
- DEFAULT_IPFS_BACKEND,
33
- INFURA_GATEWAY_MULTIADDR,
34
- IPFS_GATEWAY_PREFIX,
35
- )
36
- from ethpm.exceptions import (
37
- CannotHandleURI,
38
- EthPMValidationError,
39
- )
40
-
41
- try:
42
- # `ipfshttpclient` backend is optional. This is only imported if the "web3[ipfs]"
43
- # install extra is installed
44
- import ipfshttpclient
45
- except ImportError:
46
- pass
47
-
48
-
49
- class BaseIPFSBackend(BaseURIBackend):
50
- """
51
- Base class for all URIs with an IPFS scheme.
52
- """
53
-
54
- def can_resolve_uri(self, uri: str) -> bool:
55
- """
56
- Return a bool indicating whether or not this backend
57
- is capable of serving the content located at the URI.
58
- """
59
- return is_ipfs_uri(uri)
60
-
61
- def can_translate_uri(self, uri: str) -> bool:
62
- """
63
- Return False. IPFS URIs cannot be used to point
64
- to another content-addressed URI.
65
- """
66
- return False
67
-
68
- @abstractmethod
69
- def pin_assets(self, file_or_dir_path: Path) -> List[Dict[str, str]]:
70
- """
71
- Pin assets found at `file_or_dir_path` and return a
72
- list containing pinned asset data.
73
- """
74
- pass
75
-
76
-
77
- class IPFSOverHTTPBackend(BaseIPFSBackend):
78
- """
79
- Base class for all IPFS URIs served over an http connection.
80
- All subclasses must implement: base_uri
81
- """
82
-
83
- def __init__(self) -> None:
84
- self.client = ipfshttpclient.connect(self.base_uri)
85
-
86
- def fetch_uri_contents(self, uri: str) -> bytes:
87
- ipfs_hash = extract_ipfs_path_from_uri(uri)
88
- contents = self.client.cat(ipfs_hash)
89
- # Local validation of hashed contents only works for non-chunked files ~< 256kb
90
- # Improved validation WIP @ https://github.com/ethpm/py-ethpm/pull/165
91
- if len(contents) <= 262144:
92
- validation_hash = generate_file_hash(contents)
93
- if validation_hash != ipfs_hash:
94
- raise EthPMValidationError(
95
- f"Hashed IPFS contents retrieved from uri: {uri} "
96
- "do not match its content hash."
97
- )
98
- return contents
99
-
100
- @property
101
- @abstractmethod
102
- def base_uri(self) -> str:
103
- pass
104
-
105
- def pin_assets(self, file_or_dir_path: Path) -> List[Dict[str, str]]:
106
- if file_or_dir_path.is_dir():
107
- dir_data = self.client.add(str(file_or_dir_path), recursive=True)
108
- return dir_data
109
- elif file_or_dir_path.is_file():
110
- file_data = self.client.add(str(file_or_dir_path), recursive=False)
111
- return [file_data]
112
- else:
113
- raise TypeError(
114
- f"{file_or_dir_path} is not a valid file or directory path."
115
- )
116
-
117
-
118
- class IPFSGatewayBackend(IPFSOverHTTPBackend):
119
- """
120
- Backend class for all IPFS URIs served over the IPFS gateway.
121
- """
122
-
123
- # todo update this gateway to work r&w
124
- # https://discuss.ipfs.io/t/writeable-http-gateways/210
125
- @property
126
- def base_uri(self) -> str:
127
- return IPFS_GATEWAY_PREFIX
128
-
129
- def pin_assets(self, file_or_dir_path: Path) -> List[Dict[str, str]]:
130
- raise CannotHandleURI(
131
- "IPFS gateway is currently disabled, please use a different IPFS backend."
132
- )
133
-
134
- def fetch_uri_contents(self, uri: str) -> bytes:
135
- raise CannotHandleURI(
136
- "IPFS gateway is currently disabled, please use a different IPFS backend."
137
- )
138
-
139
-
140
- class InfuraIPFSBackend(IPFSOverHTTPBackend):
141
- """
142
- Backend class for all IPFS URIs served over the Infura IFPS gateway.
143
- """
144
-
145
- @property
146
- def base_uri(self) -> str:
147
- return INFURA_GATEWAY_MULTIADDR
148
-
149
-
150
- class LocalIPFSBackend(IPFSOverHTTPBackend):
151
- """
152
- Backend class for all IPFS URIs served through a direct connection to an IPFS node.
153
- Default IPFS port = 5001
154
- """
155
-
156
- @property
157
- def base_uri(self) -> str:
158
- return "/ip4/127.0.0.1/tcp/5001"
159
-
160
-
161
- MANIFEST_URIS = {
162
- "ipfs://QmQNffBrmbB3TuBCtYfYsJWJVLssatWXa3H6CkGeyNUySA": "standard-token",
163
- "ipfs://QmWnPsiS3Xb8GvCDEBFnnKs8Yk4HaAX6rCqJAaQXGbCoPk": "safe-math-lib",
164
- "ipfs://QmcxvhkJJVpbxEAa6cgW3B6XwPJb79w9GpNUv2P2THUzZR": "owned",
165
- }
166
-
167
-
168
- class DummyIPFSBackend(BaseIPFSBackend):
169
- """
170
- Backend class to serve IPFS URIs without having to make an HTTP request.
171
- Used primarily for testing purposes, returns a locally stored manifest or contract.
172
- ---
173
- `ipfs_uri` can either be:
174
- - Valid IPFS URI -> safe-math-lib manifest (ALWAYS)
175
- - Path to manifest/contract in ethpm_spec_dir -> defined manifest/contract
176
- """
177
-
178
- def fetch_uri_contents(self, ipfs_uri: str) -> bytes:
179
- pkg_name = MANIFEST_URIS[ipfs_uri]
180
- ethpm_spec_dir = get_ethpm_spec_dir()
181
- pkg_contents = (ethpm_spec_dir / "examples" / pkg_name / "v3.json").read_text()
182
- return to_bytes(text=pkg_contents)
183
-
184
- def can_resolve_uri(self, uri: str) -> bool:
185
- return uri in MANIFEST_URIS
186
-
187
- def pin_assets(self, file_or_dir_path: Path) -> List[Dict[str, str]]:
188
- """
189
- Return a dict containing the IPFS hash, file name, and size of a file.
190
- """
191
- if file_or_dir_path.is_dir():
192
- asset_data = [dummy_ipfs_pin(path) for path in file_or_dir_path.glob("*")]
193
- elif file_or_dir_path.is_file():
194
- asset_data = [dummy_ipfs_pin(file_or_dir_path)]
195
- else:
196
- raise FileNotFoundError(
197
- f"{file_or_dir_path} is not a valid file or directory path."
198
- )
199
- return asset_data
200
-
201
-
202
- def get_ipfs_backend(import_path: str = None) -> BaseIPFSBackend:
203
- """
204
- Return the `BaseIPFSBackend` class specified by import_path,
205
- default, or env variable.
206
- """
207
- backend_class = get_ipfs_backend_class(import_path)
208
- return backend_class()
209
-
210
-
211
- def get_ipfs_backend_class(import_path: str = None) -> Type[BaseIPFSBackend]:
212
- if import_path is None:
213
- import_path = os.environ.get("ETHPM_IPFS_BACKEND_CLASS", DEFAULT_IPFS_BACKEND)
214
- if not import_path:
215
- raise CannotHandleURI(
216
- "Please provide an import class or set "
217
- "`ETHPM_IPFS_BACKEND_CLASS` environment variable."
218
- )
219
- return import_string(import_path)
@@ -1,154 +0,0 @@
1
- from collections import (
2
- namedtuple,
3
- )
4
- from typing import (
5
- Optional,
6
- Tuple,
7
- )
8
- from urllib import (
9
- parse,
10
- )
11
-
12
- from eth_typing import (
13
- URI,
14
- )
15
- from eth_utils import (
16
- is_address,
17
- )
18
-
19
- from ens import (
20
- ENS,
21
- )
22
- from ethpm._utils.registry import (
23
- fetch_standard_registry_abi,
24
- )
25
- from ethpm.backends.base import (
26
- BaseURIBackend,
27
- )
28
- from ethpm.exceptions import (
29
- CannotHandleURI,
30
- EthPMValidationError,
31
- )
32
- from ethpm.validation.uri import (
33
- validate_registry_uri,
34
- )
35
-
36
- # TODO: Update registry ABI once ERC is finalized.
37
- REGISTRY_ABI = fetch_standard_registry_abi()
38
- RegistryURI = namedtuple(
39
- "RegistryURI", ["address", "chain_id", "name", "version", "namespaced_asset", "ens"]
40
- )
41
-
42
-
43
- class RegistryURIBackend(BaseURIBackend):
44
- """
45
- Backend class to handle Registry URIs.
46
-
47
- A Registry URI must resolve to a resolvable content-addressed URI.
48
- """
49
-
50
- def __init__(self) -> None:
51
- from web3 import (
52
- LegacyWebSocketProvider,
53
- Web3,
54
- )
55
-
56
- w3 = Web3(LegacyWebSocketProvider())
57
-
58
- self.w3 = w3
59
-
60
- def can_translate_uri(self, uri: str) -> bool:
61
- return is_valid_registry_uri(uri)
62
-
63
- def can_resolve_uri(self, uri: str) -> bool:
64
- return False
65
-
66
- def fetch_uri_contents(self, uri: str) -> URI:
67
- """
68
- Return content-addressed URI stored at registry URI.
69
- """
70
- address, chain_id, pkg_name, pkg_version, _, _ = parse_registry_uri(uri)
71
- if chain_id != "1":
72
- # todo: support all testnets
73
- raise CannotHandleURI("Currently only mainnet registry uris are supported.")
74
- self.w3.enable_unstable_package_management_api()
75
- self.w3.pm.set_registry(address)
76
- _, _, manifest_uri = self.w3.pm.get_release_data(pkg_name, pkg_version)
77
- return URI(manifest_uri)
78
-
79
-
80
- def is_valid_registry_uri(uri: str) -> bool:
81
- """
82
- Return a boolean indicating whether `uri` argument
83
- conforms to the Registry URI scheme.
84
- """
85
- try:
86
- validate_registry_uri(uri)
87
- except EthPMValidationError:
88
- return False
89
- else:
90
- return True
91
-
92
-
93
- def parse_registry_uri(uri: str) -> RegistryURI:
94
- """
95
- Validate and return (authority, chain_id, pkg_name, version)
96
- from a valid registry URI.
97
- """
98
- from web3 import (
99
- LegacyWebSocketProvider,
100
- Web3,
101
- )
102
-
103
- w3 = Web3(LegacyWebSocketProvider())
104
-
105
- validate_registry_uri(uri)
106
- parsed_uri = parse.urlparse(uri)
107
- if ":" in parsed_uri.netloc:
108
- address_or_ens, chain_id = parsed_uri.netloc.split(":")
109
- else:
110
- address_or_ens, chain_id = parsed_uri.netloc, "1"
111
- ns = ENS.from_web3(w3)
112
- if is_address(address_or_ens):
113
- address = address_or_ens
114
- ens = None
115
- elif ns.address(address_or_ens):
116
- address = ns.address(address_or_ens)
117
- ens = address_or_ens
118
- else:
119
- raise CannotHandleURI(f"Invalid address or ENS domain found in uri: {uri}.")
120
- pkg_name, pkg_version, namespaced_asset = _process_pkg_path(parsed_uri.path)
121
- return RegistryURI(address, chain_id, pkg_name, pkg_version, namespaced_asset, ens)
122
-
123
-
124
- def _process_pkg_path(
125
- raw_pkg_path: str,
126
- ) -> Tuple[Optional[str], Optional[str], Optional[str]]:
127
- pkg_path = raw_pkg_path.strip("/")
128
- if not pkg_path:
129
- return None, None, None
130
-
131
- pkg_id, namespaced_asset = _parse_pkg_path(pkg_path)
132
- pkg_name, pkg_version = _parse_pkg_id(pkg_id)
133
- if not pkg_version and namespaced_asset:
134
- raise EthPMValidationError(
135
- "Invalid registry URI, missing package version."
136
- "Version is required if namespaced assets are defined."
137
- )
138
- return pkg_name, pkg_version, namespaced_asset
139
-
140
-
141
- def _parse_pkg_path(pkg_path: str) -> Tuple[str, Optional[str]]:
142
- if "/" in pkg_path:
143
- pkg_id, _, namespaced_asset = pkg_path.partition("/")
144
- return pkg_id, namespaced_asset
145
- else:
146
- return pkg_path, None
147
-
148
-
149
- def _parse_pkg_id(pkg_id: str) -> Tuple[str, Optional[str]]:
150
- if "@" not in pkg_id:
151
- return pkg_id, None
152
- pkg_name, _, safe_pkg_version = pkg_id.partition("@")
153
- pkg_version = parse.unquote(safe_pkg_version)
154
- return pkg_name, pkg_version
ethpm/constants.py DELETED
@@ -1,17 +0,0 @@
1
- REGISTRY_URI_SCHEMES = ("erc1319", "ethpm")
2
-
3
- PACKAGE_NAME_REGEX = "^[a-zA-Z][-_a-zA-Z0-9]{0,255}$"
4
-
5
- DEFAULT_IPFS_BACKEND = "ethpm.backends.ipfs.InfuraIPFSBackend"
6
-
7
- IPFS_GATEWAY_PREFIX = "https://ipfs.io/ipfs/"
8
-
9
- INFURA_GATEWAY_MULTIADDR = "/dns4/ipfs.infura.io/tcp/5001/https/"
10
-
11
- GITHUB_API_AUTHORITY = "api.github.com"
12
-
13
- SUPPORTED_CHAIN_IDS = {
14
- 1: "mainnet",
15
- 5: "goerli",
16
- 11155111: "sepolia",
17
- }
ethpm/contract.py DELETED
@@ -1,187 +0,0 @@
1
- from typing import (
2
- TYPE_CHECKING,
3
- Any,
4
- Dict,
5
- List,
6
- Optional,
7
- Tuple,
8
- Type,
9
- )
10
-
11
- from eth_utils import (
12
- combomethod,
13
- is_canonical_address,
14
- to_bytes,
15
- to_canonical_address,
16
- )
17
- from eth_utils.toolz import (
18
- assoc,
19
- curry,
20
- pipe,
21
- )
22
-
23
- from ethpm.exceptions import (
24
- BytecodeLinkingError,
25
- EthPMValidationError,
26
- )
27
- from ethpm.validation.misc import (
28
- validate_empty_bytes,
29
- )
30
- from web3._utils.compat import (
31
- Self,
32
- )
33
- from web3._utils.validation import (
34
- validate_address,
35
- )
36
- from web3.contract import (
37
- Contract,
38
- ContractConstructor,
39
- )
40
-
41
- if TYPE_CHECKING:
42
- from web3 import Web3 # noqa: F401
43
-
44
-
45
- class LinkableContract(Contract):
46
- """
47
- A subclass of web3.contract.Contract that is capable of handling
48
- contract factories with link references in their package's manifest.
49
- """
50
-
51
- unlinked_references: Optional[Tuple[Dict[str, Any]]] = None
52
- linked_references: Optional[Tuple[Dict[str, Any]]] = None
53
- needs_bytecode_linking = None
54
-
55
- def __init__(self, address: bytes, **kwargs: Any) -> None:
56
- if self.needs_bytecode_linking:
57
- raise BytecodeLinkingError(
58
- "Contract cannot be instantiated until its bytecode is linked."
59
- )
60
- validate_address(address)
61
- # type ignored to allow for undefined **kwargs on `Contract` base class __init__
62
- super().__init__(address=address, **kwargs) # type: ignore
63
-
64
- @classmethod
65
- def factory(cls, w3: "Web3", class_name: str = None, **kwargs: Any) -> Type[Self]:
66
- dep_link_refs = kwargs.get("unlinked_references")
67
- bytecode = kwargs.get("bytecode")
68
- needs_bytecode_linking = False
69
- if dep_link_refs and bytecode:
70
- if not is_prelinked_bytecode(to_bytes(hexstr=bytecode), dep_link_refs):
71
- needs_bytecode_linking = True
72
- kwargs = assoc(kwargs, "needs_bytecode_linking", needs_bytecode_linking)
73
- return super().factory(w3, class_name, **kwargs)
74
-
75
- @classmethod
76
- def constructor(cls, *args: Any, **kwargs: Any) -> ContractConstructor:
77
- if cls.needs_bytecode_linking:
78
- raise BytecodeLinkingError(
79
- "Contract cannot be deployed until its bytecode is linked."
80
- )
81
- return super().constructor(*args, **kwargs)
82
-
83
- @classmethod
84
- def link_bytecode(cls, attr_dict: Dict[str, str]) -> Type["LinkableContract"]:
85
- """
86
- Return a cloned contract factory with the deployment / runtime bytecode linked.
87
-
88
- :attr_dict: Dict[`ContractType`: `Address`] for all deployment and runtime
89
- link references.
90
- """
91
- if not cls.unlinked_references and not cls.linked_references:
92
- raise BytecodeLinkingError("Contract factory has no linkable bytecode.")
93
- if not cls.needs_bytecode_linking:
94
- raise BytecodeLinkingError(
95
- "Bytecode for this contract factory does not require bytecode linking."
96
- )
97
- cls.validate_attr_dict(attr_dict)
98
- bytecode = apply_all_link_refs(cls.bytecode, cls.unlinked_references, attr_dict)
99
- runtime = apply_all_link_refs(
100
- cls.bytecode_runtime, cls.linked_references, attr_dict
101
- )
102
- linked_class = cls.factory(cls.w3, bytecode_runtime=runtime, bytecode=bytecode)
103
- if linked_class.needs_bytecode_linking:
104
- raise BytecodeLinkingError(
105
- "Expected class to be fully linked, but class "
106
- "still needs bytecode linking."
107
- )
108
- return linked_class
109
-
110
- @combomethod
111
- def validate_attr_dict(self, attr_dict: Dict[str, str]) -> None:
112
- """
113
- Validates that ContractType keys in attr_dict reference existing
114
- manifest ContractTypes.
115
- """
116
- attr_dict_names = attr_dict.keys()
117
-
118
- if not self.unlinked_references and not self.linked_references:
119
- raise BytecodeLinkingError(
120
- "Unable to validate attr dict, this contract has no "
121
- "linked/unlinked references."
122
- )
123
-
124
- unlinked_refs = self.unlinked_references or ({},)
125
- linked_refs = self.linked_references or ({},)
126
- all_link_refs = unlinked_refs + linked_refs
127
-
128
- all_link_names = {ref["name"] for ref in all_link_refs if ref}
129
- if attr_dict_names != all_link_names:
130
- raise BytecodeLinkingError(
131
- "All link references must be defined when calling "
132
- "`link_bytecode` on a contract factory."
133
- )
134
- for address in attr_dict.values():
135
- validate_address(address)
136
-
137
-
138
- def is_prelinked_bytecode(bytecode: bytes, link_refs: List[Dict[str, Any]]) -> bool:
139
- """
140
- Returns False if all expected link_refs are unlinked, otherwise returns True.
141
- todo support partially pre-linked bytecode (currently all or nothing)
142
- """
143
- for link_ref in link_refs:
144
- for offset in link_ref["offsets"]:
145
- try:
146
- validate_empty_bytes(offset, link_ref["length"], bytecode)
147
- except EthPMValidationError:
148
- return True
149
- return False
150
-
151
-
152
- def apply_all_link_refs(
153
- bytecode: bytes, link_refs: List[Dict[str, Any]], attr_dict: Dict[str, str]
154
- ) -> bytes:
155
- """
156
- Applies all link references corresponding to a valid attr_dict to the bytecode.
157
- """
158
- if link_refs is None:
159
- return bytecode
160
- link_fns = (
161
- apply_link_ref(offset, ref["length"], attr_dict[ref["name"]])
162
- for ref in link_refs
163
- for offset in ref["offsets"]
164
- )
165
- linked_bytecode = pipe(bytecode, *link_fns)
166
- return linked_bytecode
167
-
168
-
169
- @curry
170
- def apply_link_ref(offset: int, length: int, value: bytes, bytecode: bytes) -> bytes:
171
- """
172
- Returns the new bytecode with `value` put into the location indicated by
173
- `offset` and `length`.
174
- """
175
- try:
176
- validate_empty_bytes(offset, length, bytecode)
177
- except EthPMValidationError:
178
- raise BytecodeLinkingError("Link references cannot be applied to bytecode")
179
-
180
- address = value if is_canonical_address(value) else to_canonical_address(value)
181
- new_bytes = (
182
- # Ignore linting error b/c conflict b/w black & flake8
183
- bytecode[:offset]
184
- + address
185
- + bytecode[offset + length :] # noqa: E201, E203
186
- )
187
- return new_bytes
ethpm/dependencies.py DELETED
@@ -1,58 +0,0 @@
1
- from typing import (
2
- Dict,
3
- List,
4
- Tuple,
5
- )
6
-
7
- from ethpm.validation.package import (
8
- validate_package_name,
9
- )
10
-
11
-
12
- class Dependencies:
13
- """
14
- Class to manage the `Package` instances of a Package's `buildDependencies`.
15
- """
16
-
17
- # ignoring Package type here and below to avoid a circular dependency
18
- def __init__(
19
- self, build_dependencies: Dict[str, "Package"] # type: ignore # noqa: F821
20
- ) -> None:
21
- self.build_dependencies = build_dependencies
22
-
23
- def __getitem__(self, key: str) -> "Package": # type: ignore # noqa: F821
24
- return self.build_dependencies.get(key)
25
-
26
- def __contains__(self, key: str) -> bool:
27
- return key in self.build_dependencies
28
-
29
- def _validate_name(self, name: str) -> None:
30
- validate_package_name(name)
31
- if name not in self.build_dependencies:
32
- raise KeyError(f"Package name: {name} not found in build dependencies.")
33
-
34
- def items(self) -> Tuple[Tuple[str, "Package"], ...]: # type: ignore # noqa: F821
35
- """
36
- Return an iterable containing package name and
37
- corresponding `Package` instance that are available.
38
- """
39
- item_dict = {
40
- name: self.build_dependencies.get(name) for name in self.build_dependencies
41
- }
42
- return tuple(item_dict.items())
43
-
44
- def values(self) -> List["Package"]: # type: ignore # noqa: F821
45
- """
46
- Return an iterable of the available `Package` instances.
47
- """
48
- values = [self.build_dependencies.get(name) for name in self.build_dependencies]
49
- return values
50
-
51
- def get_dependency_package(
52
- self, package_name: str
53
- ) -> "Package": # type: ignore # noqa: F821
54
- """
55
- Return the dependency Package for a given package name.
56
- """
57
- self._validate_name(package_name)
58
- return self.build_dependencies.get(package_name)