eth 0.5.0 → 0.5.3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (50) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/codeql.yml +4 -0
  3. data/.github/workflows/spec.yml +14 -3
  4. data/.yardopts +1 -0
  5. data/AUTHORS.txt +14 -1
  6. data/CHANGELOG.md +63 -13
  7. data/README.md +121 -18
  8. data/bin/console +2 -1
  9. data/bin/setup +3 -4
  10. data/codecov.yml +6 -0
  11. data/eth.gemspec +5 -7
  12. data/lib/eth/abi/event.rb +137 -0
  13. data/lib/eth/abi/type.rb +8 -7
  14. data/lib/eth/abi.rb +29 -11
  15. data/lib/eth/address.rb +12 -5
  16. data/lib/eth/api.rb +223 -0
  17. data/lib/eth/chain.rb +31 -28
  18. data/lib/eth/client/http.rb +63 -0
  19. data/lib/eth/client/ipc.rb +50 -0
  20. data/lib/eth/client.rb +468 -0
  21. data/lib/eth/constant.rb +71 -0
  22. data/lib/eth/contract/event.rb +41 -0
  23. data/lib/eth/contract/function.rb +56 -0
  24. data/lib/eth/contract/function_input.rb +36 -0
  25. data/lib/eth/contract/function_output.rb +32 -0
  26. data/lib/eth/contract/initializer.rb +46 -0
  27. data/lib/eth/contract.rb +120 -0
  28. data/lib/eth/eip712.rb +2 -2
  29. data/lib/eth/key/decrypter.rb +16 -13
  30. data/lib/eth/key/encrypter.rb +27 -25
  31. data/lib/eth/key.rb +21 -16
  32. data/lib/eth/rlp/decoder.rb +114 -0
  33. data/lib/eth/rlp/encoder.rb +78 -0
  34. data/lib/eth/rlp/sedes/big_endian_int.rb +66 -0
  35. data/lib/eth/rlp/sedes/binary.rb +97 -0
  36. data/lib/eth/rlp/sedes/list.rb +84 -0
  37. data/lib/eth/rlp/sedes.rb +74 -0
  38. data/lib/eth/rlp.rb +63 -0
  39. data/lib/eth/signature.rb +11 -8
  40. data/lib/eth/solidity.rb +75 -0
  41. data/lib/eth/tx/eip1559.rb +22 -14
  42. data/lib/eth/tx/eip2930.rb +23 -15
  43. data/lib/eth/tx/legacy.rb +14 -10
  44. data/lib/eth/tx.rb +28 -34
  45. data/lib/eth/unit.rb +1 -1
  46. data/lib/eth/util.rb +68 -11
  47. data/lib/eth/version.rb +3 -3
  48. data/lib/eth.rb +15 -2
  49. metadata +31 -23
  50. data/lib/eth/abi/constant.rb +0 -63
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: f2e1ab048011cd64dd6d4662e2fd203e1fc2eceeaa54f0a51d16659f9de910d1
4
- data.tar.gz: b54597a0b06c94919fdd9c06a7c663d3c55f83f7210085496fbae32402e578e8
3
+ metadata.gz: 0375271f13b257337cbc0ab138c2cdf972de8f8e03cf60bb9b672b2221ac988d
4
+ data.tar.gz: 19e85a6be34904b5544d9c6845ae19231616d65f27a8146c747f66068f2c23db
5
5
  SHA512:
6
- metadata.gz: 9fb243d28dd7407f3e595d8474fb64a47a76abff7b2a3bccdd8cae5a31ddfeb1598ed62fd01a78b54103fbe613ee357bb11356d9866e9743a066b8757da725e6
7
- data.tar.gz: 6e7912c298278d60b640e7728cba2550e9443e1c8dab63a1e797163570fdeefe797f4cf4535214eeb0461cbbed9cf604f4bea9850fd3b857d8ad83c3134c76db
6
+ metadata.gz: d5cc31684e8dfbff08b7250436a0bd4a94fa90942fd27b03292806cf2ac190673f1e507d8bcabd80b968a7206401a5210298c75c1ecc7c1d94765a7e94654d0d
7
+ data.tar.gz: 11b5a667d5cb333848aee384f4276fb3982a69104ae43c9650aec572ec3d093601c44b1b33167029b3ea37bcba6d8fd46da795ada67f6ad50fc39550fd092434
@@ -42,3 +42,7 @@ jobs:
42
42
  gem install rufo
43
43
  rufo --check ./lib
44
44
  rufo --check ./spec
45
+ - name: "Run yard documentation checks"
46
+ run: |
47
+ gem install yard
48
+ yard doc --fail-on-warning
@@ -26,11 +26,22 @@ jobs:
26
26
  with:
27
27
  ruby-version: ${{ matrix.ruby }}
28
28
  bundler-cache: false
29
- - name: Homebrew maketools
29
+ - name: MacOs Dependencies
30
30
  run: |
31
- brew install --verbose pkg-config automake autogen
31
+ brew tap ethereum/ethereum
32
+ brew install --verbose pkg-config automake autogen ethereum solidity
32
33
  if: startsWith(matrix.os, 'macOS')
