eth-rb 0.1.5 → 0.1.7

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 (3) hide show
  1. checksums.yaml +4 -4
  2. data/lib/eth.rb +52 -5
  3. metadata +6 -4
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6406b8a909ffa800ee2ca237fd58b97fa5c07602aec7db483bc93aed5e50c1a4
4
- data.tar.gz: 649564b79457d90806d0c31127c2a24953497c4679384ed71284a30b5b4b8093
3
+ metadata.gz: 65e04da1733386b288cd4b5e77ab983e287e132a1b0102f8f33992ba013dda93
4
+ data.tar.gz: 15bbf5486f20692b25dbab12610a8832a26dbd0721734dbcfcb23f6e222ad74f
5
5
  SHA512:
6
- metadata.gz: 771b14da3a273e6f25da6b2e65eb0b2838b3fd23122cd716c801463eaf838c41862d1115a5a7ca556d517f6ad5a343d2a6bdf111d78e93c72dfd5226921cf753
7
- data.tar.gz: 94cf8b5447f44c1c04128b7881838351ef19c349084cf5504572eb3d11280b5586a1640e69acec3cf8b8983f37948969abd5ab19bc570325b3477068eb067943
6
+ metadata.gz: 346f28432cbea631f2eb7648318453209947e46fb4e33544b328adfaae8de1847d16aa7329b9793aad598cd5efc9ea622a3fc34133ffbf9b19521dfa25398cd1
7
+ data.tar.gz: 04c7c839490c5a6f98e457268f8ca001a914af4af92fd41936e5a198b710a6a84f37873e7ac6a3e9269418cf57f6662cd8f4293ab03a363028eb1c7380e5a656
data/lib/eth.rb CHANGED
@@ -7,9 +7,11 @@
7
7
  # ./eth.rb — show latest block number
8
8
  # ./eth.rb <address> — show ETH balance of <address>
9
9
  # ./eth.rb --price — show current ETH/USD price
10
+ # ./eth.rb --genkey or -g — generate a new private key + address
11
+ # ./eth.rb --pubkey <key> — derive public key + address from <key>
10
12
  # ./eth.rb --version or -v — show version
11
- # ./eth.rb send <key> <to> <amount> — send ETH (amount in ETH)
12
- # ./eth.rb send <key> <to> \$<amount> — send ETH (amount in USD, converted at current price)
13
+ # ./eth.rb --send <key> <to> <amount> — send ETH (amount in ETH)
14
+ # ./eth.rb --send <key> <to> \$<amount> — send ETH (amount in USD, converted at current price)
13
15
  # ./eth.rb --help — show this usage info
14
16
 
15
17
  require "net/http"
@@ -22,7 +24,7 @@ require "digest/keccak"
22
24
  ALCHEMY_URL = "https://eth-mainnet.g.alchemy.com/v2/alch_PhpVkmsabZhYV69otj1rF"
23
25
  COINGECKO_URL = "https://api.coingecko.com/api/v3/simple/price?ids=ethereum&vs_currencies=usd"
24
26
  CHAIN_ID = 1 # Ethereum mainnet
25
- VERSION = "0.1.5"
27
+ VERSION = "0.1.7"
26
28
 
27
29
  # ── JSON-RPC ────────────────────────────────────────────────────────────────
28
30
 
@@ -144,12 +146,52 @@ def private_key_to_address(priv_hex)
144
146
  hash.byteslice(12, 20)
145
147
  end
146
148
 
149
+ # Derive the uncompressed public key (04 || x || y, 64 bytes) from a
150
+ # private key hex string (with or without 0x)
151
+ def private_key_to_pubkey(priv_hex)
152
+ priv_int = normalize_hex(priv_hex).to_i(16)
153
+ pub_point = GROUP.generator.multiply_by_scalar(priv_int)
154
+
155
+ pad32 = ->(b) { b.bytesize >= 32 ? b : "\x00" * (32 - b.bytesize) + b }
156
+ "\x04" + pad32.call(to_big_endian(pub_point.x)) + pad32.call(to_big_endian(pub_point.y))
157
+ end
158
+
147
159
  def normalize_hex(str)
148
160
  hex = str.start_with?("0x") || str.start_with?("0X") ? str[2..] : str
