bitcoin-ruby 0.0.1 → 0.0.2
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +4 -1
- data/Gemfile +21 -0
- data/README.rdoc +85 -25
- data/Rakefile +7 -3
- data/bin/bitcoin_node +39 -42
- data/bin/bitcoin_shell +1 -0
- data/bin/bitcoin_wallet +129 -53
- data/bitcoin-ruby.gemspec +4 -7
- data/concept-examples/blockchain-pow.rb +1 -1
- data/doc/CONFIG.rdoc +5 -5
- data/doc/EXAMPLES.rdoc +9 -5
- data/doc/NAMECOIN.rdoc +34 -0
- data/doc/NODE.rdoc +147 -10
- data/examples/balance.rb +10 -4
- data/examples/bbe_verify_tx.rb +7 -2
- data/examples/forwarder.rb +73 -0
- data/examples/generate_tx.rb +34 -0
- data/examples/simple_network_monitor_and_util.rb +187 -0
- data/examples/verify_tx.rb +1 -1
- data/lib/bitcoin.rb +308 -18
- data/lib/bitcoin/builder.rb +62 -36
- data/lib/bitcoin/config.rb +2 -0
- data/lib/bitcoin/connection.rb +11 -8
- data/lib/bitcoin/electrum/mnemonic.rb +162 -0
- data/lib/bitcoin/ffi/openssl.rb +187 -21
- data/lib/bitcoin/gui/addr_view.rb +2 -0
- data/lib/bitcoin/gui/conn_view.rb +2 -0
- data/lib/bitcoin/gui/connection.rb +2 -0
- data/lib/bitcoin/gui/em_gtk.rb +2 -0
- data/lib/bitcoin/gui/gui.rb +2 -0
- data/lib/bitcoin/gui/helpers.rb +2 -0
- data/lib/bitcoin/gui/tree_view.rb +2 -0
- data/lib/bitcoin/gui/tx_view.rb +2 -0
- data/lib/bitcoin/key.rb +77 -11
- data/lib/bitcoin/litecoin.rb +81 -0
- data/lib/bitcoin/logger.rb +20 -1
- data/lib/bitcoin/namecoin.rb +279 -0
- data/lib/bitcoin/network/command_client.rb +7 -6
- data/lib/bitcoin/network/command_handler.rb +229 -43
- data/lib/bitcoin/network/connection_handler.rb +182 -70
- data/lib/bitcoin/network/node.rb +231 -106
- data/lib/bitcoin/protocol.rb +44 -23
- data/lib/bitcoin/protocol/address.rb +5 -3
- data/lib/bitcoin/protocol/alert.rb +3 -4
- data/lib/bitcoin/protocol/aux_pow.rb +123 -0
- data/lib/bitcoin/protocol/block.rb +98 -18
- data/lib/bitcoin/protocol/handler.rb +6 -5
- data/lib/bitcoin/protocol/parser.rb +44 -19
- data/lib/bitcoin/protocol/tx.rb +105 -52
- data/lib/bitcoin/protocol/txin.rb +39 -19
- data/lib/bitcoin/protocol/txout.rb +28 -13
- data/lib/bitcoin/protocol/version.rb +16 -7
- data/lib/bitcoin/script.rb +579 -122
- data/lib/bitcoin/storage/{dummy.rb → dummy/dummy_store.rb} +8 -14
- data/lib/bitcoin/storage/models.rb +20 -7
- data/lib/bitcoin/storage/{sequel_store/sequel_migrations.rb → sequel/migrations.rb} +22 -7
- data/lib/bitcoin/storage/sequel/migrations/001_base_schema.rb +52 -0
- data/lib/bitcoin/storage/sequel/migrations/002_tx.rb +50 -0
- data/lib/bitcoin/storage/sequel/migrations/003_change_txin_script_sig_to_blob.rb +18 -0
- data/lib/bitcoin/storage/sequel/sequel_store.rb +436 -0
- data/lib/bitcoin/storage/storage.rb +233 -28
- data/lib/bitcoin/storage/utxo/migrations/001_base_schema.rb +52 -0
- data/lib/bitcoin/storage/utxo/migrations/002_utxo.rb +18 -0
- data/lib/bitcoin/storage/utxo/utxo_store.rb +361 -0
- data/lib/bitcoin/validation.rb +369 -0
- data/lib/bitcoin/version.rb +1 -1
- data/lib/bitcoin/wallet/coinselector.rb +3 -0
- data/lib/bitcoin/wallet/keygenerator.rb +3 -1
- data/lib/bitcoin/wallet/keystore.rb +6 -2
- data/lib/bitcoin/wallet/txdp.rb +6 -4
- data/lib/bitcoin/wallet/wallet.rb +54 -16
- data/spec/bitcoin/bitcoin_spec.rb +48 -3
- data/spec/bitcoin/builder_spec.rb +40 -17
- data/spec/bitcoin/fixtures/000000000000056b1a3d84a1e2b33cde8915a4b61c0cae14fca6d3e1490b4f98.json +3697 -0
- data/spec/bitcoin/fixtures/03d7e1fa4d5fefa169431f24f7798552861b255cd55d377066fedcd088fb0e99.json +23 -0
- data/spec/bitcoin/fixtures/0961c660358478829505e16a1f028757e54b5bbf9758341a7546573738f31429.json +24 -0
- data/spec/bitcoin/fixtures/0f24294a1d23efbb49c1765cf443fba7930702752aba6d765870082fe4f13cae.json +37 -0
- data/spec/bitcoin/fixtures/315ac7d4c26d69668129cc352851d9389b4a6868f1509c6c8b66bead11e2619f.json +31 -0
- data/spec/bitcoin/fixtures/35e2001b428891fefa0bfb73167c7360669d3cbd7b3aa78e7cad125ddfc51131.json +27 -0
- data/spec/bitcoin/fixtures/3a17dace09ffb919ed627a93f1873220f4c975c1248558b18d16bce25d38c4b7.json +72 -0
- data/spec/bitcoin/fixtures/3e58b7eed0fdb599019af08578effea25c8666bbe8e200845453cacce6314477.json +27 -0
- data/spec/bitcoin/fixtures/514c46f0b61714092f15c8dfcb576c9f79b3f959989b98de3944b19d98832b58.json +24 -0
- data/spec/bitcoin/fixtures/51bf528ecf3c161e7c021224197dbe84f9a8564212f6207baa014c01a1668e1e.json +30 -0
- data/spec/bitcoin/fixtures/69216b8aaa35b76d6613e5f527f4858640d986e1046238583bdad79b35e938dc.json +28 -0
- data/spec/bitcoin/fixtures/7208e5edf525f04e705fb3390194e316205b8f995c8c9fcd8c6093abe04fa27d.json +27 -0
- data/spec/bitcoin/fixtures/761d8c5210fdfd505f6dff38f740ae3728eb93d7d0971fb433f685d40a4c04f6.json +27 -0
- data/spec/bitcoin/fixtures/aea682d68a3ea5e3583e088dcbd699a5d44d4b083f02ad0aaf2598fe1fa4dfd4.json +27 -0
- data/spec/bitcoin/fixtures/bd1715f1abfdc62bea3f605bdb461b3ba1f2cca6ec0d73a18a548b7717ca8531.json +34 -0
- data/spec/bitcoin/fixtures/block-testnet-0000000000ac85bb2530a05a4214a387e6be02b22d3348abc5e7a5d9c4ce8dab.bin +0 -0
- data/spec/bitcoin/fixtures/cd874fa8cb0e2ec2d385735d5e1fd482c4fe648533efb4c50ee53bda58e15ae2.json +24 -0
- data/spec/bitcoin/fixtures/ce5fad9b4ef094d8f4937b0707edaf0a6e6ceeaf67d5edbfd51f660eac8f398b.json +41 -0
- data/spec/bitcoin/fixtures/f003f0c1193019db2497a675fd05d9f2edddf9b67c59e677c48d3dbd4ed5f00b.json +23 -0
- data/spec/bitcoin/fixtures/freicoin-block-000000005d231b285e63af83edae2d8f5e50e70d396468643092b9239fd3be3c.bin +0 -0
- data/spec/bitcoin/fixtures/freicoin-block-000000005d231b285e63af83edae2d8f5e50e70d396468643092b9239fd3be3c.json +43 -0
- data/spec/bitcoin/fixtures/freicoin-genesis-block-000000005b1e3d23ecfd2dd4a6e1a35238aa0392c0a8528c40df52376d7efe2c.bin +0 -0
- data/spec/bitcoin/fixtures/freicoin-genesis-block-000000005b1e3d23ecfd2dd4a6e1a35238aa0392c0a8528c40df52376d7efe2c.json +67 -0
- data/spec/bitcoin/fixtures/litecoin-block-80ca095ed10b02e53d769eb6eaf92cd04e9e0759e5be4a8477b42911ba49c78f.bin +0 -0
- data/spec/bitcoin/fixtures/litecoin-block-80ca095ed10b02e53d769eb6eaf92cd04e9e0759e5be4a8477b42911ba49c78f.json +39 -0
- data/spec/bitcoin/fixtures/litecoin-genesis-block-12a765e31ffd4059bada1e25190f6e98c99d9714d334efa41a195a7e7e04bfe2.bin +0 -0
- data/spec/bitcoin/fixtures/litecoin-genesis-block-12a765e31ffd4059bada1e25190f6e98c99d9714d334efa41a195a7e7e04bfe2.json +39 -0
- data/spec/bitcoin/fixtures/rawblock-auxpow.bin +0 -0
- data/spec/bitcoin/fixtures/tx-313897799b1e37e9ecae15010e56156dddde4e683c96b0e713af95272c38aee0.json +30 -0
- data/spec/bitcoin/fixtures/tx-3da75972766f0ad13319b0b461fd16823a731e44f6e9de4eb3c52d6a6fb6c8ae.json +23 -0
- data/spec/bitcoin/fixtures/tx-44b833074e671120ba33106877b49e86ece510824b9af477a3853972bcd8d06a.json +30 -0
- data/spec/bitcoin/fixtures/tx-d3d77d63709e47d9ef58f0b557800115a6b676c6a423012fbb96f45d8fcef830.json +28 -0
- data/spec/bitcoin/key_spec.rb +128 -3
- data/spec/bitcoin/namecoin_spec.rb +182 -0
- data/spec/bitcoin/network_spec.rb +5 -3
- data/spec/bitcoin/node/command_api_spec.rb +376 -0
- data/spec/bitcoin/protocol/addr_spec.rb +2 -0
- data/spec/bitcoin/protocol/alert_spec.rb +2 -0
- data/spec/bitcoin/protocol/aux_pow_spec.rb +44 -0
- data/spec/bitcoin/protocol/block_spec.rb +134 -39
- data/spec/bitcoin/protocol/getblocks_spec.rb +32 -0
- data/spec/bitcoin/protocol/inv_spec.rb +10 -8
- data/spec/bitcoin/protocol/notfound_spec.rb +31 -0
- data/spec/bitcoin/protocol/ping_spec.rb +2 -0
- data/spec/bitcoin/protocol/tx_spec.rb +83 -17
- data/spec/bitcoin/protocol/version_spec.rb +7 -5
- data/spec/bitcoin/script/opcodes_spec.rb +412 -133
- data/spec/bitcoin/script/script_spec.rb +112 -13
- data/spec/bitcoin/spec_helper.rb +68 -0
- data/spec/bitcoin/storage/reorg_spec.rb +199 -0
- data/spec/bitcoin/storage/storage_spec.rb +337 -0
- data/spec/bitcoin/storage/validation_spec.rb +261 -0
- data/spec/bitcoin/wallet/coinselector_spec.rb +10 -7
- data/spec/bitcoin/wallet/keygenerator_spec.rb +2 -0
- data/spec/bitcoin/wallet/keystore_spec.rb +2 -0
- data/spec/bitcoin/wallet/txdp_spec.rb +2 -0
- data/spec/bitcoin/wallet/wallet_spec.rb +91 -58
- metadata +105 -51
- data/lib/bitcoin/storage/sequel.rb +0 -335
- data/spec/bitcoin/fixtures/0d0affb5964abe804ffe85e53f1dbb9f29e406aa3046e2db04fba240e63c7fdd.json +0 -27
- data/spec/bitcoin/fixtures/477fff140b363ec2cc51f3a65c0c58eda38f4d41f04a295bbd62babf25e4c590.json +0 -27
- data/spec/bitcoin/reorg_spec.rb +0 -129
- data/spec/bitcoin/storage_spec.rb +0 -229
data/bitcoin-ruby.gemspec
CHANGED
@@ -8,8 +8,9 @@ Gem::Specification.new do |s|
|
|
8
8
|
s.authors = ["lian"]
|
9
9
|
s.email = ["meta.rb@gmail.com"]
|
10
10
|
s.homepage = ""
|
11
|
-
s.summary = %q{
|
12
|
-
s.description = %q{
|
11
|
+
s.summary = %q{bitcoin utils and protocol in ruby}
|
12
|
+
s.description = %q{This is a ruby library for interacting with the bitcoin protocol/network}
|
13
|
+
s.homepage = "https://github.com/lian/bitcoin-ruby"
|
13
14
|
|
14
15
|
s.rubyforge_project = "bitcoin-ruby"
|
15
16
|
|
@@ -19,9 +20,5 @@ Gem::Specification.new do |s|
|
|
19
20
|
s.require_paths = ["lib"]
|
20
21
|
|
21
22
|
s.required_rubygems_version = ">= 1.3.6"
|
22
|
-
s.
|
23
|
-
s.add_dependency "eventmachine"
|
24
|
-
|
25
|
-
s.add_development_dependency "bacon"
|
26
|
-
|
23
|
+
#s.add_development_dependency "bacon"
|
27
24
|
end
|
data/doc/CONFIG.rdoc
CHANGED
@@ -6,9 +6,9 @@ All commands accept configuration, either via config file, or at the command lin
|
|
6
6
|
|
7
7
|
There are 3 default locations where configfiles are loaded from:
|
8
8
|
|
9
|
-
*
|
10
|
-
*
|
11
|
-
*
|
9
|
+
* /etc/bitcoin-ruby.yml
|
10
|
+
* ~/.bitcoin-ruby.yml
|
11
|
+
* ./bitcoin-ruby.yml
|
12
12
|
|
13
13
|
Files are loaded in order (if they exist) and override each others settings.
|
14
14
|
|
@@ -42,7 +42,7 @@ from the +all+ category (ie. +bitcoin_wallet+ loads +all+ and +wallet+).
|
|
42
42
|
command: "127.0.0.1:9999" # IP:Port to listen for incomming command connections
|
43
43
|
listen: "0.0.0.0:8332" # IP:Port to listen for incoming peer connections
|
44
44
|
connect: "" # List of IP:Port,IP:Port of nodes to connect to
|
45
|
-
storage: "sequel::sqlite
|
45
|
+
storage: "sequel::sqlite://~/.bitcoin-ruby/<network>/blocks.db" # storage backend to use (see STORAGE)
|
46
46
|
node:
|
47
47
|
headers_only: false # download/store only block headers (experimental)
|
48
48
|
dns: true # query peers from dns server
|
@@ -63,4 +63,4 @@ from the +all+ category (ie. +bitcoin_wallet+ loads +all+ and +wallet+).
|
|
63
63
|
addrs: 15 # collect new peer addrs
|
64
64
|
connect: 30 # connect to new peers
|
65
65
|
wallet:
|
66
|
-
keystore: "simple::file=~/.bitcoin-ruby
|
66
|
+
keystore: "simple::file=~/.bitcoin-ruby/<network>/keys.json" # keystore to use
|
data/doc/EXAMPLES.rdoc
CHANGED
@@ -2,8 +2,12 @@
|
|
2
2
|
|
3
3
|
There are a few demo scripts in `examples/` that might give you an idea where to start.
|
4
4
|
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
5
|
+
connect.rb:: Connect to a network node and chat a little.
|
6
|
+
verify_tx.rb:: Fetch a transaction from local storage and verify signatures.
|
7
|
+
bbe_verify_tx.rb:: Fetch transaction from blockexplorer.com and verify signatures.
|
8
|
+
balance.rb:: Display balance/transactions for given address.
|
9
|
+
relay_tx.rb:: Relay transaction to the network.
|
10
|
+
generate_tx.rb:: Create a transaction.
|
11
|
+
validate_tx.rb:: Verify transaction signatures.
|
12
|
+
simple_network_monitor_and_util:: Connects to the network and lets you monitor and query blocks/txs.
|
13
|
+
forwarder.rb:: Waits for tx sent to your address and forwards them to another address.
|
data/doc/NAMECOIN.rdoc
ADDED
@@ -0,0 +1,34 @@
|
|
1
|
+
= Namecoin
|
2
|
+
|
3
|
+
Namecoin is almost fully supported.
|
4
|
+
* connect to the network,
|
5
|
+
* store and query the blockchain
|
6
|
+
* transact NMC
|
7
|
+
* create/handle name_new/first/update transaction types
|
8
|
+
|
9
|
+
The AuxPow is parsed from the block header, the only thing missing is actually verifying it.
|
10
|
+
|
11
|
+
== Usage
|
12
|
+
|
13
|
+
It should suffice to just set the network to :namecoin when running the node/wallet.
|
14
|
+
|
15
|
+
bitcoin_node -n namecoin
|
16
|
+
|
17
|
+
bitcoin_wallet -n namecoin list
|
18
|
+
bitcoin_wallet -n namecoin send address:NCme95FewQEjTeBhBfXTyqjz1GTxw4bo56:1.0 0.1
|
19
|
+
|
20
|
+
bitcoin_wallet -n namecoin name_show d/bitcoin
|
21
|
+
bitcoin_wallet -n namecoin name_history d/bitcoin
|
22
|
+
|
23
|
+
bitcoin_wallet -n namecoin name_new d/bitcoin
|
24
|
+
bitcoin_wallet -n namecoin name_firstupdate d/bitcoin abcdef '{"foo": "bar"}'
|
25
|
+
bitcoin_wallet -n namecoin name_update d/bitcoin '{"bar": "baz"}'
|
26
|
+
bitcoin_wallet -n namecoin name_update d/bitcoin 'transferring...' NCme95FewQEjTeBhBfXTyqjz1GTxw4bo56
|
27
|
+
|
28
|
+
== Implementation Details
|
29
|
+
|
30
|
+
All the differences from regular bitcoin behaviour should be in separate modules inside
|
31
|
+
Bitcoin::Namecoin. (this is still a work in progress)
|
32
|
+
|
33
|
+
The AuxPow parsing is implemented in the Bitcoin::Protocol/::Block, because there might
|
34
|
+
be other altchains using it one day.
|
data/doc/NODE.rdoc
CHANGED
@@ -11,25 +11,162 @@ using the sequel::sqlite3 STORAGE backend):
|
|
11
11
|
|
12
12
|
You can specify options (see +--help+) or pass a config file with +--config+ (see CONFIG).
|
13
13
|
|
14
|
-
Some common options you might want to
|
14
|
+
Some common options you might want to use:
|
15
15
|
|
16
16
|
<tt>-n --network</tt> <i><name></i>::
|
17
|
-
+bitcoin
|
17
|
+
Network to use. Usually +bitcoin+. Support for +namecoin+ is also quite good.
|
18
|
+
Use +testnet+ for development.
|
19
|
+
|
20
|
+
<tt>-c --config</tt> <i><file></i>::
|
21
|
+
Read options from config file. See also CONFIG.
|
22
|
+
|
18
23
|
<tt>--connect</tt> <i><ip:port></i>::
|
19
|
-
|
24
|
+
List of peers to connect to.
|
25
|
+
|
20
26
|
<tt>-s --storage</tt> <i><backend-string></i>::
|
21
|
-
|
27
|
+
Storage backend to use. See also STORAGE.
|
28
|
+
|
29
|
+
<tt>--import</tt> <i><blockchain dir></i>::
|
30
|
+
Import blockchain in bitcoind/qt format from given directory.
|
31
|
+
|
32
|
+
<tt>--skip-validation</tt>::
|
33
|
+
Skip validation of received blockchain data. Can be used to speed up import/sync when
|
34
|
+
blockchain data is received from a trusted source.
|
35
|
+
|
36
|
+
<tt>--check-blocks <i><count></i>::
|
37
|
+
Check consistency of the +count+ most recent blocks. Pass -1 to check all blocks.
|
38
|
+
|
39
|
+
<tt>-v --verbose</tt>::
|
40
|
+
Display debug output.
|
41
|
+
|
42
|
+
<tt>-h --help</tt>::
|
43
|
+
Display all available options.
|
22
44
|
|
23
|
-
It will take
|
45
|
+
It will take a long time to download/store the entire blockchain at first, so be patient ;)
|
24
46
|
|
25
47
|
|
26
|
-
== Command
|
48
|
+
== Command socket
|
27
49
|
|
28
50
|
The node opens a separate command socket which you can connect to and query statistics
|
29
|
-
or get notified about new blocks/tx, etc.
|
51
|
+
or get notified about new blocks/tx, etc. See below for a list of available commands.
|
52
|
+
|
53
|
+
=== CLI interface
|
54
|
+
|
55
|
+
The easiest way is to just call `bitcoin_node` again in the same way you started it,
|
56
|
+
but with an extra command argument:
|
57
|
+
|
58
|
+
bitcoin_node info
|
59
|
+
bitcoin_node -c config.yml info
|
60
|
+
bitcoin_node monitor "block tx"
|
61
|
+
|
62
|
+
|
63
|
+
=== CommandClient
|
64
|
+
|
65
|
+
If you are programming in an EventMachine context, you might find the
|
66
|
+
Bitcoin::Network::CommandClient convenient.
|
67
|
+
|
68
|
+
=== Raw socket
|
69
|
+
|
70
|
+
Of course you can also connect to the socket by any other means you like, just
|
71
|
+
send [<command>, <params>] pairs and receive [<command>, <response>] pairs back (both
|
72
|
+
encoded in JSON):
|
73
|
+
|
74
|
+
$ echo -e '["tslb", []]\0' | nc 127.0.0.1 9999
|
75
|
+
["tslb",{"tslb":2700}]
|
76
|
+
|
77
|
+
|
78
|
+
=== Commands
|
79
|
+
|
80
|
+
==== info
|
81
|
+
|
82
|
+
Get various statistics.
|
83
|
+
|
84
|
+
bitcoin_node info
|
85
|
+
|
86
|
+
==== config
|
87
|
+
|
88
|
+
Get the currently active configuration.
|
89
|
+
|
90
|
+
bitcoin_node config
|
91
|
+
|
92
|
+
==== connections
|
93
|
+
|
94
|
+
Get currently connected peers.
|
95
|
+
|
96
|
+
bitcoin_node connections
|
97
|
+
|
98
|
+
==== connect
|
99
|
+
|
100
|
+
Connect to given peer(s).
|
101
|
+
|
102
|
+
bitcoin_node connect <ip>:<port>[,<ip>:<port>]
|
103
|
+
|
104
|
+
==== disconnect
|
105
|
+
|
106
|
+
Disconnect given peer(s).
|
107
|
+
|
108
|
+
bitcoin_node disconnect <ip>:<port>[,<ip>,<port>]
|
109
|
+
|
110
|
+
==== getblocks
|
111
|
+
|
112
|
+
Trigger the node to ask its peers for new blocks.
|
113
|
+
|
114
|
+
bitcoin_node getblocks
|
115
|
+
|
116
|
+
==== getaddr
|
117
|
+
|
118
|
+
Trigger the node to ask its for new peer addresses.
|
119
|
+
|
120
|
+
bitcoin_node getaddr
|
121
|
+
|
122
|
+
==== addrs
|
123
|
+
|
124
|
+
Get known peer addresses (used by bin/bitcoin_dns_seed)
|
125
|
+
|
126
|
+
bitcoin_node addrs [count]
|
127
|
+
|
128
|
+
==== tslb
|
129
|
+
|
130
|
+
Get Time Since Last Block.
|
131
|
+
|
132
|
+
bitcoin_node tslb
|
133
|
+
|
134
|
+
==== create_tx
|
135
|
+
|
136
|
+
TODO
|
137
|
+
|
138
|
+
==== assemble_tx
|
139
|
+
|
140
|
+
TODO
|
141
|
+
|
142
|
+
==== relay_tx
|
143
|
+
|
144
|
+
Relay given transaction (in hex).
|
145
|
+
|
146
|
+
bitcoin_node relay_tx <tx in hex>
|
147
|
+
|
148
|
+
==== store_block
|
149
|
+
|
150
|
+
Validate and store given block (in hex) as if it was received by a peer.
|
151
|
+
|
152
|
+
bitcoin_node store_block <block in hex>
|
153
|
+
|
154
|
+
==== store_tx
|
155
|
+
|
156
|
+
Store given transaction (in hex) as if it was received by a peer.
|
157
|
+
|
158
|
+
bitcoin_node store_tx <tx in hex>
|
159
|
+
|
160
|
+
==== stop
|
161
|
+
|
162
|
+
Stop the bitcoin node.
|
163
|
+
|
164
|
+
bitcoin_node stop
|
165
|
+
|
166
|
+
==== help
|
167
|
+
|
168
|
+
List all available commands.
|
30
169
|
|
31
|
-
bitcoin_node
|
170
|
+
bitcoin_node help
|
32
171
|
|
33
|
-
bitcoin_node help # list all commands
|
34
172
|
|
35
|
-
bitcoin_node monitor block # wait for new blocks and output their hashes
|
data/examples/balance.rb
CHANGED
@@ -15,7 +15,7 @@ store = Bitcoin::Storage.sequel(:db => "sqlite://bitcoin.db")
|
|
15
15
|
address = ARGV.shift
|
16
16
|
|
17
17
|
unless Bitcoin.valid_address?(address)
|
18
|
-
puts "Address #{address} is invalid."
|
18
|
+
puts "Address #{address} is invalid for #{Bitcoin.network_name} network."
|
19
19
|
exit 1
|
20
20
|
end
|
21
21
|
|
@@ -38,8 +38,14 @@ if ARGV[0] == "--list"
|
|
38
38
|
total += txout.value
|
39
39
|
puts "#{tx.hash} |#{str_val(txout.value, '+ ')} |=> #{str_val(total)}"
|
40
40
|
|
41
|
-
txout.get_tx
|
42
|
-
|
41
|
+
tx = txout.get_tx
|
42
|
+
if tx.is_coinbase?
|
43
|
+
puts " "*12 + "generated (#{tx.get_block.hash})"
|
44
|
+
else
|
45
|
+
tx.in.each do |txin|
|
46
|
+
addresses = txin.get_prev_out.get_addresses.join(", ")
|
47
|
+
puts " #{str_val(txin.get_prev_out.value)} from #{addresses}"
|
48
|
+
end
|
43
49
|
end
|
44
50
|
puts
|
45
51
|
|
@@ -48,7 +54,7 @@ if ARGV[0] == "--list"
|
|
48
54
|
total -= txout.value
|
49
55
|
puts "#{tx.hash} |#{str_val(txout.value, '- ')} |=> #{str_val(total)}"
|
50
56
|
txin.get_tx.out.each do |out|
|
51
|
-
puts " to #{out.get_addresses.join(", ")}"
|
57
|
+
puts " #{str_val(out.value)} to #{out.get_addresses.join(", ")}"
|
52
58
|
end
|
53
59
|
puts
|
54
60
|
end
|
data/examples/bbe_verify_tx.rb
CHANGED
@@ -11,11 +11,16 @@ require 'bitcoin'
|
|
11
11
|
require 'open-uri'
|
12
12
|
|
13
13
|
tx_hash = ARGV[0]
|
14
|
-
$testnet = ARGV[
|
14
|
+
$testnet = ARGV.select{|i| i.downcase == 'testnet' }[0] ? true : false
|
15
|
+
$use_coinbase_bbe = ARGV.select{|i| i.downcase == 'coinbase' }[0] ? true : false
|
15
16
|
|
16
17
|
# fetch transaction from bbe as json and deserialize into Bitcoin::Protocol::Tx object
|
17
18
|
def get_tx(hash)
|
18
|
-
|
19
|
+
if $use_coinbase_bbe && !$testnet
|
20
|
+
url = "https://coinbase.com/network/tx/%s.json" % [hash]
|
21
|
+
else
|
22
|
+
url = "http://blockexplorer.com/%srawtx/%s" % [$testnet ? 'testnet/' : '', hash]
|
23
|
+
end
|
19
24
|
json = open(url).read
|
20
25
|
Bitcoin::Protocol::Tx.from_json(json)
|
21
26
|
rescue Exception
|
@@ -0,0 +1,73 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
#
|
3
|
+
# Connect to a node's command socket, monitor incoming payments to one address
|
4
|
+
# and forward everything to another address.
|
5
|
+
# Needs the private key of the receiving address (to sign new tx) and the forwarding
|
6
|
+
# address where payments are sent to.
|
7
|
+
# Note how the private key does NOT have to be passed to the node, we just sign the
|
8
|
+
# sig_hash ourselves.
|
9
|
+
#
|
10
|
+
# examples/forwarder.rb <base58_privkey> <forwarding_address>
|
11
|
+
# examples/forwarder.rb KyZsiZiFyewBswJpdYywz4b5sif252iN5zZQjGzPVVgAsGYyMk8a 12bL22Pynmp7pDtDqD2w9iP7dRzdM1gNUd
|
12
|
+
|
13
|
+
$:.unshift( File.expand_path("../../lib", __FILE__) )
|
14
|
+
require 'eventmachine'
|
15
|
+
require 'bitcoin'
|
16
|
+
|
17
|
+
Bitcoin.network = :testnet3
|
18
|
+
|
19
|
+
EM.run do
|
20
|
+
|
21
|
+
# key/address where people can send money
|
22
|
+
KEY = Bitcoin::Key.from_base58(ARGV[0])
|
23
|
+
|
24
|
+
# address where received money is forwarded to
|
25
|
+
FORWARD = ARGV[1]
|
26
|
+
|
27
|
+
# number of confirmations tx need before being forwarded
|
28
|
+
CONFIRMATIONS = 1
|
29
|
+
|
30
|
+
# list of already forwarded txs, to prevent duplicates
|
31
|
+
FORWARDED_TXS = []
|
32
|
+
|
33
|
+
Bitcoin::Network::CommandClient.connect("127.0.0.1", 9999) do
|
34
|
+
|
35
|
+
on_connected do
|
36
|
+
request("monitor", "output", "output_#{CONFIRMATIONS}")
|
37
|
+
|
38
|
+
puts "Running bitcoin forwarder on address #{KEY.addr}."
|
39
|
+
puts "Forwarding every incoming payment to #{FORWARD}."
|
40
|
+
end
|
41
|
+
|
42
|
+
on_output do |tx_hash, recipient_addr, value, confirmations|
|
43
|
+
if recipient_addr == KEY.addr
|
44
|
+
if confirmations >= CONFIRMATIONS
|
45
|
+
next if FORWARDED_TXS.include?(tx_hash)
|
46
|
+
FORWARDED_TXS << tx_hash
|
47
|
+
puts "Payment of #{value.to_f/1e8} BTC confirmed. Forwarding..."
|
48
|
+
|
49
|
+
# Note: We could also pass KEY.priv instead of KEY.addr here.
|
50
|
+
# Then we would get the complete tx in one step without calling "assemble_tx".
|
51
|
+
request("create_tx", [KEY.addr], [[FORWARD, value]])
|
52
|
+
else
|
53
|
+
puts "Received unconfirmed payment of #{value.to_f/1e8} BTC."
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
on_create_tx do |unsigned_tx, sig_hashes|
|
59
|
+
sig_pubkeys = sig_hashes.map do |sig_hash, address|
|
60
|
+
[KEY.sign(sig_hash.htb).hth, KEY.pub]
|
61
|
+
end
|
62
|
+
request("assemble_tx", unsigned_tx, sig_pubkeys)
|
63
|
+
end
|
64
|
+
|
65
|
+
on_assemble_tx do |tx_in_hex|
|
66
|
+
tx = Bitcoin::P::Tx.new(tx_in_hex.htb)
|
67
|
+
puts "Relaying tx #{tx.hash}..."
|
68
|
+
request("relay_tx", tx_in_hex)
|
69
|
+
end
|
70
|
+
|
71
|
+
end
|
72
|
+
|
73
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
$:.unshift( File.expand_path("../../lib", __FILE__) )
|
2
|
+
require 'bitcoin'
|
3
|
+
|
4
|
+
# p Bitcoin.generate_address # returns address, privkey, pubkey, hash160
|
5
|
+
|
6
|
+
prev_tx = Bitcoin::Protocol::Tx.from_json_file('baedb362adba39753a7d2c58fd3dc4897a1b479859f707a819f096696f3facad.json') # <- redeeming transaction input fetchted by for example simple_network_monitor_and_util.rb
|
7
|
+
prev_tx_output_index = 0
|
8
|
+
value = prev_tx.outputs[prev_tx_output_index].value
|
9
|
+
#value = 1337 # maybe change the value (eg subtract for fees)
|
10
|
+
|
11
|
+
|
12
|
+
tx = Bitcoin::Protocol::Tx.new
|
13
|
+
tx.add_in Bitcoin::Protocol::TxIn.new(prev_tx.binary_hash, prev_tx_output_index, 0)
|
14
|
+
|
15
|
+
tx.add_out Bitcoin::Protocol::TxOut.value_to_address(value, "1MiQ3zD3hzZBZ4cUDfPd8Eqnjcedkwt5jy") # <- dest address (our donation address)
|
16
|
+
|
17
|
+
# if all in and outputs are defined, start signing inputs.
|
18
|
+
key = Bitcoin.open_key("9b2f08ebc186d435ffc1d10f3627f05ce4b983b72c76b0aee4fcce99e57b0342") # <- privkey
|
19
|
+
sig = Bitcoin.sign_data(key, tx.signature_hash_for_input(0, prev_tx))
|
20
|
+
tx.in[0].script_sig = Bitcoin::Script.to_signature_pubkey_script(sig, [key.public_key_hex].pack("H*"))
|
21
|
+
#tx.in[0].add_signature_pubkey_script(sig, key.public_key_hex)
|
22
|
+
|
23
|
+
# finish check
|
24
|
+
tx = Bitcoin::Protocol::Tx.new( tx.to_payload )
|
25
|
+
p tx.hash
|
26
|
+
p tx.verify_input_signature(0, prev_tx) == true
|
27
|
+
|
28
|
+
puts "json:\n"
|
29
|
+
puts tx.to_json # json
|
30
|
+
puts "\nhex:\n"
|
31
|
+
puts tx.to_payload.unpack("H*")[0] # hex binary
|
32
|
+
|
33
|
+
# use this json file for example with `ruby simple_network_monitor_and_util.rb send_tx=<filename>` to push/send it to the network
|
34
|
+
File.open(tx.hash + ".json", 'wb'){|f| f.print tx.to_json }
|