33
- - name: Install Dependencies
34
+ - name: Ubuntu Dependencies
35
+ run: |
36
+ sudo add-apt-repository -y ppa:ethereum/ethereum
37
+ sudo apt-get update
38
+ sudo apt-get install ethereum solc
39
+ if: startsWith(matrix.os, 'Ubuntu')
40
+ - name: Run Geth
41
+ run: |
42
+ geth --dev --http --ipcpath /tmp/geth.ipc &
43
+ disown &
44
+ - name: Gem Dependencies
34
45
  run: |
35
46
  git submodule update --init
36
47
  bundle install
data/.yardopts ADDED
@@ -0,0 +1 @@
1
+ --verbose --fail-on-warning --markup markdown --embed-mixins
data/AUTHORS.txt CHANGED
@@ -2,6 +2,8 @@ The Ruby-Eth Contributors are:
2
2
  * Steve Ellis @se3000
3
3
  * Afri Schoedon @q9f
4
4
  * John Omar @chainoperator
5
+ * Joshua Peek @josh
6
+ * Yuta Kurotaki @kurotaky
5
7
 
6
8
  See also:
7
9
  * https://github.com/q9f/eth.rb/graphs/contributors
@@ -10,7 +12,18 @@ The Ruby-Eth project was maintained 2016-2020 in Steve Ellis's (@se3000)
10
12
  repository licensed under MIT conditions:
11
13
  * https://github.com/se3000/ruby-eth
12
14
 
13
- The latest version of the Ruby-Eth gem contains a revised version the
15
+ The latest Ruby-Eth gem is not only a rewrite of the aforementioned gem
16
+ but also a partial merge of the Ethereum.rb Ruby Ethereum library by
17
+ Marek Kirejczyk (@marekkirejczyk) and Yuta Kurotaki (@kurotaky) licensed
18
+ under MIT conditions:
19
+ * https://github.com/EthWorks/ethereum.rb
20
+
21
+ The latest version of the Ruby-Eth gem includes a revised version of the
14
22
  ABI gem by Jan Xie (@janx) and Zhang Yaning (@u2) licensed under MIT
15
23
  conditions:
16
24
  * https://github.com/cryptape/ruby-ethereum-abi
25
+
26
+ The latest version of the Ruby-Eth gem contains a condensed version of the
27
+ RLP gem by Jan Xie (@janx) and Zhang Yaning (@u2) licensed under MIT
28
+ conditions:
29
+ * https://github.com/cryptape/ruby-rlp
data/CHANGELOG.md CHANGED
@@ -1,25 +1,75 @@
1
1
  # Change Log
2
2
  All notable changes to this project will be documented in this file.
3
3
 
