sibit 0.4.0 → 0.5.0

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 662e8ffacbcc0e1aa2c0572b9bf1a8038773a92223726fcf286ee0be20fb0a0b
4
- data.tar.gz: ab96954610ece8e418672c64201b13f6ce36a69830d6c961d5e1f7a2a1622e49
3
+ metadata.gz: 478069971b53901e3037034ee2830d5b66154a77fc1b5087b17f15e94870ca39
4
+ data.tar.gz: 48039e52d5835aef4515e28c3fa3575e946e99556fcdb424f71c9f4c022f66e5
5
5
  SHA512:
6
- metadata.gz: 04a1b22d49ac9b8fd92b3a64d0db9abc818d56a066aa0aec30fe7fbf35898e580477f0bd716d9666e0444ad7a2b51e3ab77f5ea925c37314465c50b747fd08e0
7
- data.tar.gz: 43c3158f0e98c9b3754ade613df2c3faccb60efdec932107c47e72039b0002f3455c975f42028692b6acc158082882a455745d61be3b58ec275554bcd5629e08
6
+ metadata.gz: 80d804206aa880655b81a696a73558a47fc8dd1eee00d0c82fe7965283469d0b0586e56cace8d6309114af8572f8781deda7c259f6522317a9180c889a3e7fe5
7
+ data.tar.gz: 92d14ce0a35f45a1d994615a18fdde4472b33e39ff30c64f22606c0691bf37beed91db3a0c71f8a0f9f8b690da11eae24b8606030483213b5d34f42aae36d0fb
data/bin/sibit CHANGED
@@ -31,6 +31,8 @@ begin
31
31
  opts = Slop.parse(ARGV, strict: true, help: true) do |o|
32
32
  o.banner = "Usage (#{Sibit::VERSION}): sibit [options] command [args]
33
33
  Commands are:
34
+ price: Get current price of BTC in USD
35
+ latest: Get hash of the latest block
34
36
  generate: Generate a new private key
35
37
  create: Create a public Bitcoin address from the key
36
38
  balance: Check the balance of the Bitcoin address
@@ -48,6 +50,10 @@ Options are:"
48
50
  raise 'Try --help' if opts.arguments.empty?
49
51
  sibit = Sibit.new(log: opts[:verbose] ? STDOUT : nil)
50
52
  case opts.arguments[0]
53
+ when 'price'
54
+ puts sibit.price
55
+ when 'latest'
56
+ puts sibit.latest
51
57
  when 'generate'
52
58
  puts sibit.generate
53
59
  when 'create'
data/lib/sibit/version.rb CHANGED
@@ -26,5 +26,5 @@
26
26
  # License:: MIT
27
27
  class Sibit
28
28
  # Current version of the library.
29
- VERSION = '0.4.0'
29
+ VERSION = '0.5.0'
30
30
  end
data/lib/sibit.rb CHANGED
@@ -34,6 +34,9 @@ require 'json'
34
34
  # Copyright:: Copyright (c) 2019 Yegor Bugayenko
35
35
  # License:: MIT
36
36
  class Sibit
37
+ # If something goes wrong.
38
+ class Error < StandardError; end
39
+
37
40
  # Constructor.
38
41
  #
39
42
  # You may provide the log you want to see the messages in. If you don't
@@ -46,8 +49,8 @@ class Sibit
46
49
 
47
50
  # Current price of 1 BTC.
48
51
  def price(cur = 'USD')
49
- h = get_json('https://blockchain.info/ticker')[cur.upcase]
50
- raise "Unrecognized currency #{cur}" if h.nil?
52
+ h = get_json('/ticker')[cur.upcase]
53
+ raise Error, "Unrecognized currency #{cur}" if h.nil?
51
54
  h['15m']
52
55
  end
53
56
 
@@ -63,7 +66,7 @@ class Sibit
63
66
 
64
67
  # Gets the balance of the address, in satoshi.
65
68
  def balance(address)
66
- json = get_json("https://blockchain.info/rawaddr/#{address}")
69
+ json = get_json("/rawaddr/#{address}")
67
70
  debug("Total transactions: #{json['n_tx']}")
68
71
  debug("Received/sent: #{json['total_received']}/#{json['total_sent']}")
69
72
  json['final_balance']
@@ -92,7 +95,7 @@ class Sibit
92
95
  unspent = 0
93
96
  size = 100