149
161
  hex = "0#{hex}" if hex.bytesize.odd?
150
162
  hex
151
163
  end
152
164
 
165
+ # Generate a random private key: a scalar in [1, n-1] where n is the
166
+ # order of the secp256k1 curve group
167
+ def generate_private_key
168
+ SecureRandom.random_number(GROUP.order - 1) + 1
169
+ end
170
+
171
+ def show_new_key
172
+ priv = generate_private_key
173
+ priv_hex = "0x%064x" % priv
174
+ addr = "0x#{private_key_to_address(priv_hex).unpack1('H*')}"
175
+ puts "Private Key: #{priv_hex}"
176
+ puts "Address: #{addr}"
177
+ end
178
+
179
+ def cmd_pubkey(args)
180
+ if args.empty?
181
+ puts "Usage: ./eth.rb --pubkey <private_key_hex>"
182
+ exit 1
183
+ end
184
+
185
+ priv_hex = normalize_hex(args[0])
186
+ priv = priv_hex.to_i(16)
187
+ pub_hex = "0x#{private_key_to_pubkey(args[0]).unpack1('H*')}"
188
+ addr = "0x#{private_key_to_address(args[0]).unpack1('H*')}"
189
+
190
+ puts "Private Key: 0x%064x" % priv
191
+ puts "Public Key: #{pub_hex}"
192
+ puts "Address: #{addr}"
193
+ end
194
+
153
195
  # ── Transaction signing ─────────────────────────────────────────────────────
154
196
 
155
197
  def build_and_sign_tx(private_key_hex, to_address, amount_wei)
@@ -231,7 +273,7 @@ end
231
273
  def cmd_send(args)
232
274
  # p args
233
275
  if args.length < 3
234
- puts "Usage: ./eth.rb send <private_key_hex> <to_address> <amount>"
276
+ puts "Usage: ./eth.rb --send <private_key_hex> <to_address> <amount>"
235
277
  puts " amount: number (ETH) or $number (USD, converted to ETH at current price)"
236
278
  exit 1
237
279
  end
@@ -323,6 +365,7 @@ def show_version
323
365
  end
324
366
 
325
367
  def print_usage
368
+ puts "eth.rb v#{VERSION}"
326
369
  puts File.read(__FILE__)[/^#\sUsage:.*?(?=\n\n)/m]
327
370
  end
328
371
 
@@ -333,11 +376,15 @@ def run_cli(args)
333
376
  show_block_number
334
377
  elsif args[0] == "--price"
335
378
  show_price
379
+ elsif args[0] == "--genkey" || args[0] == "-g"
380
+ show_new_key
381
+ elsif args[0] == "--pubkey" || args[0] == "pubkey"
382
+ cmd_pubkey(args[1..])
336
383
  elsif args[0] == "--version" || args[0] == "-v"
337
384
  show_version
338
385
  elsif args[0] == "--help" || args[0] == "-h"
339
386
  print_usage
340
- elsif args[0] == "send"
387
+ elsif args[0] == "--send" || args[0] == "send"
341
388
  cmd_send(args[1..])
342
389
  else
343
390
  show_balance(args[0])
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: eth-rb
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.5
4
+ version: 0.1.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - Khalid Shaikh
@@ -37,8 +37,9 @@ dependencies:
37
37
  - - "~>"
38
38
  - !ruby/object:Gem::Version
39
39
  version: '1.3'
40
- description: A lightweight CLI tool for querying Ethereum balances, block numbers,
41
- ETH/USD prices, and sending transactions via Alchemy JSON-RPC.
40
+ description: A lightweight CLI tool for generating Ethereum private keys and addresses,
41
+ querying balances, block numbers, and ETH/USD prices, and sending transactions via
42
+ Alchemy JSON-RPC.
42
43
  email:
43
44
  - k@iai.lol
44
45
  executables:
@@ -68,5 +69,6 @@ required_rubygems_version: !ruby/object:Gem::Requirement
68
69
  requirements: []
69
70
  rubygems_version: 4.0.17
70
71
  specification_version: 4
71
- summary: Ethereum blockchain queries via Alchemy JSON-RPC
72
+ summary: 'Ethereum CLI: balances, prices, key generation, and transactions via Alchemy
73
+ JSON-RPC'
72
74
  test_files: []