eth 0.5.6 → 0.5.8
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.github/workflows/codeql.yml +1 -1
- data/.github/workflows/docs.yml +2 -2
- data/.github/workflows/spec.yml +2 -2
- data/CHANGELOG.md +49 -0
- data/Gemfile +2 -2
- data/README.md +23 -259
- data/abis/ens.json +422 -0
- data/eth.gemspec +2 -2
- data/lib/eth/chain.rb +9 -0
- data/lib/eth/client/http_auth.rb +73 -0
- data/lib/eth/client.rb +114 -128
- data/lib/eth/contract/function_input.rb +1 -1
- data/lib/eth/contract/function_output.rb +1 -1
- data/lib/eth/ens/resolver.rb +77 -0
- data/lib/eth/signature.rb +4 -1
- data/lib/eth/tx/eip1559.rb +1 -1
- data/lib/eth/tx/eip2930.rb +1 -1
- data/lib/eth/tx/legacy.rb +1 -1
- data/lib/eth/tx.rb +6 -3
- data/lib/eth/version.rb +1 -1
- data/lib/eth.rb +1 -0
- metadata +8 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 8bb2370cb186c41e849c2949bbfcc1cb5cc6b2572064d8abba4631ed3ed3a692
|
4
|
+
data.tar.gz: dabde7655f7d8921f05a1cdb5d860981c3ee4cced8e1a7b085482d01b14c24b1
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 23a6ac9854368723b40fc0e46fed5e7ae90d1691358538f94cf8a9a43c333dc3e002e5d359513914440823501f882608d9e55e7a71a5a19ee88d38a57498a570
|
7
|
+
data.tar.gz: 14f5f74ea076a2fbdd5b538521a2b4006e58bf9105e34f0a942560841371f69a48cf80e86c680228ee5253e9483c3d85a857aeea7f48e8f4c1698a0f5ae0236c
|
data/.github/workflows/docs.yml
CHANGED
@@ -13,14 +13,14 @@ jobs:
|
|
13
13
|
- uses: actions/checkout@v3
|
14
14
|
- uses: ruby/setup-ruby@v1
|
15
15
|
with:
|
16
|
-
ruby-version: '
|
16
|
+
ruby-version: '3.0'
|
17
17
|
bundler-cache: true
|
18
18
|
- name: Run Yard Doc
|
19
19
|
run: |
|
20
20
|
gem install yard
|
21
21
|
yard doc
|
22
22
|
- name: Deploy GH Pages
|
23
|
-
uses: JamesIves/github-pages-deploy-action@v4.
|
23
|
+
uses: JamesIves/github-pages-deploy-action@v4.4.1
|
24
24
|
with:
|
25
25
|
branch: gh-pages
|
26
26
|
folder: doc/
|
data/.github/workflows/spec.yml
CHANGED
data/CHANGELOG.md
CHANGED
@@ -1,6 +1,55 @@
|
|
1
1
|
# Change Log
|
2
2
|
All notable changes to this project will be documented in this file.
|
3
3
|
|
4
|
+
## [0.5.7]
|
5
|
+
### Added
|
6
|
+
* Eth/client: add http basic support auth ([#151](https://github.com/q9f/eth.rb/pull/151))
|
7
|
+
* Chore: add polygon chain test case ([#146](https://github.com/q9f/eth.rb/pull/146))
|
8
|
+
|
9
|
+
### Changed
|
10
|
+
* Docs: add readme header for yard ([#159](https://github.com/q9f/eth.rb/pull/159))
|
11
|
+
* Eth/client: fix api documentation ([#158](https://github.com/q9f/eth.rb/pull/158))
|
12
|
+
* Eth/client: update default fees ([#157](https://github.com/q9f/eth.rb/pull/157))
|
13
|
+
* Docs: move readme usage to wiki ([#156](https://github.com/q9f/eth.rb/pull/156))
|
14
|
+
* Eth/signature: fix allowing ledger v values of 0 ([#155](https://github.com/q9f/eth.rb/pull/155))
|
15
|
+
* Eth/client: rename http basic to http auth ([#154](https://github.com/q9f/eth.rb/pull/154))
|
16
|
+
* Fix Eth:Tx.decode for transaction with s length < 64 chars ([#148](https://github.com/q9f/eth.rb/pull/148))
|
17
|
+
* Build(deps): bump JamesIves/github-pages-deploy-action from 4.3.4 to 4.4.0 ([#140](https://github.com/q9f/eth.rb/pull/140))
|
18
|
+
* Fixed to return uint256[] correctly when passed as type ([#147](https://github.com/q9f/eth.rb/pull/147))
|
19
|
+
* Build(deps): bump JamesIves/github-pages-deploy-action from 4.3.3 to 4.3.4 ([#133](https://github.com/q9f/eth.rb/pull/133))
|
20
|
+
* Docs: update CHANGELOG ([#132](https://github.com/q9f/eth.rb/pull/132))
|
21
|
+
* Gem: bump version to 0.5.7 ([#131](https://github.com/q9f/eth.rb/pull/131))
|
22
|
+
|
23
|
+
## [0.5.6]
|
24
|
+
### Added
|
25
|
+
- Eth/client: Add gas limit override option for contract deployments ([#128](https://github.com/q9f/eth.rb/pull/128))
|
26
|
+
- Eth/abi: support dynamic array encoding ([#122](https://github.com/q9f/eth.rb/pull/122))
|
27
|
+
|
28
|
+
### Changed
|
29
|
+
- Eth/client: Include contract constructor args when estimating intrinsic gas ([#111](https://github.com/q9f/eth.rb/pull/111))
|
30
|
+
- Eth/abi: allow parsing numerics from string inputs ([#112](https://github.com/q9f/eth.rb/pull/112))
|
31
|
+
- Eth/signature: fix prefix_message for multibyte characters ([#120](https://github.com/q9f/eth.rb/pull/120))
|
32
|
+
- Eth/abi: raise error if numeric comes as string ([#114](https://github.com/q9f/eth.rb/pull/114))
|
33
|
+
- Gem: bump version to 0.5.6 ([#130](https://github.com/q9f/eth.rb/pull/130))
|
34
|
+
|
35
|
+
## [0.5.5]
|
36
|
+
### Added
|
37
|
+
- Eth/contract: Add missing def_delegator for constructor_inputs ([#96](https://github.com/q9f/eth.rb/pull/96))
|
38
|
+
- Eth/client: Enable passing in constructor params to deploy ([#106](https://github.com/q9f/eth.rb/pull/106))
|
39
|
+
- Eth/chain: add matic/mumbai ([#107](https://github.com/q9f/eth.rb/pull/107))
|
40
|
+
|
41
|
+
### Changed
|
42
|
+
- Gem: bump version to 0.5.5 ([#89](https://github.com/q9f/eth.rb/pull/89))
|
43
|
+
- Docs: update changelog for 0.5.4 ([#90](https://github.com/q9f/eth.rb/pull/90))
|
44
|
+
- Ci: add weekly dependency checks ([#91](https://github.com/q9f/eth.rb/pull/91))
|
45
|
+
- Build(deps): bump github/codeql-action from 1 to 2 ([#92](https://github.com/q9f/eth.rb/pull/92))
|
46
|
+
- Build(deps): bump actions/checkout from 2 to 3 ([#93](https://github.com/q9f/eth.rb/pull/93))
|
47
|
+
- Build(deps): bump JamesIves/github-pages-deploy-action from 4.1.7 to 4.3.3 ([#94](https://github.com/q9f/eth.rb/pull/94))
|
48
|
+
- Eth/abi: fix handling of hex values for byte strings ([#100](https://github.com/q9f/eth.rb/pull/100))
|
49
|
+
- Eth/abi: add a testcase for handling hex and bin strings ([#101](https://github.com/q9f/eth.rb/pull/101))
|
50
|
+
- Eth/abi: Fix Eth::Abi::DecodingError in call method ([#105](https://github.com/q9f/eth.rb/pull/105))
|
51
|
+
- Eth: some docs and cleanups ([#108](https://github.com/q9f/eth.rb/pull/108))
|
52
|
+
|
4
53
|
## [0.5.4]
|
5
54
|
### Added
|
6
55
|
- Eth/client: method for eip-1271 ([#80](https://github.com/q9f/eth.rb/pull/80))
|
data/Gemfile
CHANGED
@@ -7,8 +7,8 @@ group :test, :development do
|
|
7
7
|
gem "codecov", "~> 0.6"
|
8
8
|
gem "pry", "~> 0.14"
|
9
9
|
gem "rake", "~> 13.0"
|
10
|
-
gem "rdoc", "~> 6.
|
11
|
-
gem "rspec", "~> 3.
|
10
|
+
gem "rdoc", "~> 6.4"
|
11
|
+
gem "rspec", "~> 3.11"
|
12
12
|
gem "rufo", "~> 0.13"
|
13
13
|
gem "simplecov", "~> 0.21"
|
14
14
|
gem "yard", "~> 0.9"
|
data/README.md
CHANGED
@@ -1,3 +1,9 @@
|
|
1
|
+
<!--
|
2
|
+
# @markup markdown
|
3
|
+
# @title Ethereum for Ruby
|
4
|
+
# @author Afri Schoedon
|
5
|
+
-->
|
6
|
+
|
1
7
|
# Ethereum for Ruby
|
2
8
|
|
3
9
|
[![GitHub Workflow Status](https://img.shields.io/github/workflow/status/q9f/eth.rb/Spec)](https://github.com/q9f/eth.rb/actions)
|
@@ -30,26 +36,9 @@ What you get:
|
|
30
36
|
- [x] RLP-Encoder and Decoder (including sedes)
|
31
37
|
- [x] RPC-Client (IPC/HTTP) for Execution-Layer APIs
|
32
38
|
- [x] Solidity bindings (compile contracts from Ruby)
|
33
|
-
- [x] Full smart-contract support (deploy, transact, and call)
|
34
|
-
|
35
|
-
Contents:
|
36
|
-
- [1. Installation](#1-installation)
|
37
|
-
- [2. Usage](#2-usage)
|
38
|
-
- [2.1. Ethereum Keys and Addresses (EIP-55)](#21-ethereum-keys-and-addresses-eip-55)
|
39
|
-
- [2.2. Ethereum Signatures (EIP-191, EIP-712)](#22-ethereum-signatures-eip-191-eip-712)
|
40
|
-
- [2.3. Ethereum Chains (EIP-155)](#23-ethereum-chains-eip-155)
|
41
|
-
- [2.4. Ethereum Transactions (EIP-1559, EIP-2718, EIP-2930)](#24-ethereum-transactions-eip-1559-eip-2718-eip-2930)
|
42
|
-
- [2.5. Ethereum ABI Encoder and Decoder](#25-ethereum-abi-encoder-and-decoder)
|
43
|
-
- [2.6. Ethereum RLP Encoder and Decoder](#26-ethereum-rlp-encoder-and-decoder)
|
44
|
-
- [2.7. Ethereum RPC-Client](#27-ethereum-rpc-client)
|
45
|
-
- [2.8. Solidity Compiler Bindings](#28-solidity-compiler-bindings)
|
46
|
-
- [2.9. Interact with Smart Contract](#29-interact-with-smart-contract)
|
47
|
-
- [3. Documentation](#3-documentation)
|
48
|
-
- [4. Testing](#4-testing)
|
49
|
-
- [5. Contributing](#5-contributing)
|
50
|
-
- [6. License and Credits](#6-license-and-credits)
|
39
|
+
- [x] ~~Full~~ Some smart-contract support (deploy, transact, and call)
|
51
40
|
|
52
|
-
##
|
41
|
+
## Installation
|
53
42
|
Add this line to your application's Gemfile:
|
54
43
|
|
55
44
|
```ruby
|
@@ -62,252 +51,27 @@ Or install it yourself as:
|
|
62
51
|
gem install eth
|
63
52
|
```
|
64
53
|
|
65
|
-
##
|
66
|
-
Check out
|
67
|
-
[![Yard
|
68
|
-
and
|
54
|
+
## Usage
|
55
|
+
Check out the
|
56
|
+
[![Yard API Docs](https://img.shields.io/badge/documentation-API-blue)](https://q9f.github.io/eth.rb)
|
57
|
+
and the
|
69
58
|
[![Usage Wiki](https://img.shields.io/badge/usage-WIKI-blue)](https://github.com/q9f/eth.rb/wiki)
|
70
|
-
for
|
71
|
-
|
72
|
-
### 2.1. Ethereum Keys and Addresses (EIP-55)
|
73
|
-
Generate a random Secp256k1 key-pair.
|
74
|
-
|
75
|
-
```ruby
|
76
|
-
key = Eth::Key.new
|
77
|
-
# => #<Eth::Key:0x00005574a6ba80b8 @private_key=#<Secp256k1::PrivateKey:0x00005574a6b9a0a8 @data=")&\x86P\xB5\x16\xD9]\xFA;\x1F\xF6\xD9\xCF\xE3Vj/\xE2\x81\xC0\x9D\xE9\x05o!q\x82G\x9A\x10Q">, @public_key=#<Secp256k1::PublicKey:0x00005574a6b9bf98>>
|
78
|
-
```
|
79
|
-
|
80
|
-
Create an password-encrypted Ethereum key-store.
|
81
|
-
|
82
|
-
```ruby
|
83
|
-
my_key = Eth::Key.new priv: "30137644b564785d01420f8043f043d74dcca64008e57c59f8ce713a0005a54b"
|
84
|
-
key_store = Eth::Key::Encrypter.perform my_key, "secret-password-1337"
|
85
|
-
# => "{\"crypto\":{\"cipher\":\"aes-128-ctr\",\"cipherparams\":{\"iv\":\"7e5c0fe1e27f4ea61b0f4427dd63555f\"},\"ciphertext\":\"6353653bba494cdae6bcd510febc980cdc6f7b23cfbdf950d7a909a69625c8fd\",\"kdf\":\"pbkdf2\",\"kdfparams\":{\"c\":262144,\"dklen\":32,\"prf\":\"hmac-sha256\",\"salt\":\"cce96286f3c32267fc91f756365307fe6a4c83b6b2a73c69535f721fa407736c\"},\"mac\":\"3361ffd2b158a1d7bca5a5fd86a251ba3e9d80b602c867a2e0f47023a0e17a57\"},\"id\":\"642ee9fc-72e4-4d0a-902f-247c0b59bfda\",\"version\":3}"
|
86
|
-
restored_key = Eth::Key::Decrypter.perform key_store, "secret-password-1337"
|
87
|
-
# => "30137644b564785d01420f8043f043d74dcca64008e57c59f8ce713a0005a54b"
|
88
|
-
```
|
89
|
-
|
90
|
-
Manage Ethereum address objects adhering to EIP-55 checksum format.
|
91
|
-
|
92
|
-
```ruby
|
93
|
-
address = Eth::Address.new "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"
|
94
|
-
# => #<Eth::Address:0x00005574a6bd4fc8 @address="0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9">
|
95
|
-
address.valid?
|
96
|
-
# => true
|
97
|
-
address.checksummed # EIP 55
|
98
|
-
# => "0xD496b23D61F88A8C7758fca7560dCFac7b3b01F9"
|
99
|
-
```
|
100
|
-
|
101
|
-
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.
|
102
|
-
|
103
|
-
### 2.2. Ethereum Signatures (EIP-191, EIP-712)
|
104
|
-
Manage keypairs to sign messages in EIP-191 (`personal_sign`) format or typed data in EIP-712 (`sign_typed_data`) format.
|
105
|
-
|
106
|
-
```ruby
|
107
|
-
key = Eth::Key.new priv: "268be6f4a68c40f6862b7ac9aed8f701dc25a95ddb9a44d8b1f520b75f440a9a"
|
108
|
-
# => #<Eth::Key:0x00005574a699adc0 @private_key=#<Secp256k1::PrivateKey:0x00005574a6998200 @data="&\x8B\xE6\xF4\xA6\x8C@\xF6\x86+z\xC9\xAE\xD8\xF7\x01\xDC%\xA9]\xDB\x9AD\xD8\xB1\xF5 \xB7_D\n\x9A">, @public_key=#<Secp256k1::PublicKey:0x00005574a6998160>>
|
109
|
-
key.public_hex
|
110
|
-
# => "04b45200621c013a5fbab999ac33b0c836328a04afa0255ffbe6ea0f6fd97e187b02199886d942a9f50f7e279a2bc74c93b2afcbd7255489939f9b36a5eae5e281"
|
111
|
-
key.address.to_s
|
112
|
-
# => "0xD496b23D61F88A8C7758fca7560dCFac7b3b01F9"
|
113
|
-
key.personal_sign "Hello World!"
|
114
|
-
# => "ac6a59417d8688c8144f01a662384fa691636b48a071d4b7c13902bb87ca472b0bce1d7a758f39a5759ed5e937ce61f50dd1b83158371f8d0faeb9b7d81c194225"
|
115
|
-
```
|
116
|
-
|
117
|
-
Recover and verify personal signatures respecting EIPs 155, 191, and 712.
|
118
|
-
|
119
|
-
```ruby
|
120
|
-
address = Eth::Address.new "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"
|
121
|
-
# => #<Eth::Address:0x00005574a6bd4fc8 @address="0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9">
|
122
|
-
signature = "ac6a59417d8688c8144f01a662384fa691636b48a071d4b7c13902bb87ca472b0bce1d7a758f39a5759ed5e937ce61f50dd1b83158371f8d0faeb9b7d81c19422d"
|
123
|
-
# => "ac6a59417d8688c8144f01a662384fa691636b48a071d4b7c13902bb87ca472b0bce1d7a758f39a5759ed5e937ce61f50dd1b83158371f8d0faeb9b7d81c19422d"
|
124
|
-
recovered_key = Eth::Signature.personal_recover "Hello World!", signature, Eth::Chain::GOERLI
|
125
|
-
# => "04b45200621c013a5fbab999ac33b0c836328a04afa0255ffbe6ea0f6fd97e187b02199886d942a9f50f7e279a2bc74c93b2afcbd7255489939f9b36a5eae5e281"
|
126
|
-
Eth::Util.public_key_to_address(recovered_key).to_s
|
127
|
-
# => "0xD496b23D61F88A8C7758fca7560dCFac7b3b01F9"
|
128
|
-
Eth::Signature.verify "Hello World!", signature, address, Eth::Chain::GOERLI
|
129
|
-
# => true
|
130
|
-
```
|
131
|
-
|
132
|
-
See `/spec` or [Documentation](https://q9f.github.io/eth.rb/) for signing typed data as per EIP-712.
|
133
|
-
|
134
|
-
### 2.3. Ethereum Chains (EIP-155)
|
135
|
-
Manage Ethereum chain IDs for EIP-155 replay protection.
|
136
|
-
|
137
|
-
```ruby
|
138
|
-
chain_id = Eth::Chain::OPTIMISM
|
139
|
-
# => 10
|
140
|
-
v = Eth::Chain.to_v 0, Eth::Chain::OPTIMISM
|
141
|
-
# => 55
|
142
|
-
recovery_id = Eth::Chain.to_recovery_id v, Eth::Chain::OPTIMISM
|
143
|
-
# => 0
|
144
|
-
chain_id = Eth::Chain.to_chain_id v
|
145
|
-
# => 10
|
146
|
-
```
|
147
|
-
|
148
|
-
### 2.4. Ethereum Transactions (EIP-1559, EIP-2718, EIP-2930)
|
149
|
-
Create an EIP-1559-conform transaction:
|
150
|
-
|
151
|
-
```ruby
|
152
|
-
payload = {
|
153
|
-
chain_id: Eth::Chain::GOERLI,
|
154
|
-
nonce: 5,
|
155
|
-
priority_fee: 3 * Eth::Unit::GWEI,
|
156
|
-
max_gas_fee: 69 * Eth::Unit::GWEI,
|
157
|
-
gas_limit: 230_420,
|
158
|
-
to: "0xCaA29806044A08E533963b2e573C1230A2cd9a2d",
|
159
|
-
value: 0.069423 * Eth::Unit::ETHER,
|
160
|
-
}
|
161
|
-
# => {:chain_id=>5, :nonce=>5, :priority_fee=>0.3e10, :max_gas_fee=>0.69e11, :gas_limit=>230420, :to=>"0xCaA29806044A08E533963b2e573C1230A2cd9a2d", :value=>0.69423e17}
|
162
|
-
tx = Eth::Tx.new payload
|
163
|
-
# => #<Eth::Tx::Eip1559:0x0000557e35fc5a68 @access_list=[], @amount=69423000000000000, @chain_id=5, @destination="CaA29806044A08E533963b2e573C1230A2cd9a2d", @gas_limit=230420, @max_fee_per_gas=69000000000, @max_priority_fee_per_gas=3000000000, @payload="", @sender="", @signature_r=0, @signature_s=0, @signature_y_parity=nil, @signer_nonce=5, @type=2>
|
164
|
-
my_key = Eth::Key.new priv: "30137644b564785d01420f8043f043d74dcca64008e57c59f8ce713a0005a54b"
|
165
|
-
# => #<Eth::Key:0x0000557e36243178 @private_key=#<Secp256k1::PrivateKey:0x0000557e36242d40 @data="0\x13vD\xB5dx]\x01B\x0F\x80C\xF0C\xD7M\xCC\xA6@\b\xE5|Y\xF8\xCEq:\x00\x05\xA5K">, @public_key=#<Secp256k1::PublicKey:0x0000557e36242cf0>>
|
166
|
-
tx.sign my_key
|
167
|
-
# => "cba302c0ebf8d0205a78ae97f560419b407e32e2426f416abc95a9bfc9dac09c"
|
168
|
-
tx.hex
|
169
|
-
# => "02f873050584b2d05e00851010b872008303841494caa29806044a08e533963b2e573c1230a2cd9a2d87f6a3d9c63df00080c080a03aa187d10b138d3e0155729adb961cd89e10f988ba2d19d6869770b9e5a23d10a04d40864600136ae214916043c7d63b849c98db757e95c86983a036982816e1af"
|
170
|
-
```
|
171
|
-
|
172
|
-
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.
|
173
|
-
|
174
|
-
### 2.5. Ethereum ABI Encoder and Decoder
|
175
|
-
Encode and decode Ethereum application binary interface data (ABI).
|
176
|
-
|
177
|
-
```ruby
|
178
|
-
Eth::Util.bin_to_hex Eth::Abi.encode(["string", "address"], ["Hello, Bob!", "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"])
|
179
|
-
# => "0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000d496b23d61f88a8c7758fca7560dcfac7b3b01f9000000000000000000000000000000000000000000000000000000000000000b48656c6c6f2c20426f6221000000000000000000000000000000000000000000"
|
180
|
-
Eth::Abi.decode(["string", "address"], "0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000d496b23d61f88a8c7758fca7560dcfac7b3b01f9000000000000000000000000000000000000000000000000000000000000000b48656c6c6f2c20426f6221000000000000000000000000000000000000000000")
|
181
|
-
# => ["Hello, Bob!", "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"]
|
182
|
-
```
|
183
|
-
|
184
|
-
### 2.6. Ethereum RLP Encoder and Decoder
|
185
|
-
Serialize and deserialize Ethereum recursive-length prefix data (RLP).
|
186
|
-
|
187
|
-
```ruby
|
188
|
-
Eth::Util.bin_to_hex Eth::Rlp.encode ["Hello, Bob!", "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"]
|
189
|
-
# => "f78b48656c6c6f2c20426f6221aa307864343936623233643631663838613863373735386663613735363064636661633762336230316639"
|
190
|
-
Eth::Rlp.decode "f78b48656c6c6f2c20426f6221aa307864343936623233643631663838613863373735386663613735363064636661633762336230316639"
|
191
|
-
# => ["Hello, Bob!", "0xd496b23d61f88a8c7758fca7560dcfac7b3b01f9"]
|
192
|
-
```
|
193
|
-
|
194
|
-
Or ;-)
|
195
|
-
|
196
|
-
```ruby
|
197
|
-
Eth::Rlp.decode "c7c0c1c0c3c0c1c0"
|
198
|
-
# => [[], [[]], [[], [[]]]]
|
199
|
-
```
|
200
|
-
|
201
|
-
### 2.7. Ethereum RPC-Client
|
202
|
-
Create an IPC- or HTTP-RPC-API client to seamlessly query the chain state, e.g., Infura over HTTPS with access token:
|
203
|
-
|
204
|
-
```ruby
|
205
|
-
infura = Eth::Client.create "https://mainnet.infura.io/v3/#{access_token}"
|
206
|
-
# => #<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>>
|
207
|
-
deposit_contract = Eth::Address.new "0x00000000219ab540356cBB839Cbe05303d7705Fa"
|
208
|
-
# => #<Eth::Address:0x000055d43f381738 @address="0x00000000219ab540356cBB839Cbe05303d7705Fa">
|
209
|
-
infura.get_balance deposit_contract
|
210
|
-
# => 9087314000069000000000069
|
211
|
-
```
|
212
|
-
|
213
|
-
Or set up a local development environment with `geth --dev`:
|
214
|
-
|
215
|
-
```ruby
|
216
|
-
cli = Eth::Client.create "/tmp/geth.ipc"
|
217
|
-
# => #<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">
|
218
|
-
cli.eth_coinbase
|
219
|
-
# => {"jsonrpc"=>"2.0", "id"=>1, "result"=>"0x6868074fb21c48dfad0c448fbabd99383a6598e4"}
|
220
|
-
tx = cli.transfer_and_wait(Eth::Key.new.address, 1337 * Eth::Unit::ETHER)
|
221
|
-
# => "0x141c6dff40df34fe4fce5a65588d2161dab3e0e977fb8049ff7d79bc901034f7"
|
222
|
-
cli.eth_get_transaction_by_hash tx
|
223
|
-
# => {"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"}}
|
224
|
-
cli.get_balance "0x311c61e5dc6123ad016bb7fd687d283c327bcd5f"
|
225
|
-
# => 1337000000000000000000
|
226
|
-
cli.get_nonce cli.eth_coinbase["result"]
|
227
|
-
# => 1
|
228
|
-
```
|
229
|
-
|
230
|
-
Check out `Eth::Api` for a list of supported RPC-APIs or consult the [Documentation](https://q9f.github.io/eth.rb/) for more details.
|
231
|
-
|
232
|
-
### 2.8. Solidity Compiler Bindings
|
233
|
-
Link a system-level Solidity compiler (`solc`) to your Ruby library and compile contracts.
|
234
|
-
|
235
|
-
```ruby
|
236
|
-
solc = Eth::Solidity.new
|
237
|
-
# => #<Eth::Solidity:0x000055f05040c6d0 @compiler="/usr/bin/solc">
|
238
|
-
contract = solc.compile "spec/fixtures/contracts/greeter.sol"
|
239
|
-
# => {"Greeter"=>
|
240
|
-
# {"abi"=>
|
241
|
-
# [{"inputs"=>[{"internalType"=>"string", "name"=>"message", "type"=>"string"}], "stateMutability"=>"nonpayable", "type"=>"constructor"},
|
242
|
-
# {"inputs"=>[], "name"=>"greet", "outputs"=>[{"internalType"=>"string", "name"=>"", "type"=>"string"}], "stateMutability"=>"view", "type"=>"function"},
|
243
|
-
# {"inputs"=>[], "name"=>"kill", "outputs"=>[], "stateMutability"=>"nonpayable", "type"=>"function"}],
|
244
|
-
# "bin"=>
|
245
|
-
# "6080604052348015...6c634300080c0033"},
|
246
|
-
# "Mortal"=>
|
247
|
-
# {"abi"=>[{"inputs"=>[], "stateMutability"=>"nonpayable", "type"=>"constructor"}, {"inputs"=>[], "name"=>"kill", "outputs"=>[], "stateMutability"=>"nonpayable", "type"=>"function"}],
|
248
|
-
# "bin"=>
|
249
|
-
# "6080604052348015...6c634300080c0033"}}
|
250
|
-
```
|
251
|
-
|
252
|
-
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.
|
253
|
-
|
254
|
-
### 2.9. Interact with Smart Contract
|
255
|
-
|
256
|
-
Create, compile, and deploy smart contracts.
|
257
|
-
|
258
|
-
```ruby
|
259
|
-
contract = Eth::Contract.from_file(file: 'spec/fixtures/contracts/dummy.sol')
|
260
|
-
# => #<Eth::Contract::Dummy:0x00007fbeee936598>
|
261
|
-
cli = Eth::Client.create "/tmp/geth.ipc"
|
262
|
-
# => #<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">
|
263
|
-
address = cli.deploy_and_wait(contract)
|
264
|
-
# => "0x2f2faa160420cee087ded96bad52475147136bd8"
|
265
|
-
```
|
266
|
-
|
267
|
-
Transact with or call the deployed contract.
|
268
|
-
|
269
|
-
```ruby
|
270
|
-
cli.transact_and_wait(contract, "set", 1234)
|
271
|
-
# => "0x49ca4c0a5729da19a1d2574de9a444a9cd3219bdad81745b54f9cf3bb83b6a06"
|
272
|
-
cli.call(contract, "get")
|
273
|
-
# => 1234
|
274
|
-
```
|
275
|
-
|
276
|
-
Or call an existing contract, e.g., the ENS registry:
|
277
|
-
|
278
|
-
```ruby
|
279
|
-
ens_registry_abi = '[{"inputs":[{"internalType":"contract ENS","name":"_old","type":"address"}],"payable":false,"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"address","name":"owner","type":"address"},{"indexed":true,"internalType":"address","name":"operator","type":"address"},{"indexed":false,"internalType":"bool","name":"approved","type":"bool"}],"name":"ApprovalForAll","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":true,"internalType":"bytes32","name":"label","type":"bytes32"},{"indexed":false,"internalType":"address","name":"owner","type":"address"}],"name":"NewOwner","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"address","name":"resolver","type":"address"}],"name":"NewResolver","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"uint64","name":"ttl","type":"uint64"}],"name":"NewTTL","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"bytes32","name":"node","type":"bytes32"},{"indexed":false,"internalType":"address","name":"owner","type":"address"}],"name":"Transfer","type":"event"},{"constant":true,"inputs":[{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"operator","type":"address"}],"name":"isApprovedForAll","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[],"name":"old","outputs":[{"internalType":"contract ENS","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"}],"name":"owner","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"}],"name":"recordExists","outputs":[{"internalType":"bool","name":"","type":"bool"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":true,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"}],"name":"resolver","outputs":[{"internalType":"address","name":"","type":"address"}],"payable":false,"stateMutability":"view","type":"function"},{"constant":false,"inputs":[{"internalType":"address","name":"operator","type":"address"},{"internalType":"bool","name":"approved","type":"bool"}],"name":"setApprovalForAll","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"address","name":"owner","type":"address"}],"name":"setOwner","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"resolver","type":"address"},{"internalType":"uint64","name":"ttl","type":"uint64"}],"name":"setRecord","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"address","name":"resolver","type":"address"}],"name":"setResolver","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"bytes32","name":"label","type":"bytes32"},{"internalType":"address","name":"owner","type":"address"}],"name":"setSubnodeOwner","outputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"bytes32","name":"label","type":"bytes32"},{"internalType":"address","name":"owner","type":"address"},{"internalType":"address","name":"resolver","type":"address"},{"internalType":"uint64","name":"ttl","type":"uint64"}],"name":"setSubnodeRecord","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":false,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"},{"internalType":"uint64","name":"ttl","type":"uint64"}],"name":"setTTL","outputs":[],"payable":false,"stateMutability":"nonpayable","type":"function"},{"constant":true,"inputs":[{"internalType":"bytes32","name":"node","type":"bytes32"}],"name":"ttl","outputs":[{"internalType":"uint64","name":"","type":"uint64"}],"payable":false,"stateMutability":"view","type":"function"}]'
|
280
|
-
ens_registry_address = "0x00000000000C2E074eC69A0dFb2997BA6C7d2e1e"
|
281
|
-
ens_registry_name = "ENSRegistryWithFallback"
|
282
|
-
ens_registry = Eth::Contract.from_abi(name: ens_registry_name, address: ens_registry_address, abi: ens_registry_abi)
|
283
|
-
# => #<Eth::Contract::ENSRegistryWithFallback:0x000055bece570980>
|
284
|
-
ens_registry.address
|
285
|
-
# => "0x00000000000C2E074eC69A0dFb2997BA6C7d2e1e"
|
286
|
-
cli.call(ens_registry, "old")
|
287
|
-
# => "0x112234455c3a32fd11230c42e7bccd4a84e02010"
|
288
|
-
```
|
289
|
-
|
290
|
-
The gem also comes with an EIP-1271 smart-contract authentification interface.
|
291
|
-
|
292
|
-
```ruby
|
293
|
-
cli.is_valid_signature contract, hash, signature
|
294
|
-
# => true
|
295
|
-
```
|
59
|
+
for all the details and example snippets.
|
296
60
|
|
297
|
-
##
|
61
|
+
## Documentation
|
298
62
|
The documentation can be found at: https://q9f.github.io/eth.rb
|
299
63
|
|
300
64
|
For any specific version, docs can be generated by `yard`:
|
301
65
|
|
302
66
|
```shell
|
303
67
|
gem install bundler rdoc yard
|
304
|
-
git checkout
|
68
|
+
git checkout $VERSION
|
305
69
|
yard doc
|
306
70
|
```
|
307
71
|
|
308
72
|
The goal is to have 100% API documentation available.
|
309
73
|
|
310
|
-
##
|
74
|
+
## Testing
|
311
75
|
The test suite expects working local HTTP and IPC endpoints with a prefunded developer account, e.g.:
|
312
76
|
|
313
77
|
```shell
|
@@ -324,24 +88,24 @@ rspec
|
|
324
88
|
|
325
89
|
The goal is to have 100% specification coverage for all code inside this gem.
|
326
90
|
|
327
|
-
##
|
91
|
+
## Contributing
|
328
92
|
Pull requests are welcome! To contribute, please consider the following:
|
329
93
|
* Code should be fully documented. Run `yard doc` and make sure it does not yield any warnings or undocumented sets.
|
330
94
|
* 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%.
|
331
95
|
* Code should be formatted properly. Try to eliminate the most common issues such as trailing white-spaces or duplicate new-lines. Usage of the `rufo` gem is recommended.
|
332
|
-
* Submit pull requests, questions, or issues to Github: https://github.com/q9f/eth.rb
|
96
|
+
* Submit pull requests, questions, or issues to Github: <https://github.com/q9f/eth.rb>
|
333
97
|
|
334
|
-
##
|
98
|
+
## License and Credits
|
335
99
|
The `eth` gem is licensed under the conditions of [Apache 2.0](./LICENSE.txt). Please see [AUTHORS](./AUTHORS.txt) for contributors and copyright notices.
|
336
100
|
|
337
101
|
This gem is a complete rewrite of the old `eth` gem by Steve Ellis.
|
338
|
-
* https://github.com/se3000/ruby-eth
|
102
|
+
* <https://github.com/se3000/ruby-eth> (MIT)
|
339
103
|
|
340
104
|
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.
|
341
|
-
* https://github.com/EthWorks/ethereum.rb (MIT)
|
105
|
+
* <https://github.com/EthWorks/ethereum.rb> (MIT)
|
342
106
|
|
343
107
|
This gem also includes a revised version of the ABI gem by Jan Xie and Zhang Yaning.
|
344
|
-
* https://github.com/cryptape/ruby-ethereum-abi (MIT)
|
108
|
+
* <https://github.com/cryptape/ruby-ethereum-abi> (MIT)
|
345
109
|
|
346
110
|
It also contains a condensed version of the RLP gem by Jan Xie and Zhang Yaning.
|
347
|
-
* https://github.com/cryptape/ruby-rlp (MIT)
|
111
|
+
* <https://github.com/cryptape/ruby-rlp> (MIT)
|