4
- The format is based on [Keep a Changelog](http://keepachangelog.com/)
5
- and this project adheres to [Semantic Versioning](http://semver.org/).
6
-
7
- ### Unreleased
4
+ ## [0.5.1]
5
+ ### Changed
6
+ - Docs: update changelog ([#61](https://github.com/q9f/eth.rb/pull/61))
7
+ - Eth/chain: add sepolia chain id; docs ([#60](https://github.com/q9f/eth.rb/pull/60))
8
+ - Eth/rlp: cleanup ([#59](https://github.com/q9f/eth.rb/pull/59))
9
+ - Add eth::rlp module ([#52](https://github.com/q9f/eth.rb/pull/52))
10
+ - Eth/tx: properly serialize signatures ([#58](https://github.com/q9f/eth.rb/pull/58))
11
+ - Eth/client: fix legacy transfer ([#57](https://github.com/q9f/eth.rb/pull/57))
12
+ - Gem: relax openssl requirement ([#56](https://github.com/q9f/eth.rb/pull/56))
13
+ - Eth/client: implement http/ipc ([#37](https://github.com/q9f/eth.rb/pull/37))
14
+ - Docs: update changelog ([#53](https://github.com/q9f/eth.rb/pull/53))
15
+ - Spec: add upstream test fixtures for keystore ([#50](https://github.com/q9f/eth.rb/pull/50))
16
+
17
+ ## [0.5.0]
18
+ ### Changed
19
+ - Docs: update readme with features [#49](https://github.com/q9f/eth.rb/pull/49)
20
+ - Eth/tx: add method to estimate intrinsic gas costs [#48](https://github.com/q9f/eth.rb/pull/48)
21
+ - Eth/key: allow chain_id empty for signing messages/data [#47](https://github.com/q9f/eth.rb/pull/47)
22
+ - Gem: prepare for release [#46](https://github.com/q9f/eth.rb/pull/46)
23
+ - Eth/sig: allow v values > 0xff, fix #30 [#43](https://github.com/q9f/eth.rb/pull/43)
24
+ - Eth/abi: refactor for maintainability [#42](https://github.com/q9f/eth.rb/pull/42)
25
+ - Docs: improve readme [#41](https://github.com/q9f/eth.rb/pull/41)
26
+ - Lib: improve error handling [#39](https://github.com/q9f/eth.rb/pull/39)
27
+ - Docs: update readme for tx and keys [#40](https://github.com/q9f/eth.rb/pull/40)
28
+ - Implement encrypt/decrypt [#22](https://github.com/q9f/eth.rb/pull/22)
29
+ - Eth/tx: create legacy, type-1, and type-2 transactions [#33](https://github.com/q9f/eth.rb/pull/33)
30
+ - Gem: clean up some docs and scripts [#32](https://github.com/q9f/eth.rb/pull/32)
31
+ - Signature: implement eip 712 typed structured data signing [#27](https://github.com/q9f/eth.rb/pull/27)
32
+ - Lib: import ABI to eth/abi [#29](https://github.com/q9f/eth.rb/pull/29)
33
+ - Rename util and chain to singular [#26](https://github.com/q9f/eth.rb/pull/26)
34
+ - Docs: add some examples to readme [#25](https://github.com/q9f/eth.rb/pull/25)
35
+ - Key/signature: personal sign and verify [#24](https://github.com/q9f/eth.rb/pull/24)
36
+ - Ci: only run coverage on CI [#23](https://github.com/q9f/eth.rb/pull/23)
37
+ - Lib/signature: implement personal_recover (eip 191 [#21](https://github.com/q9f/eth.rb/pull/21)
38
+ - Eth/chains: implement eip 155 for replay protection [#20](https://github.com/q9f/eth.rb/pull/20)
39
+ - Eth/util: public_key_to_address should return an eth::address [#19](https://github.com/q9f/eth.rb/pull/19)
40
+ - Ci: add docs workflow [#18](https://github.com/q9f/eth.rb/pull/18)
41
+ - Address class implementation and tests [#13](https://github.com/q9f/eth.rb/pull/13)
42
+ - Spec: improve util tests [#12](https://github.com/q9f/eth.rb/pull/12)
43
+ - Spec: improve key tests [#11](https://github.com/q9f/eth.rb/pull/11)
44
+ - Gems: bump keccak and secp256k1 [#10](https://github.com/q9f/eth.rb/pull/10)
45
+ - Docs: add code climate badge [#8](https://github.com/q9f/eth.rb/pull/8)
46
+ - Ci: enable codecov [#7](https://github.com/q9f/eth.rb/pull/7)
47
+ - Docs: add AUTHORS file [#6](https://github.com/q9f/eth.rb/pull/6)
48
+ - Lib: implement Eth::Key class [#4](https://github.com/q9f/eth.rb/pull/4)
49
+ - Ci: add nightly schedule [#2](https://github.com/q9f/eth.rb/pull/2)
50
+ - Reset gem to point blank [#1](https://github.com/q9f/eth.rb/pull/1)
51
+
52
+ ## [0.4.18]
53
+ ### Changed
54
+ - CI: add yard doc and rufo workflows [se3000/ruby-eth#75](https://github.com/se3000/ruby-eth/pull/75)
55
+ - Gem: run rufo [se3000/ruby-eth#74](https://github.com/se3000/ruby-eth/pull/74)
56
+ - Gem: dependencies [se3000/ruby-eth#73](https://github.com/se3000/ruby-eth/pull/73)
57
+ - Lib: fix compatibility with libressl (macos) and openssl 1.1.1k [se3000/ruby-eth#66](https://github.com/se3000/ruby-eth/pull/66)
8
58
 
9
59
  ## [0.4.17]
10
60
  ### Changed
11
- - Gems: bump version to 0.4.17 [#70](https://github.com/se3000/ruby-eth/pull/70)
12
- - Gems: bump keccak to 1.3.0 [#69](https://github.com/se3000/ruby-eth/pull/69)
61
+ - Gems: bump version to 0.4.17 [se3000/ruby-eth#70](https://github.com/se3000/ruby-eth/pull/70)
62
+ - Gems: bump keccak to 1.3.0 [se3000/ruby-eth#69](https://github.com/se3000/ruby-eth/pull/69)
13
63
 
14
64
  ## [0.4.16]
15
65
  ### Changed
16
- - Docs: update changelog [#65](https://github.com/se3000/ruby-eth/pull/65)
17
- - Gems: bump version to 0.4.16 [#65](https://github.com/se3000/ruby-eth/pull/65)
18
- - License: update copyright notice [#64](https://github.com/se3000/ruby-eth/pull/64)
19
- - Docs: add badges to readme [#64](https://github.com/se3000/ruby-eth/pull/64)
20
- - Git: deprecating master [#63](https://github.com/se3000/ruby-eth/pull/63)
21
- - CI: replace travis with github actions [#62](https://github.com/se3000/ruby-eth/pull/62)
22
- - Gems: replace digest-sha3-patched with keccak [#58](https://github.com/se3000/ruby-eth/pull/58)
66
+ - Docs: update changelog [se3000/ruby-eth#65](https://github.com/se3000/ruby-eth/pull/65)
67
+ - Gems: bump version to 0.4.16 [se3000/ruby-eth#65](https://github.com/se3000/ruby-eth/pull/65)
68
+ - License: update copyright notice [se3000/ruby-eth#64](https://github.com/se3000/ruby-eth/pull/64)
69
+ - Docs: add badges to readme [se3000/ruby-eth#64](https://github.com/se3000/ruby-eth/pull/64)
70
+ - Git: deprecating master [se3000/ruby-eth#63](https://github.com/se3000/ruby-eth/pull/63)
71
+ - CI: replace travis with github actions [se3000/ruby-eth#62](https://github.com/se3000/ruby-eth/pull/62)
72
+ - Gems: replace digest-sha3-patched with keccak [se3000/ruby-eth#58](https://github.com/se3000/ruby-eth/pull/58)
23
73
 
24
74
  ## [0.4.13], [0.4.14], [0.4.15]
25
75
  _Released as [`eth-patched`](https://github.com/q9f/ruby-eth) from a different source tree._
data/README.md CHANGED
@@ -1,16 +1,19 @@
1
- # Eth for Ruby
1
+ # Ethereum for Ruby
2
2
 
3
3
  [![GitHub Workflow Status](https://img.shields.io/github/workflow/status/q9f/eth.rb/Spec)](https://github.com/q9f/eth.rb/actions)
4
4
  [![GitHub release (latest by date)](https://img.shields.io/github/v/release/q9f/eth.rb)](https://github.com/q9f/eth.rb/releases)
5
5
  [![Gem](https://img.shields.io/gem/v/eth)](https://rubygems.org/gems/eth)
6
6
  [![Gem](https://img.shields.io/gem/dt/eth)](https://rubygems.org/gems/eth)
7
+ [![Visitors](https://hits.seeyoufarm.com/api/count/incr/badge.svg?url=https%3A%2F%2Fgithub.com%2Fq9f%2Feth.rb&count_bg=%2379C83D&title_bg=%23555555&icon=rubygems.svg&icon_color=%23FF0000&title=visitors&edge_flat=false)](https://hits.seeyoufarm.com)
7
8
  [![codecov](https://codecov.io/gh/q9f/eth.rb/branch/main/graph/badge.svg?token=IK7USBPBZY)](https://codecov.io/gh/q9f/eth.rb)
8
9
  [![Maintainability](https://api.codeclimate.com/v1/badges/469e6f66425198ad7614/maintainability)](https://codeclimate.com/github/q9f/eth.rb/maintainability)
9
- [![Yard Doc API](https://img.shields.io/badge/docs-API-blue)](https://q9f.github.io/eth.rb)
10
- [![GitHub top language](https://img.shields.io/github/languages/top/q9f/eth.rb?color=red)](https://github.com/q9f/eth.rb/pulse)
11
- [![GitHub](https://img.shields.io/github/license/q9f/eth.rb)](LICENSE)
10
+ [![Top Language](https://img.shields.io/github/languages/top/q9f/eth.rb?color=red)](https://github.com/q9f/eth.rb/pulse)
11
+ [![Yard Doc API](https://img.shields.io/badge/documentation-API-blue)](https://q9f.github.io/eth.rb)
12
+ [![Usage Wiki](https://img.shields.io/badge/usage-WIKI-blue)](https://github.com/q9f/eth.rb/wiki)
13
+ [![Open-Source License](https://img.shields.io/github/license/q9f/eth.rb)](LICENSE)
14
+ [![Contributions Welcome](https://img.shields.io/badge/contributions-welcome-brightgreen.svg?style=flat)](https://github.com/q9f/eth.rb/issues)
12
15
 
13
- A simple library to build and sign Ethereum transactions. Allows separation of key and node management. Sign transactions and handle keys anywhere you can run ruby, broadcast transactions through any node. Sign messages and recover signatures for authentication.
16
+ A straightforward library to build, sign, and broadcast Ethereum transactions. It allows the separation of key and node management. Sign transactions and handle keys anywhere you can run Ruby and broadcast transactions through any local or remote node. Sign messages and recover signatures for authentication.
14
17
 
15
18
  What you get:
16
19
  - [x] Secp256k1 Key-Pairs and Encrypted Ethereum Key-Stores (JSON)
@@ -23,11 +26,12 @@ What you get:
23
26
  - [x] EIP-2718 Ethereum Transaction Envelopes (and types)
24
27
  - [x] EIP-2930 Ethereum Type-1 Transactions (with access lists)
25
28
  - [x] ABI-Encoder and Decoder (including type parser)
29
+ - [x] RLP-Encoder and Decoder (including sedes)
30
+ - [x] RPC-Client (IPC/HTTP) for Execution-Layer APIs
31
+ - [x] Solidity bindings (compile contracts from Ruby)
26
32
 
27
33
  Soon (TM):
28
- - [ ] RLP-Encoder and Decoder (including sedes)
29
- - [ ] RPC-Client (HTTP) for Execution APIs and Consensus APIs
30
- - [ ] Smart Contracts and Solidity Support
34
+ - [ ] Smart Contract Support
31
35
  - [ ] EIP-1271 Smart-Contract Authentification
32
36
  - [ ] HD-Wallets (BIP-32) and Mnemonics (BIP-39)
33
37
 
@@ -39,13 +43,16 @@ Contents:
39
43
  - [2.3. Ethereum Chains (EIP-155)](#23-ethereum-chains-eip-155)
40
44
  - [2.4. Ethereum Transactions (EIP-1559, EIP-2718, EIP-2930)](#24-ethereum-transactions-eip-1559-eip-2718-eip-2930)
41
45
  - [2.5. Ethereum ABI Encoder and Decoder](#25-ethereum-abi-encoder-and-decoder)
46
+ - [2.6. Ethereum RLP Encoder and Decoder](#26-ethereum-rlp-encoder-and-decoder)
47
+ - [2.7. Ethereum RPC-Client](#27-ethereum-rpc-client)
48
+ - [2.8 Solidity Compiler Bindings](#28-solidity-compiler-bindings)
49
+ - [2.9 Interact with Smart Contract](#29-interact-with-smart-contract)
42
50
  - [3. Documentation](#3-documentation)
43
51
  - [4. Testing](#4-testing)
44
52
  - [5. Contributing](#5-contributing)
45
53
  - [6. License and Credits](#6-license-and-credits)
46
54
 
47
55
  ## 1. Installation
48
-
49
56
  Add this line to your application's Gemfile:
50
57
 
51
58
  ```ruby
@@ -59,9 +66,13 @@ gem install eth
59
66
  ```
60
67
 
61
68
  ## 2. Usage
69
+ Check out
70
+ [![Yard Doc API](https://img.shields.io/badge/documentation-API-blue)](https://q9f.github.io/eth.rb)
71
+ and
72
+ [![Usage Wiki](https://img.shields.io/badge/usage-WIKI-blue)](https://github.com/q9f/eth.rb/wiki)
73
+ for full details.
62
74
 
63
75
  ### 2.1. Ethereum Keys and Addresses (EIP-55)
64
-
65
76
  Generate a random Secp256k1 key-pair.
66
77
 
67
78
  ```ruby
@@ -93,7 +104,6 @@ address.checksummed # EIP 55
93
104
  See `/spec` or [Documentation](https://q9f.github.io/eth.rb/) for more details about key-pairs, encrypting/decrypting key-stores with a secret, and checksummed addresses.
94
105
 
95
106
  ### 2.2. Ethereum Signatures (EIP-191, EIP-712)
96
-
97
107
  Manage keypairs to sign messages in EIP-191 (`personal_sign`) format or typed data in EIP-712 (`sign_typed_data`) format.
98
108
 
99
109
  ```ruby
@@ -125,7 +135,6 @@ Eth::Signature.verify "Hello World!", signature, address, Eth::Chain::GOERLI
125
135
  See `/spec` or [Documentation](https://q9f.github.io/eth.rb/) for signing typed data as per EIP-712.
126
136
 
127
137
  ### 2.3. Ethereum Chains (EIP-155)
128
-
129
138
  Manage Ethereum chain IDs for EIP-155 replay protection.
130
139
 
131
140
  ```ruby
@@ -140,7 +149,6 @@ chain_id = Eth::Chain.to_chain_id v
140
149
  ```
141
150
 
142
151
  ### 2.4. Ethereum Transactions (EIP-1559, EIP-2718, EIP-2930)
143
-
144
152
  Create an EIP-1559-conform transaction:
145
153
 
146
154
  ```ruby
@@ -167,7 +175,6 @@ tx.hex
167
175
  This gem also supports access lists and ABI-encoded data payloads. See `/spec` or [Documentation](https://q9f.github.io/eth.rb/) for more details about the various supported transaction types (legacy, type-1, type-2), payload parameters, and how to estimate intrinsic gas costs.
168
176
 
169
177
  ### 2.5. Ethereum ABI Encoder and Decoder
170
-
171
178
  Encode and decode Ethereum application binary interface data (ABI).
172
179
 
173
180
  ```ruby
@@ -177,8 +184,94 @@ Eth::Abi.decode(["string", "address"], "0000000000000000000000000000000000000000
177
184
  # => ["Hello, Bob!", "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"]
178
185
  ```
179
186
 
180
- ## 3. Documentation
187
+ ### 2.6. Ethereum RLP Encoder and Decoder
188
+ Serialize and deserialize Ethereum recursive-length prefix data (RLP).
189
+
190
+ ```ruby
191
+ Eth::Util.bin_to_hex Eth::Rlp.encode ["Hello, Bob!", "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"]
192
+ # => "f78b48656c6c6f2c20426f6221aa307864343936623233643631663838613863373735386663613735363064636661633762336230316639"
193
+ Eth::Rlp.decode "f78b48656c6c6f2c20426f6221aa307864343936623233643631663838613863373735386663613735363064636661633762336230316639"
194
+ # => ["Hello, Bob!", "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"]
195
+ ```
181
196
 
197
+ Or ;-)
198
+
199
+ ```ruby
200
+ Eth::Rlp.decode "c7c0c1c0c3c0c1c0"
201
+ # => [[], [[]], [[], [[]]]]
202
+ ```
203
+
204
+ ### 2.7. Ethereum RPC-Client
205
+ Create an IPC- or HTTP-RPC-API client to seamlessly query the chain state, e.g., Infura over HTTPS with access token:
206
+
207
+ ```ruby
208
+ infura = Eth::Client.create "https://mainnet.infura.io/v3/#{access_token}"
209
+ # => #<Eth::Client::Http:0x000055d43f3ca460 @gas_limit=21000, @host="mainnet.infura.io", @id=0, @max_fee_per_gas=0.2e11, @max_priority_fee_per_gas=0, @port=443, @ssl=true, @uri=#<URI::HTTPS https://mainnet.infura.io/v3/31b...d93>>
210
+ deposit_contract = Eth::Address.new "0x00000000219ab540356cBB839Cbe05303d7705Fa"
211
+ # => #<Eth::Address:0x000055d43f381738 @address="0x00000000219ab540356cBB839Cbe05303d7705Fa">
212
+ infura.get_balance deposit_contract
213
+ # => 9087314000069000000000069
214
+ ```
215
+
216
+ Or set up a local development environment with `geth --dev`:
217
+
218
+ ```ruby
219
+ cli = Eth::Client.create "/tmp/geth.ipc"
220
+ # => #<Eth::Client::Ipc:0x000055d43f51c390 @gas_limit=21000, @id=0, @max_fee_per_gas=0.2e11, @max_priority_fee_per_gas=0, @path="/tmp/geth.ipc">
221
+ cli.eth_coinbase
222
+ # => {"jsonrpc"=>"2.0", "id"=>1, "result"=>"0x6868074fb21c48dfad0c448fbabd99383a6598e4"}
223
+ tx = cli.transfer_and_wait(Eth::Key.new.address, 1337 * Eth::Unit::ETHER)
224
+ # => "0x141c6dff40df34fe4fce5a65588d2161dab3e0e977fb8049ff7d79bc901034f7"
225
+ cli.eth_get_transaction_by_hash tx
226
+ # => {"jsonrpc"=>"2.0", "id"=>8, "result"=> {"blockHash"=>"0x47e742038c75851348dbda87b15fde044d54c442c371f43bea881a44d5589de3", "blockNumber"=>"0x1", "from"=>"0x6868074fb21c48dfad0c448fbabd99383a6598e4", "gas"=>"0x5208", "gasPrice"=>"0x342770c1", "maxFeePerGas"=>"0x77359401", "maxPriorityFeePerGas"=>"0x1", "hash"=>"0x141c6dff40df34fe4fce5a65588d2161dab3e0e977fb8049ff7d79bc901034f7", "input"=>"0x", "nonce"=>"0x0", "to"=>"0x311c61e5dc6123ad016bb7fd687d283c327bcd5f", "transactionIndex"=>"0x0", "value"=>"0x487a9a304539440000", "type"=>"0x2", "accessList"=>[], "chainId"=>"0x539", "v"=>"0x0", "r"=>"0xb42477d69eae65a3a3d91d9cb173e4a45a403fb0a15fa729dbfdc9d13211d7b5", "s"=>"0x4a2f98fc2b61c2d7c907520bc8c6ebe42ea6fe1cb6824f95e4b30e9464395100"}}
227
+ cli.get_balance "0x311c61e5dc6123ad016bb7fd687d283c327bcd5f"
228
+ # => 1337000000000000000000
229
+ cli.get_nonce cli.eth_coinbase["result"]
230
+ # => 1
231
+ ```
232
+
233
+ Check out `Eth::Api` for a list of supported RPC-APIs or consult the [Documentation](https://q9f.github.io/eth.rb/) for more details.
234
+
235
+ ### 2.8 Solidity Compiler Bindings
236
+ Link a system-level Solidity compiler (`solc`) to your Ruby library and compile contracts.
237
+
238
+ ```ruby
239
+ solc = Eth::Solidity.new
240
+ # => #<Eth::Solidity:0x000055f05040c6d0 @compiler="/usr/bin/solc">
241
+ contract = solc.compile "spec/fixtures/contracts/greeter.sol"
242
+ # => {"Greeter"=>
243
+ # {"abi"=>
244
+ # [{"inputs"=>[{"internalType"=>"string", "name"=>"message", "type"=>"string"}], "stateMutability"=>"nonpayable", "type"=>"constructor"},
245
+ # {"inputs"=>[], "name"=>"greet", "outputs"=>[{"internalType"=>"string", "name"=>"", "type"=>"string"}], "stateMutability"=>"view", "type"=>"function"},
246
+ # {"inputs"=>[], "name"=>"kill", "outputs"=>[], "stateMutability"=>"nonpayable", "type"=>"function"}],
247
+ # "bin"=>
248
+ # "6080604052348015...6c634300080c0033"},
249
+ # "Mortal"=>
250
+ # {"abi"=>[{"inputs"=>[], "stateMutability"=>"nonpayable", "type"=>"constructor"}, {"inputs"=>[], "name"=>"kill", "outputs"=>[], "stateMutability"=>"nonpayable", "type"=>"function"}],
251
+ # "bin"=>
252
+ # "6080604052348015...6c634300080c0033"}}
253
+ ```
254
+
255
+ The `contract["Greeter"]["bin"]` could be directly used to deploy the contract as `Eth::Tx` payload. Check out the [Documentation](https://q9f.github.io/eth.rb/) for more details.
256
+
257
+ ### 2.9 Interact with Smart Contract
258
+
259
+ Functions to interact with smart contract.
260
+
261
+ ```ruby
262
+ contract = Eth::Contract.create(file: 'spec/fixtures/contracts/dummy.sol')
263
+ # => #<Eth::Contract::Dummy:0x00007fbeee936598>
264
+ cli = Eth::Client.create "/tmp/geth.ipc"
265
+ # => #<Eth::Client::Ipc:0x00007fbeee946128 @gas_limit=21000, @id=0, @max_fee_per_gas=0.2e11, @max_priority_fee_per_gas=0, @path="/tmp/geth.ipc">
266
+ address = cli.deploy_and_wait(contract)
267
+ # => "0x2f2faa160420cee087ded96bad52475147136bd8"
268
+ cli.transact_and_wait(contract, "set", 1234)
269
+ # => "0x49ca4c0a5729da19a1d2574de9a444a9cd3219bdad81745b54f9cf3bb83b6a06"
270
+ cli.call(contract, "get")
271
+ # => 1234
272
+ ```
273
+
274
+ ## 3. Documentation
182
275
  The documentation can be found at: https://q9f.github.io/eth.rb
183
276
 
184
277
  For any specific version, docs can be generated by `yard`:
@@ -192,8 +285,13 @@ yard doc
192
285
  The goal is to have 100% API documentation available.
193
286
 
194
287
  ## 4. Testing
288
+ The test suite expects working local HTTP and IPC endpoints with a prefunded developer account, e.g.:
289
+
290
+ ```shell
291
+ geth --dev --http --ipcpath /tmp/geth.ipc &
292
+ ```
195
293
 
196
- To run tests, simply use `rspec`. Note, that the Ethereum tests fixtures are required.
294
+ To run tests, simply use `rspec`. Note, that the Ethereum test fixtures are also required.
197
295
 
198
296
  ```shell
199
297
  git submodule update --init --recursive
@@ -204,7 +302,6 @@ rspec
204
302
  The goal is to have 100% specification coverage for all code inside this gem.
205
303
 
206
304
  ## 5. Contributing
207
-
208
305
  Pull requests are welcome! To contribute, please consider the following:
209
306
  * Code should be fully documented. Run `yard doc` and make sure it does not yield any warnings or undocumented sets.
210
307
  * Code should be fully covered by tests. Run `rspec` to make sure all tests pass. The CI has an integration that will assis you to identify uncovered lines of code and get coverage up to 100%.
@@ -217,5 +314,11 @@ The `eth` gem is licensed under the conditions of [Apache 2.0](./LICENSE.txt). P
217
314
  This gem is a complete rewrite of the old `eth` gem by Steve Ellis.
218
315
  * https://github.com/se3000/ruby-eth/ (MIT)
219
316
 
220
- It also contains a revised version the ABI gem by Jan Xie and Zhang Yaning.
317
+ It is not only a rewrite of the `eth` gem but also a partial merge of the `ethereum` gem by Marek Kirejczyk and Yuta Kurotaki.
318
+ * https://github.com/EthWorks/ethereum.rb (MIT)
319
+
320
+ This gem also includes a revised version of the ABI gem by Jan Xie and Zhang Yaning.
221
321
  * https://github.com/cryptape/ruby-ethereum-abi (MIT)
322
+
323
+ It also contains a condensed version of the RLP gem by Jan Xie and Zhang Yaning.
324
+ * https://github.com/cryptape/ruby-rlp (MIT)
data/bin/console CHANGED
@@ -4,6 +4,7 @@
4
4
  $LOAD_PATH.unshift File.expand_path("../../lib", __FILE__)
5
5
 
6
6
  require "eth"
7
- require "pry"
7
+ include Eth
8
8
 
9
+ require "pry"
9
10
  Pry.start
data/bin/setup CHANGED
@@ -1,10 +1,9 @@
1
1
  #!/usr/bin/env bash
2
2
 
3
- set -euo pipefail
4
- IFS=$'\n\t'
5
- set -vx
6
-
7
3
  bundle install
8
4
  git submodule update --init --recursive
5
+ rufo .
9
6
  yard doc
10
7
  rspec
8
+
9
+ echo "Tests fail? Run \`geth --dev --http --ipcpath /tmp/geth.ipc\` in background and try again."
data/codecov.yml ADDED
@@ -0,0 +1,6 @@
1
+ coverage:
2
+ status:
3
+ project:
4
+ default:
5
+ target: 99%
6
+ threshold: 1%
data/eth.gemspec CHANGED
@@ -18,10 +18,11 @@ Gem::Specification.new do |spec|
18
18
  spec.license = "Apache-2.0"
19
19
 
20
20
  spec.metadata = {
21
- "homepage_uri" => "https://github.com/q9f/eth.rb",
22
- "source_code_uri" => "https://github.com/q9f/eth.rb",
23
- "github_repo" => "https://github.com/q9f/eth.rb",
24
21
  "bug_tracker_uri" => "https://github.com/q9f/eth.rb/issues",
22
+ "changelog_uri" => "https://github.com/q9f/eth.rb/blob/main/CHANGELOG.md",
23
+ "documentation_uri" => "https://q9f.github.io/eth.rb/",
24
+ "github_repo" => "https://github.com/q9f/eth.rb",
25
+ "source_code_uri" => "https://github.com/q9f/eth.rb",
25
26
  }.freeze
26
27
 
27
28
  spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
@@ -42,11 +43,8 @@ Gem::Specification.new do |spec|
42
43
  # rbsecp256k1 for key-pairs and signatures
43
44
  spec.add_dependency "rbsecp256k1", "~> 5.1"
44
45
 
45
- # rlp for transaction encoding
46
- spec.add_dependency "rlp", "~> 0.7"
47
-
48
46
  # openssl for encrypted key derivation
49
- spec.add_dependency "openssl", "~> 3.0"
47
+ spec.add_dependency "openssl", "~> 2.2"
50
48
 
51
49
  # scrypt for encrypted key derivation
52
50
  spec.add_dependency "scrypt", "~> 3.0"
@@ -0,0 +1,137 @@
1
+ # Copyright (c) 2016-2022 The Ruby-Eth Contributors
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ # -*- encoding : ascii-8bit -*-
16
+
17
+ # Provides the {Eth} module.
18
+ module Eth
19
+
20
+ # Provides a Ruby implementation of the Ethereum Applicatoin Binary Interface (ABI).
21
+ module Abi
22
+
23
+ # Provides a module to decode transaction log events.
24
+ module Event
25
+ extend self
26
+
27
+ # Compute topic for ABI event interface.
28
+ #
29
+ # @param interface [Hash] ABI event interface.
30
+ # @return [String] a hex-string topic.
31
+ def compute_topic(interface)
32
+ sig = Abi.signature(interface)
33
+ Util.prefix_hex(Util.bin_to_hex(Util.keccak256(sig)))
34
+ end
35
+
36
+ # A decoded event log.
37
+ class LogDescription
38
+ # The event ABI interface used to decode the log.
39
+ attr_accessor :event_interface
40
+
41
+ # The the input argument of the event.
42
+ attr_accessor :args
43
+
44
+ # The named input argument of the event.
45
+ attr_accessor :kwargs
46
+
47
+ # The topic hash.
48
+ attr_accessor :topic
49
+
50
+ # Decodes event log argument values.
51
+ #
52
+ # @param event_interface [Hash] event ABI type.
53
+ # @param log [Hash] transaction receipt log
54
+ def initialize(event_interface, log)
55
+ @event_interface = event_interface
56
+
57
+ inputs = event_interface.fetch("inputs")
58
+ data = log.fetch("data")
59
+ topics = log.fetch("topics", [])
60
+ anonymous = event_interface.fetch("anonymous", false)
61
+
62
+ @topic = topics[0] if !anonymous
63
+ @args, @kwargs = Event.decode_log(inputs, data, topics, anonymous)
64
+ end
65
+
66
+ # The event name. (e.g. Transfer)
67
+ def name
68
+ @name ||= event_interface.fetch("name")
69
+ end
70
+
71
+ # The event signature. (e.g. Transfer(address,address,uint256))
72
+ def signature
73
+ @signature ||= Abi.signature(event_interface)
74
+ end
75
+ end
76
+
77
+ # Decodes a stream of receipt logs with a set of ABI interfaces.
78
+ #
79
+ # @param interfaces [Array] event ABI types.
80
+ # @param logs [Array] transaction receipt logs
81
+ # @return [Hash] an enumerator of LogDescription objects.
82
+ def decode_logs(interfaces, logs)
83
+ Enumerator.new do |y|
84
+ topic_to_interfaces = Hash[interfaces.map { |i| [compute_topic(i), i] }]
85
+
86
+ logs.each do |log|
87
+ topic = log.fetch("topics", [])[0]
88
+ if topic && interface = topic_to_interfaces[topic]
89
+ y << [log, LogDescription.new(interface, log)]
90
+ else
91
+ y << [log, nil]
92
+ end
93
+ end
94
+ end
95
+ end
96
+
97
+ # Decodes event log argument values.
98
+ #
99
+ # @param inputs [Array] event ABI types.
100
+ # @param data [String] ABI event data to be decoded.
101
+ # @param topics [Array] ABI event topics to be decoded.
102
+ # @param anonymous [Boolean] If event signature is excluded from topics.
103
+ # @return [[Array, Hash]] decoded positional arguments and decoded keyword arguments.
104
+ # @raise [DecodingError] if decoding fails for type.
105
+ def decode_log(inputs, data, topics, anonymous = false)
106
+ topic_inputs, data_inputs = inputs.partition { |i| i["indexed"] }
107
+
108
+ topic_types = topic_inputs.map { |i| i["type"] }
109
+ data_types = data_inputs.map { |i| i["type"] }
110
+
111
+ # If event is anonymous, all topics are arguments. Otherwise, the first
112
+ # topic will be the event signature.
113
+ if anonymous == false
114
+ topics = topics[1..-1]
115
+ end
116
+
117
+ decoded_topics = topics.map.with_index { |t, i| Abi.decode([topic_types[i]], t)[0] }
118
+ decoded_data = Abi.decode(data_types, data)
119
+
120
+ args = []
121
+ kwargs = {}
122
+
123
+ inputs.each_with_index do |input, index|
124
+ if input["indexed"]
125
+ value = decoded_topics[topic_inputs.index(input)]
126
+ else
127
+ value = decoded_data[data_inputs.index(input)]
128
+ end
129
+ args[index] = value
130
+ kwargs[input["name"].to_sym] = value
131
+ end
132
+
133
+ return args, kwargs
134
+ end
135
+ end
136
+ end
137
+ end