94
97
  utxos = get_json(
95
- "https://blockchain.info/unspent?active=#{sources.join('|')}&limit=1000"
98
+ "/unspent?active=#{sources.join('|')}&limit=1000"
96
99
  )['unspent_outputs']
97
100
  debug("#{utxos.count} UTXOs found:")
98
101
  utxos.each do |utxo|
@@ -107,7 +110,7 @@ class Sibit
107
110
  debug(" #{utxo['value']}/#{utxo['confirmations']} at #{utxo['tx_hash_big_endian']}")
108
111
  break if unspent > satoshi
109
112
  end
110
- raise "Not enough funds to send #{amount}, only #{unspent} left" if unspent < satoshi
113
+ raise Error, "Not enough funds to send #{amount}, only #{unspent} left" if unspent < satoshi
111
114
  builder.output(satoshi, target)
112
115
  tx = builder.tx(
113
116
  input_value: unspent,
@@ -118,6 +121,22 @@ class Sibit
118
121
  tx.hash
119
122
  end
120
123
 
124
+ # Gets the hash of the latest block.
125
+ def latest
126
+ get_json('/latestblock')['hash']
127
+ end
128
+
129
+ # Send GET request to the Blockchain API and return JSON response.
130
+ # This method will also log the process and will validate the
131
+ # response for correctness.
132
+ def get_json(uri)
133
+ start = Time.now
134
+ res = Net::HTTP.get_response(URI('https://blockchain.info' + uri))
135
+ raise Error, "Failed to retrieve #{uri}: #{res.code}" unless res.code == '200'
136
+ debug("GET #{uri}: #{res.code} in #{age(start)}")
137
+ JSON.parse(res.body)
138
+ end
139
+
121
140
  private
122
141
 
123
142
  # Convert text to amount.
@@ -138,7 +157,7 @@ class Sibit
138
157
  when 'XL'
139
158
  return 250 * size
140
159
  else
141
- raise "Can't understand the fee: #{fee.inspect}"
160
+ raise Error, "Can't understand the fee: #{fee.inspect}"
142
161
  end
143
162
  end
144
163
 
@@ -157,18 +176,10 @@ class Sibit
157
176
  start = Time.now
158
177
  uri = URI('https://blockchain.info/pushtx')
159
178
  res = Net::HTTP.post_form(uri, tx: body)
160
- raise "Failed to post tx to #{uri}: #{res.code}" unless res.code == '200'
179
+ raise Error, "Failed to post tx to #{uri}: #{res.code}" unless res.code == '200'
161
180
  debug("POST #{uri}: #{res.code} in #{age(start)}")
162
181
  end
163
182
 
164
- def get_json(uri)
165
- start = Time.now
166
- res = Net::HTTP.get_response(URI(uri))
167
- raise "Failed to retrieve #{uri}: #{res.code}" unless res.code == '200'
168
- debug("GET #{uri}: #{res.code} in #{age(start)}")
169
- JSON.parse(res.body)
170
- end
171
-
172
183
  def debug(msg)
173
184
  if @log.respond_to?(:debug)
174
185
  @log.debug(msg)
data/test/test_sibit.rb CHANGED
@@ -57,7 +57,7 @@ class TestSibit < Minitest::Test
57
57
  assert(/^1[0-9a-zA-Z]+$/.match?(address))
58
58
  end
59
59
 
60
- def test_gets_balance
60
+ def test_get_balance
61
61
  stub_request(
62
62
  :get,
63
63
  'https://blockchain.info/rawaddr/1MZT1fa6y8H9UmbZV6HqKF4UY41o9MGT5f'
@@ -68,7 +68,17 @@ class TestSibit < Minitest::Test
68
68
  assert_equal(100, balance)
69
69
  end
70
70
 
71
- def test_sends_payment
71
+ def test_get_latest_block
72
+ stub_request(:get, 'https://blockchain.info/latestblock').to_return(
73
+ status: 200,
74
+ body: '{"hash": "0000000000000538200a48202ca6340e983646ca088c7618ae82d68e0c76ef5a"}'
75
+ )
76
+ sibit = Sibit.new
77
+ hash = sibit.latest
78
+ assert_equal('0000000000000538200a48202ca6340e983646ca088c7618ae82d68e0c76ef5a', hash)
79
+ end
80
+
81
+ def test_send_payment
72
82
  json = {
73
83
  unspent_outputs: [
74
84
  {
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sibit
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.0
4
+ version: 0.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Yegor Bugayenko