bitcoinrb 0.2.1 → 0.2.2
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 +4 -4
- data/lib/bitcoin/block.rb +5 -1
- data/lib/bitcoin/block_header.rb +5 -2
- data/lib/bitcoin/merkle_tree.rb +37 -10
- data/lib/bitcoin/network/message_handler.rb +1 -0
- data/lib/bitcoin/network/peer.rb +7 -2
- data/lib/bitcoin/psbt/hd_key_path.rb +2 -2
- data/lib/bitcoin/psbt/input.rb +8 -0
- data/lib/bitcoin/psbt/output.rb +2 -0
- data/lib/bitcoin/psbt/tx.rb +7 -6
- data/lib/bitcoin/rpc/request_handler.rb +1 -1
- data/lib/bitcoin/script/script.rb +5 -0
- data/lib/bitcoin/store/chain_entry.rb +6 -2
- data/lib/bitcoin/store/db/level_db.rb +5 -7
- data/lib/bitcoin/store/spv_chain.rb +4 -4
- data/lib/bitcoin/tx.rb +6 -2
- data/lib/bitcoin/validation.rb +1 -1
- data/lib/bitcoin/version.rb +1 -1
- data/lib/openassets/marker_output.rb +8 -2
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 524753cfa61041f101f72d76e914f70b20b504fb0eecad9d378a436afe7db718
|
4
|
+
data.tar.gz: f3181a60120da9f892ceaaaaf22aba5923b26f495fb9fb9dd314c5cce8127129
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: da27669ddabc4d64bf3c96d4e83eb8c5d90ef837ed91b6f2e1d0e7d50c74153c62ff39eecb1867463f5a8435f7643d62ba6108e7a10d1fa46e4b10178fe8e2f1
|
7
|
+
data.tar.gz: 2f85e04fecddba5bb1d1ce4fc61bf79fd972280f4834e56a4b56974958903e74bd1d19789c93d6bdebe8bead9b5fca8ad26d4c35967760cf0517da42ebfeb35d
|
data/lib/bitcoin/block.rb
CHANGED
@@ -17,6 +17,10 @@ module Bitcoin
|
|
17
17
|
header.hash
|
18
18
|
end
|
19
19
|
|
20
|
+
def block_hash
|
21
|
+
header.block_hash
|
22
|
+
end
|
23
|
+
|
20
24
|
# calculate block weight
|
21
25
|
def weight
|
22
26
|
stripped_size * (WITNESS_SCALE_FACTOR - 1) + size
|
@@ -41,7 +45,7 @@ module Bitcoin
|
|
41
45
|
|
42
46
|
# calculate merkle root from tx list.
|
43
47
|
def calculate_merkle_root
|
44
|
-
Bitcoin::MerkleTree.build_from_leaf(transactions.map(&:
|
48
|
+
Bitcoin::MerkleTree.build_from_leaf(transactions.map(&:tx_hash)).merkle_root
|
45
49
|
end
|
46
50
|
|
47
51
|
# check the witness commitment in coinbase tx matches witness commitment calculated from tx list.
|
data/lib/bitcoin/block_header.rb
CHANGED
@@ -36,14 +36,17 @@ module Bitcoin
|
|
36
36
|
(mantissa * 2 ** (8 * (exponent - 3)))
|
37
37
|
end
|
38
38
|
|
39
|
-
# block hash(little endian)
|
40
39
|
def hash
|
40
|
+
calc_hash.to_i(16)
|
41
|
+
end
|
42
|
+
|
43
|
+
def block_hash
|
41
44
|
calc_hash
|
42
45
|
end
|
43
46
|
|
44
47
|
# block hash(big endian)
|
45
48
|
def block_id
|
46
|
-
|
49
|
+
block_hash.rhex
|
47
50
|
end
|
48
51
|
|
49
52
|
# evaluate block header
|
data/lib/bitcoin/merkle_tree.rb
CHANGED
@@ -10,7 +10,7 @@ module Bitcoin
|
|
10
10
|
end
|
11
11
|
|
12
12
|
def merkle_root
|
13
|
-
root.
|
13
|
+
root.value
|
14
14
|
end
|
15
15
|
|
16
16
|
def self.build_from_leaf(txids)
|
@@ -31,11 +31,16 @@ module Bitcoin
|
|
31
31
|
flags.each do |f|
|
32
32
|
current_node.flag = f
|
33
33
|
if f.zero? || current_node.leaf?
|
34
|
-
current_node.
|
34
|
+
current_node.value = hashes[hash_index]
|
35
35
|
hash_index += 1
|
36
36
|
end
|
37
37
|
current_node = current_node.next_partial
|
38
|
-
|
38
|
+
if hash_index == hashes.size
|
39
|
+
if current_node&.leaf?
|
40
|
+
current_node.value = hashes.last
|
41
|
+
end
|
42
|
+
break
|
43
|
+
end
|
39
44
|
end
|
40
45
|
new(root)
|
41
46
|
end
|
@@ -52,17 +57,21 @@ module Bitcoin
|
|
52
57
|
nodes.first
|
53
58
|
end
|
54
59
|
|
60
|
+
def find_node(value)
|
61
|
+
root.find_node(value)
|
62
|
+
end
|
63
|
+
|
55
64
|
# node of merkle tree
|
56
65
|
class Node
|
57
66
|
|
58
67
|
attr_accessor :flag
|
59
|
-
attr_accessor :
|
68
|
+
attr_accessor :value
|
60
69
|
attr_accessor :parent
|
61
70
|
attr_accessor :left
|
62
71
|
attr_accessor :right
|
63
72
|
|
64
|
-
def initialize(
|
65
|
-
@
|
73
|
+
def initialize(value = nil)
|
74
|
+
@value = value
|
66
75
|
end
|
67
76
|
|
68
77
|
def left=(node)
|
@@ -75,10 +84,10 @@ module Bitcoin
|
|
75
84
|
@right = node
|
76
85
|
end
|
77
86
|
|
78
|
-
def
|
79
|
-
return @
|
87
|
+
def value
|
88
|
+
return @value if @value
|
80
89
|
self.right = left.dup unless right
|
81
|
-
Bitcoin.double_sha256([left.
|
90
|
+
Bitcoin.double_sha256([left.value + right.value].pack('H*')).bth
|
82
91
|
end
|
83
92
|
|
84
93
|
def root?
|
@@ -112,7 +121,25 @@ module Bitcoin
|
|
112
121
|
d
|
113
122
|
end
|
114
123
|
|
124
|
+
# @param target value to be found
|
125
|
+
# @return node which has same value as target. nil if this node and any children don't have same value.
|
126
|
+
def find_node(target)
|
127
|
+
return self if value == target
|
128
|
+
return nil if flag && flag.zero?
|
129
|
+
return left&.find_node(target) || right&.find_node(target)
|
130
|
+
end
|
131
|
+
|
132
|
+
def index
|
133
|
+
i = 0
|
134
|
+
d = 1
|
135
|
+
current_node = self
|
136
|
+
until current_node.root? do
|
137
|
+
i += d if current_node.parent.right == current_node
|
138
|
+
current_node = current_node.parent
|
139
|
+
d *= 2
|
140
|
+
end
|
141
|
+
i
|
142
|
+
end
|
115
143
|
end
|
116
144
|
end
|
117
|
-
|
118
145
|
end
|
data/lib/bitcoin/network/peer.rb
CHANGED
@@ -92,7 +92,7 @@ module Bitcoin
|
|
92
92
|
def start_block_header_download
|
93
93
|
logger.info("[#{addr}] start block header download.")
|
94
94
|
get_headers = Bitcoin::Message::GetHeaders.new(
|
95
|
-
Bitcoin.chain_params.protocol_version, [chain.latest_block.
|
95
|
+
Bitcoin.chain_params.protocol_version, [chain.latest_block.block_hash])
|
96
96
|
conn.send_message(get_headers)
|
97
97
|
end
|
98
98
|
|
@@ -138,7 +138,7 @@ module Bitcoin
|
|
138
138
|
break unless header.valid?
|
139
139
|
entry = chain.append_header(header)
|
140
140
|
next unless entry
|
141
|
-
@best_hash = entry.
|
141
|
+
@best_hash = entry.block_hash
|
142
142
|
@best_height = entry.height
|
143
143
|
end
|
144
144
|
pool.changed
|
@@ -190,6 +190,11 @@ module Bitcoin
|
|
190
190
|
pool.notify_observers(:tx, tx)
|
191
191
|
end
|
192
192
|
|
193
|
+
def handle_merkle_block(merkle_block)
|
194
|
+
pool.changed
|
195
|
+
pool.notify_observers(:merkleblock, merkle_block)
|
196
|
+
end
|
197
|
+
|
193
198
|
# send ping message.
|
194
199
|
def send_ping
|
195
200
|
ping = Bitcoin::Message::Ping.new
|
@@ -20,9 +20,9 @@ module Bitcoin
|
|
20
20
|
# @param [String] payload hd key path value with binary format.
|
21
21
|
# @return [Bitcoin::PSBT::HDKeyPath]
|
22
22
|
def self.parse_from_payload(pubkey, payload)
|
23
|
-
raise 'Size of key was not the expected size for the type BIP32 keypath' unless [Bitcoin::Key::PUBLIC_KEY_SIZE, Bitcoin::Key::COMPRESSED_PUBLIC_KEY_SIZE].include?(pubkey.bytesize)
|
23
|
+
raise ArgumentError, 'Size of key was not the expected size for the type BIP32 keypath.' unless [Bitcoin::Key::PUBLIC_KEY_SIZE, Bitcoin::Key::COMPRESSED_PUBLIC_KEY_SIZE].include?(pubkey.bytesize)
|
24
24
|
pubkey = Bitcoin::Key.new(pubkey: pubkey.bth)
|
25
|
-
raise 'Invalid pubkey' unless pubkey.fully_valid_pubkey?
|
25
|
+
raise ArgumentError, 'Invalid pubkey' unless pubkey.fully_valid_pubkey?
|
26
26
|
self.new(pubkey.pubkey, fingerprint: payload[0...4].bth, path: payload[4..-1].unpack('I*'))
|
27
27
|
end
|
28
28
|
|
data/lib/bitcoin/psbt/input.rb
CHANGED
@@ -38,9 +38,11 @@ module Bitcoin
|
|
38
38
|
|
39
39
|
case key_type
|
40
40
|
when PSBT_IN_TYPES[:non_witness_utxo]
|
41
|
+
raise ArgumentError, 'Invalid non-witness utxo typed key.' unless key_len == 1
|
41
42
|
raise ArgumentError, 'Duplicate Key, input non-witness utxo already provided.' if input.non_witness_utxo
|
42
43
|
input.non_witness_utxo = Bitcoin::Tx.parse_from_payload(value)
|
43
44
|
when PSBT_IN_TYPES[:witness_utxo]
|
45
|
+
raise ArgumentError, 'Invalid input witness utxo typed key.' unless key_len == 1
|
44
46
|
raise ArgumentError, 'Duplicate Key, input witness utxo already provided.' if input.witness_utxo
|
45
47
|
input.witness_utxo = Bitcoin::TxOut.parse_from_payload(value)
|
46
48
|
when PSBT_IN_TYPES[:partial_sig]
|
@@ -52,21 +54,27 @@ module Bitcoin
|
|
52
54
|
raise ArgumentError, 'Duplicate Key, input partial signature for pubkey already provided.' if input.partial_sigs[pubkey.pubkey]
|
53
55
|
input.partial_sigs[pubkey.pubkey] = value
|
54
56
|
when PSBT_IN_TYPES[:sighash]
|
57
|
+
raise ArgumentError, 'Invalid input sighash type typed key.' unless key_len == 1
|
55
58
|
raise ArgumentError 'Duplicate Key, input sighash type already provided.' if input.sighash_type
|
56
59
|
input.sighash_type = value.unpack('I').first
|
57
60
|
when PSBT_IN_TYPES[:redeem_script]
|
61
|
+
raise ArgumentError, 'Invalid redeemscript typed key.' unless key_len == 1
|
58
62
|
raise ArgumentError, 'Duplicate Key, input redeemScript already provided.' if input.redeem_script
|
59
63
|
input.redeem_script = Bitcoin::Script.parse_from_payload(value)
|
60
64
|
when PSBT_IN_TYPES[:witness_script]
|
65
|
+
raise ArgumentError, 'Invalid witnessscript typed key.' unless key_len == 1
|
61
66
|
raise ArgumentError, 'Duplicate Key, input witnessScript already provided.' if input.witness_script
|
62
67
|
input.witness_script = Bitcoin::Script.parse_from_payload(value)
|
63
68
|
when PSBT_IN_TYPES[:bip32_derivation]
|
69
|
+
raise ArgumentError, 'Invalid bip32 typed key.' unless key_len
|
64
70
|
raise ArgumentError, 'Duplicate Key, pubkey derivation path already provided.' if input.hd_key_paths[key.bth]
|
65
71
|
input.hd_key_paths[key.bth] = Bitcoin::PSBT::HDKeyPath.parse_from_payload(key, value)
|
66
72
|
when PSBT_IN_TYPES[:script_sig]
|
73
|
+
raise ArgumentError, 'Invalid final scriptsig typed key.' unless key_len == 1
|
67
74
|
raise ArgumentError, 'Duplicate Key, input final scriptSig already provided.' if input.final_script_sig
|
68
75
|
input.final_script_sig = Bitcoin::Script.parse_from_payload(value)
|
69
76
|
when PSBT_IN_TYPES[:script_witness]
|
77
|
+
raise ArgumentError, 'Invalid final script witness typed key.' unless key_len == 1
|
70
78
|
raise ArgumentError, 'Duplicate Key, input final scriptWitness already provided.' if input.final_script_witness
|
71
79
|
input.final_script_witness = Bitcoin::ScriptWitness.parse_from_payload(value)
|
72
80
|
else
|
data/lib/bitcoin/psbt/output.rb
CHANGED
@@ -27,9 +27,11 @@ module Bitcoin
|
|
27
27
|
value = buf.read(Bitcoin.unpack_var_int_from_io(buf))
|
28
28
|
case key_type
|
29
29
|
when PSBT_OUT_TYPES[:redeem_script]
|
30
|
+
raise ArgumentError, 'Invalid output redeemScript typed key.' unless key_len == 1
|
30
31
|
raise ArgumentError, 'Duplicate Key, output redeemScript already provided' if output.redeem_script
|
31
32
|
output.redeem_script = value
|
32
33
|
when PSBT_OUT_TYPES[:witness_script]
|
34
|
+
raise ArgumentError, 'Invalid output witnessScript typed key.' unless key_len == 1
|
33
35
|
raise ArgumentError, 'Duplicate Key, output witnessScript already provided' if output.witness_script
|
34
36
|
output.witness_script = value
|
35
37
|
when PSBT_OUT_TYPES[:bip32_derivation]
|
data/lib/bitcoin/psbt/tx.rb
CHANGED
@@ -40,26 +40,27 @@ module Bitcoin
|
|
40
40
|
|
41
41
|
case key_type
|
42
42
|
when PSBT_GLOBAL_TYPES[:unsigned_tx]
|
43
|
-
raise ArgumentError, '
|
43
|
+
raise ArgumentError, 'Invalid global transaction typed key.' unless key_len == 1
|
44
|
+
raise ArgumentError, 'Duplicate Key, unsigned tx already provided.' if partial_tx.tx
|
44
45
|
partial_tx.tx = Bitcoin::Tx.parse_from_payload(value)
|
45
46
|
partial_tx.tx.in.each do |tx_in|
|
46
47
|
raise ArgumentError, 'Unsigned tx does not have empty scriptSigs and scriptWitnesses.' if !tx_in.script_sig.empty? || !tx_in.script_witness.empty?
|
47
48
|
end
|
48
49
|
else
|
49
|
-
raise ArgumentError, 'Duplicate Key, key for unknown value already provided' if partial_tx.unknowns[key]
|
50
|
+
raise ArgumentError, 'Duplicate Key, key for unknown value already provided.' if partial_tx.unknowns[key]
|
50
51
|
partial_tx.unknowns[([key_type].pack('C') + key).bth] = value
|
51
52
|
end
|
52
53
|
end
|
53
54
|
|
54
|
-
raise ArgumentError, 'No unsigned
|
55
|
+
raise ArgumentError, 'No unsigned transaction was provided.' unless partial_tx.tx
|
55
56
|
|
56
57
|
# read input data.
|
57
58
|
partial_tx.tx.in.each do |tx_in|
|
58
59
|
break if buf.eof?
|
59
60
|
input = Input.parse_from_buf(buf)
|
60
61
|
partial_tx.inputs << input
|
61
|
-
if input.non_witness_utxo && input.non_witness_utxo.
|
62
|
-
raise ArgumentError, 'Non-witness UTXO does not match outpoint hash'
|
62
|
+
if input.non_witness_utxo && input.non_witness_utxo.tx_hash != tx_in.prev_hash
|
63
|
+
raise ArgumentError, 'Non-witness UTXO does not match outpoint hash.'
|
63
64
|
end
|
64
65
|
end
|
65
66
|
|
@@ -110,7 +111,7 @@ module Bitcoin
|
|
110
111
|
# @param [Bitcoin::Script] witness_script witness script to set input.
|
111
112
|
# @param [Hash] hd_key_paths bip 32 hd key paths to set input.
|
112
113
|
def update!(prev_tx, redeem_script: nil, witness_script: nil, hd_key_paths: [])
|
113
|
-
prev_hash = prev_tx.
|
114
|
+
prev_hash = prev_tx.tx_hash
|
114
115
|
tx.in.each_with_index do|tx_in, i|
|
115
116
|
if tx_in.prev_hash == prev_hash
|
116
117
|
utxo = prev_tx.out[tx_in.out_point.index]
|
@@ -12,7 +12,7 @@ module Bitcoin
|
|
12
12
|
h[:headers] = best_block.height
|
13
13
|
h[:bestblockhash] = best_block.header.block_id
|
14
14
|
h[:chainwork] = best_block.header.work
|
15
|
-
h[:mediantime] = node.chain.mtp(best_block.
|
15
|
+
h[:mediantime] = node.chain.mtp(best_block.block_hash)
|
16
16
|
h
|
17
17
|
end
|
18
18
|
|
@@ -352,6 +352,11 @@ module Bitcoin
|
|
352
352
|
to_payload.bytesize
|
353
353
|
end
|
354
354
|
|
355
|
+
# execute script interpreter using this script for development.
|
356
|
+
def run
|
357
|
+
Bitcoin::ScriptInterpreter.eval(Bitcoin::Script.new, self.dup)
|
358
|
+
end
|
359
|
+
|
355
360
|
# encode int value to script number hex.
|
356
361
|
# The stacks hold byte vectors.
|
357
362
|
# When used as numbers, byte vectors are interpreted as little-endian variable-length integers
|
@@ -16,14 +16,18 @@ module Bitcoin
|
|
16
16
|
|
17
17
|
# get database key
|
18
18
|
def key
|
19
|
-
Bitcoin::Store::KEY_PREFIX[:entry] + header.
|
19
|
+
Bitcoin::Store::KEY_PREFIX[:entry] + header.block_hash
|
20
20
|
end
|
21
21
|
|
22
|
-
# block hash
|
23
22
|
def hash
|
24
23
|
header.hash
|
25
24
|
end
|
26
25
|
|
26
|
+
# block hash
|
27
|
+
def block_hash
|
28
|
+
header.block_hash
|
29
|
+
end
|
30
|
+
|
27
31
|
# previous block hash
|
28
32
|
def prev_hash
|
29
33
|
header.prev_hash
|
@@ -61,7 +61,7 @@ module Bitcoin
|
|
61
61
|
def save_entry(entry)
|
62
62
|
db.batch do
|
63
63
|
db.put(entry.key ,entry.to_payload)
|
64
|
-
db.put(height_key(entry.height), entry.
|
64
|
+
db.put(height_key(entry.height), entry.block_hash)
|
65
65
|
connect_entry(entry)
|
66
66
|
end
|
67
67
|
end
|
@@ -81,17 +81,15 @@ module Bitcoin
|
|
81
81
|
def connect_entry(entry)
|
82
82
|
unless entry.genesis?
|
83
83
|
tip_block = Bitcoin::Store::ChainEntry.parse_from_payload(get_entry_payload_from_hash(best_hash))
|
84
|
-
unless tip_block.
|
85
|
-
raise "entry(#{entry.
|
84
|
+
unless tip_block.block_hash == entry.prev_hash
|
85
|
+
raise "entry(#{entry.block_hash}) does not reference current best block hash(#{tip_block.block_hash})"
|
86
86
|
end
|
87
87
|
unless tip_block.height + 1 == entry.height
|
88
88
|
raise "block height is small than current best block."
|
89
89
|
end
|
90
90
|
end
|
91
|
-
|
92
|
-
|
93
|
-
db.put(KEY_PREFIX[:best], entry.hash)
|
94
|
-
db.put(KEY_PREFIX[:next] + entry.prev_hash, entry.hash)
|
91
|
+
db.put(KEY_PREFIX[:best], entry.block_hash)
|
92
|
+
db.put(KEY_PREFIX[:next] + entry.prev_hash, entry.block_hash)
|
95
93
|
end
|
96
94
|
end
|
97
95
|
|
@@ -44,17 +44,17 @@ module Bitcoin
|
|
44
44
|
# @return [Bitcoin::Store::ChainEntry] appended block header entry.
|
45
45
|
def append_header(header)
|
46
46
|
logger.info("append header #{header.block_id}")
|
47
|
-
raise "this header is invalid. #{header.
|
47
|
+
raise "this header is invalid. #{header.block_hash}" unless header.valid?
|
48
48
|
best_block = latest_block
|
49
49
|
current_height = best_block.height
|
50
|
-
if best_block.
|
50
|
+
if best_block.block_hash == header.prev_hash
|
51
51
|
entry = Bitcoin::Store::ChainEntry.new(header, current_height + 1)
|
52
52
|
db.save_entry(entry)
|
53
53
|
entry
|
54
54
|
else
|
55
|
-
unless find_entry_by_hash(header.
|
55
|
+
unless find_entry_by_hash(header.block_hash)
|
56
56
|
# TODO implements recovery process
|
57
|
-
raise "header's previous hash(#{header.prev_hash}) does not match current best block's(#{best_block.
|
57
|
+
raise "header's previous hash(#{header.prev_hash}) does not match current best block's(#{best_block.block_hash})."
|
58
58
|
end
|
59
59
|
end
|
60
60
|
end
|
data/lib/bitcoin/tx.rb
CHANGED
@@ -70,11 +70,15 @@ module Bitcoin
|
|
70
70
|
end
|
71
71
|
|
72
72
|
def hash
|
73
|
+
to_payload.bth.to_i(16)
|
74
|
+
end
|
75
|
+
|
76
|
+
def tx_hash
|
73
77
|
Bitcoin.double_sha256(serialize_old_format).bth
|
74
78
|
end
|
75
79
|
|
76
80
|
def txid
|
77
|
-
|
81
|
+
tx_hash.rhex
|
78
82
|
end
|
79
83
|
|
80
84
|
def witness_hash
|
@@ -109,7 +113,7 @@ module Bitcoin
|
|
109
113
|
end
|
110
114
|
|
111
115
|
def ==(other)
|
112
|
-
|
116
|
+
to_payload == other.to_payload
|
113
117
|
end
|
114
118
|
|
115
119
|
# serialize tx with old tx format
|
data/lib/bitcoin/validation.rb
CHANGED
data/lib/bitcoin/version.rb
CHANGED
@@ -5,8 +5,14 @@ module OpenAssets
|
|
5
5
|
# whether this output is marker output for open assets.
|
6
6
|
def open_assets_marker?
|
7
7
|
return false unless script_pubkey.op_return?
|
8
|
-
|
9
|
-
|
8
|
+
!oa_payload.nil?
|
9
|
+
end
|
10
|
+
|
11
|
+
# get open asset payload.
|
12
|
+
# @return [OpenAssets::Payload] open asset payload.
|
13
|
+
def oa_payload
|
14
|
+
return nil unless script_pubkey.op_return?
|
15
|
+
Payload.parse_from_payload(script_pubkey.op_return_data)
|
10
16
|
end
|
11
17
|
|
12
18
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: bitcoinrb
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.2.
|
4
|
+
version: 0.2.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- azuchi
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-
|
11
|
+
date: 2018-09-29 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: ecdsa
|