bitcoinrb 1.12.0 → 1.13.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.
Files changed (67) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ruby.yml +1 -1
  3. data/bitcoinrb.gemspec +1 -6
  4. data/lib/bitcoin/bip321_uri.rb +3 -6
  5. data/lib/bitcoin/bip324/fs_chacha20.rb +4 -6
  6. data/lib/bitcoin/bip324/fs_chacha_poly1305.rb +20 -17
  7. data/lib/bitcoin/bip324.rb +3 -1
  8. data/lib/bitcoin/descriptor/checksum.rb +6 -2
  9. data/lib/bitcoin/descriptor/expression.rb +2 -2
  10. data/lib/bitcoin/descriptor/sp.rb +219 -0
  11. data/lib/bitcoin/descriptor.rb +20 -0
  12. data/lib/bitcoin/ext_key.rb +11 -7
  13. data/lib/bitcoin/key.rb +1 -1
  14. data/lib/bitcoin/message/cf_parser.rb +2 -2
  15. data/lib/bitcoin/message/fee_filter.rb +2 -2
  16. data/lib/bitcoin/message/header_and_short_ids.rb +4 -4
  17. data/lib/bitcoin/message/inventory.rb +1 -1
  18. data/lib/bitcoin/message/network_addr.rb +7 -3
  19. data/lib/bitcoin/message/ping.rb +5 -3
  20. data/lib/bitcoin/message/pong.rb +2 -2
  21. data/lib/bitcoin/message/send_cmpct.rb +2 -2
  22. data/lib/bitcoin/message/version.rb +4 -4
  23. data/lib/bitcoin/message.rb +12 -2
  24. data/lib/bitcoin/message_sign.rb +98 -38
  25. data/lib/bitcoin/mnemonic.rb +9 -4
  26. data/lib/bitcoin/psbt/input.rb +51 -33
  27. data/lib/bitcoin/psbt/key_origin_info.rb +2 -2
  28. data/lib/bitcoin/psbt/output.rb +9 -5
  29. data/lib/bitcoin/psbt/tx.rb +16 -10
  30. data/lib/bitcoin/psbt.rb +1 -1
  31. data/lib/bitcoin/rpc.rb +0 -2
  32. data/lib/bitcoin/script/script.rb +14 -4
  33. data/lib/bitcoin/secp256k1/rfc6979.rb +6 -3
  34. data/lib/bitcoin/sighash_generator.rb +2 -2
  35. data/lib/bitcoin/silent_payment/output.rb +46 -0
  36. data/lib/bitcoin/silent_payment.rb +113 -12
  37. data/lib/bitcoin/taproot/control_block.rb +1 -0
  38. data/lib/bitcoin/tx.rb +8 -6
  39. data/lib/bitcoin/tx_out.rb +2 -2
  40. data/lib/bitcoin/util.rb +5 -5
  41. data/lib/bitcoin/version.rb +1 -1
  42. data/lib/bitcoin/wallet/account.rb +2 -2
  43. data/lib/bitcoin/wallet/db.rb +3 -3
  44. data/lib/bitcoin/wallet/master_key.rb +2 -2
  45. data/lib/bitcoin/wallet/utxo.rb +2 -2
  46. data/lib/bitcoin.rb +1 -6
  47. metadata +18 -108
  48. data/exe/bitcoinrb-cli +0 -5
  49. data/exe/bitcoinrbd +0 -46
  50. data/lib/bitcoin/network/connection.rb +0 -73
  51. data/lib/bitcoin/network/message_handler.rb +0 -243
  52. data/lib/bitcoin/network/peer.rb +0 -228
  53. data/lib/bitcoin/network/peer_discovery.rb +0 -42
  54. data/lib/bitcoin/network/pool.rb +0 -135
  55. data/lib/bitcoin/network.rb +0 -13
  56. data/lib/bitcoin/node/cli.rb +0 -122
  57. data/lib/bitcoin/node/configuration.rb +0 -40
  58. data/lib/bitcoin/node/spv.rb +0 -87
  59. data/lib/bitcoin/node.rb +0 -7
  60. data/lib/bitcoin/rpc/http_server.rb +0 -84
  61. data/lib/bitcoin/rpc/request_handler.rb +0 -150
  62. data/lib/bitcoin/store/chain_entry.rb +0 -68
  63. data/lib/bitcoin/store/db/level_db.rb +0 -98
  64. data/lib/bitcoin/store/db.rb +0 -9
  65. data/lib/bitcoin/store/spv_chain.rb +0 -101
  66. data/lib/bitcoin/store/utxo_db.rb +0 -226
  67. data/lib/bitcoin/store.rb +0 -12
@@ -1,228 +0,0 @@
1
- module Bitcoin
2
- module Network
3
-
4
- # remote peer class.
5
- class Peer
6
-
7
- # Interval for pinging peers.
8
- PING_INTERVAL = 2 * 60
9
-
10
- attr_reader :logger
11
- attr_accessor :id
12
- attr_accessor :local_version
13
- attr_accessor :last_send
14
- attr_accessor :last_recv
15
- attr_accessor :bytes_sent
16
- attr_accessor :bytes_recv
17
- attr_accessor :conn_time
18
- attr_accessor :last_ping
19
- attr_accessor :last_ping_nonce
20
- attr_accessor :last_pong
21
- attr_accessor :min_ping
22
- attr_accessor :outbound # TODO need implements to accept inbound connection
23
- attr_accessor :best_hash
24
- attr_accessor :best_height
25
- # remote peer info
26
- attr_reader :host
27
- attr_reader :port
28
- # remote peer connection
29
- attr_accessor :conn
30
- attr_accessor :connected
31
- attr_accessor :primary
32
- # parent pool
33
- attr_reader :pool
34
- attr_reader :chain
35
- attr_accessor :fee_rate
36
-
37
- def initialize(host, port, pool, configuration)
38
- @host = host
39
- @port = port
40
- @pool = pool
41
- @chain = pool.chain
42
- @connected = false
43
- @primary = false
44
- @logger = Bitcoin::Logger.create(:debug)
45
- @outbound = true
46
- @best_hash = -1
47
- @best_height = -1
48
- @min_ping = -1
49
- @bytes_sent = 0
50
- @bytes_recv = 0
51
- @relay = configuration.conf[:relay]
52
- current_height = @chain.latest_block.height
53
- remote_addr = Bitcoin::Message::NetworkAddr.new(ip: host, port: port, time: nil)
54
- @local_version = Bitcoin::Message::Version.new(remote_addr: remote_addr, start_height: current_height, relay: @relay)
55
- end
56
-
57
- def connect
58
- self.conn ||= EM.connect(host, port, Bitcoin::Network::Connection, self)
59
- end
60
-
61
- def connected?
62
- @connected
63
- end
64
-
65
- def outbound?
66
- @outbound
67
- end
68
-
69
- def addr
70
- "#{host}:#{port}"
71
- end
72
-
73
- # calculate ping-pong time.
74
- def ping_time
75
- last_pong ? (last_pong - last_ping) / 1e6 : -1
76
- end
77
-
78
- # set last pong
79
- def last_pong=(time)
80
- @last_pong = time
81
- @min_ping = ping_time if min_ping == -1 || ping_time < min_ping
82
- end
83
-
84
- def post_handshake
85
- @connected = true
86
- if remote_version.support?(Bitcoin::Message::SERVICE_FLAGS[:bloom])
87
- pool.handle_new_peer(self)
88
- # require remote peer to use headers message instead fo inv message.
89
- conn.send_message(Bitcoin::Message::SendHeaders.new)
90
- EM.add_periodic_timer(PING_INTERVAL) {send_ping}
91
- else
92
- close("peer does not support NODE_BLOOM.")
93
- pool.pending_peers.delete(self)
94
- end
95
- end
96
-
97
- # start block header download
98
- def start_block_header_download
99
- logger.info("[#{addr}] start block header download.")
100
- get_headers = Bitcoin::Message::GetHeaders.new(
101
- Bitcoin.chain_params.protocol_version, [chain.latest_block.block_hash])
102
- conn.send_message(get_headers)
103
- end
104
-
105
- # broadcast tx.
106
- def broadcast_tx(tx)
107
- conn.send_message(Bitcoin::Message::Tx.new(tx, support_witness?))
108
- end
109
-
110
- # check the remote peer support witness.
111
- def support_witness?
112
- return false unless remote_version
113
- remote_version.services & Bitcoin::Message::SERVICE_FLAGS[:witness] > 0
114
- end
115
-
116
- # check the remote peer supports compact block.
117
- def support_cmpct?
118
- return false if remote_version.version < Bitcoin::Message::VERSION[:compact]
119
- return true unless local_version.services & Bitcoin::Message::SERVICE_FLAGS[:witness] > 0
120
- return false unless support_witness?
121
- remote_version.version >= Bitcoin::Message::VERSION[:compact_witness]
122
- end
123
-
124
- # get peer's block type.
125
- def block_type
126
- Bitcoin::Message::Inventory::MSG_FILTERED_BLOCK # TODO need other implementation
127
- end
128
-
129
- # get remote peer's version message.
130
- # @return [Bitcoin::Message::Version]
131
- def remote_version
132
- conn.version
133
- end
134
-
135
- # Whether to try and download blocks and transactions from this peer.
136
- def primary?
137
- primary
138
- end
139
-
140
- # handle headers message
141
- # @params [Bitcoin::Message::Headers]
142
- def handle_headers(headers)
143
- headers.headers.each do |header|
144
- break unless header.valid?
145
- entry = chain.append_header(header)
146
- next unless entry
147
- @best_hash = entry.block_hash
148
- @best_height = entry.height
149
- end
150
- pool.changed
151
- pool.notify_observers(:header, {hash: @best_hash, height: @best_height})
152
- start_block_header_download if headers.headers.size > 0 # next header download
153
- end
154
-
155
- # handle error
156
- def handle_error(e)
157
- pool.handle_error(e)
158
- end
159
-
160
- def unbind
161
- pool.handle_close_peer(self)
162
- end
163
-
164
- # close peer connection.
165
- def close(msg = '')
166
- conn.close(msg)
167
- end
168
-
169
- # generate Bitcoin::Message::NetworkAddr object from this peer info.
170
- # @return [Bitcoin::Message::NetworkAddr]
171
- def to_network_addr
172
- v = remote_version
173
- Bitcoin::Message::NetworkAddr.new(ip: host, port: port, services: v.services, time: v.timestamp)
174
- end
175
-
176
- # send +addr+ message to remote peer
177
- def send_addrs
178
- addrs = pool.peers.select{|p|p != self}.map(&:to_network_addr)
179
- conn.send_message(Bitcoin::Message::Addr.new(addrs))
180
- end
181
-
182
- # handle block inv message.
183
- def handle_block_inv(hashes)
184
- getdata = Bitcoin::Message::GetData.new(
185
- hashes.map{|h|Bitcoin::Message::Inventory.new(block_type, h)})
186
- conn.send_message(getdata)
187
- end
188
-
189
- def handle_tx(tx)
190
- pool.changed
191
- pool.notify_observers(:tx, tx)
192
- end
193
-
194
- def handle_merkle_block(merkle_block)
195
- pool.changed
196
- pool.notify_observers(:merkleblock, merkle_block)
197
- end
198
-
199
- # send ping message.
200
- def send_ping
201
- ping = Bitcoin::Message::Ping.new
202
- @last_ping = Time.now.to_i
203
- @last_pong = -1
204
- @last_ping_nonce = ping.nonce
205
- conn.send_message(ping)
206
- end
207
-
208
- # send filterload message.
209
- def send_filter_load(bloom)
210
- filter_load = Bitcoin::Message::FilterLoad.new(
211
- bloom, Bitcoin::Message::FilterLoad::BLOOM_UPDATE_ALL)
212
- conn.send_message(filter_load)
213
- end
214
-
215
- # send filteradd message.
216
- def send_filter_add(element)
217
- filter_add = Bitcoin::Message::FilterAdd.new(element)
218
- conn.send_message(filter_add)
219
- end
220
-
221
- # send filterclear message.
222
- def send_filter_clear
223
- filter_clear = Bitcoin::Message::FilterClear.new
224
- conn.send_message(filter_clear)
225
- end
226
- end
227
- end
228
- end
@@ -1,42 +0,0 @@
1
- module Bitcoin
2
- module Network
3
-
4
- class PeerDiscovery
5
-
6
- attr_reader :logger, :configuration
7
-
8
- def initialize(configuration)
9
- @logger = Bitcoin::Logger.create(:debug)
10
- @configuration = configuration
11
- end
12
-
13
- # get peer addresses, from DNS seeds.
14
- def peers
15
- # TODO add find from previous connected peer at first.
16
- (find_from_dns_seeds + seeds).uniq
17
- end
18
-
19
- private
20
-
21
- def dns_seeds
22
- Bitcoin.chain_params.dns_seeds || []
23
- end
24
-
25
- def seeds
26
- [*configuration.conf[:connect]]
27
- end
28
-
29
- def find_from_dns_seeds
30
- logger.debug 'discover peer address from DNS seeds.'
31
- dns_seeds.map { |seed|
32
- begin
33
- Socket.getaddrinfo("#{seed}", Bitcoin.chain_params.default_port).map{|a|a[2]}.uniq
34
- rescue SocketError => e
35
- logger.error "SocketError occurred when load DNS seed: #{seed}, error: #{e.message}"
36
- nil
37
- end
38
- }.flatten.compact
39
- end
40
- end
41
- end
42
- end
@@ -1,135 +0,0 @@
1
- module Bitcoin
2
-
3
- module Network
4
-
5
- # Time between pings automatically sent out for latency probing and keepalive (in seconds).
6
- PING_INTERVAL = 2 * 60
7
- # Time after which to disconnect, after waiting for a ping response (or inactivity).
8
- TIMEOUT_INTERVAL = 20 * 60
9
- # Maximum number of automatic outgoing nodes
10
- MAX_OUTBOUND_CONNECTIONS = 4
11
-
12
- # peer pool class.
13
- class Pool
14
- include Observable
15
-
16
- attr_reader :peers # active peers
17
- attr_reader :pending_peers # currently connecting peer
18
- attr_reader :node
19
- attr_reader :chain
20
- attr_reader :max_outbound
21
- attr_reader :logger
22
- attr_reader :peer_discovery
23
- attr_accessor :started
24
- attr_reader :mutex
25
-
26
- def initialize(node, chain, configuration)
27
- @node = node
28
- @peers = []
29
- @pending_peers = []
30
- @max_outbound = MAX_OUTBOUND_CONNECTIONS
31
- @chain = chain
32
- @logger = Bitcoin::Logger.create(:debug)
33
- @configuration = configuration
34
- @peer_discovery = PeerDiscovery.new(configuration)
35
- @started = false
36
- @mutex = Mutex.new
37
- end
38
-
39
- # connecting other peers and begin network activity.
40
- def start
41
- raise 'Cannot start a peer pool twice.' if started
42
- logger.debug 'Start connecting other pears.'
43
- addr_list = peer_discovery.peers
44
-
45
- connect(addr_list)
46
-
47
- @started = true
48
- end
49
-
50
- # detect new peer connection.
51
- def handle_new_peer(peer)
52
- logger.debug "connected new peer #{peer.addr}."
53
- mutex.synchronize do
54
- peer.id = allocate_peer_id
55
- unless peers.find(&:primary?)
56
- peer.primary = true
57
- peer.start_block_header_download
58
- end
59
- peers << peer
60
- end
61
- pending_peers.delete(peer)
62
- filter_load(peer) if node.wallet
63
- end
64
-
65
- def handle_close_peer(peer)
66
- return unless started
67
- peers.delete(peer)
68
- pending_peers.delete(peer)
69
- addr_list = peer_discovery.peers - peers.map(&:host) - pending_peers.map(&:host) - [peer.host]
70
- connect(addr_list)
71
- end
72
-
73
- # terminate peers.
74
- def terminate
75
- peers.each { |peer| peer.close('terminate') }
76
- pending_peers.each { |peer| peer.close('terminate') }
77
- @peers = []
78
- @started = false
79
- end
80
-
81
- # broadcast tx to connecting peer.
82
- def broadcast(tx)
83
- peers.each { |peer| peer.broadcast_tx(tx) }
84
- end
85
-
86
- # new bloom filter.
87
- def filter_load(peer)
88
- peer.send_filter_load(node.bloom)
89
- end
90
-
91
- # add element to bloom filter.
92
- def filter_add(element)
93
- peers.each { |peer| peer.send_filter_add(element) }
94
- end
95
-
96
- # clear bloom filter.
97
- def filter_clear
98
- peers.each { |peer| peer.send_filter_clear }
99
- end
100
-
101
- def handle_error(e)
102
- terminate
103
- end
104
-
105
- private
106
-
107
- # get primary peer
108
- def primary_peer
109
- peers.find(&:primary?)
110
- end
111
-
112
- # allocate new peer id
113
- def allocate_peer_id
114
- id = 0
115
- until peers.empty? || peers.find{|p|p.id == id}.nil?
116
- id += 1
117
- end
118
- id
119
- end
120
-
121
- def connect(addr_list)
122
- port = Bitcoin.chain_params.default_port
123
-
124
- EM::Iterator.new(addr_list, Bitcoin::PARALLEL_THREAD).each do |ip, iter|
125
- if pending_peers.size + peers.size < MAX_OUTBOUND_CONNECTIONS
126
- peer = Peer.new(ip, port, self, @configuration)
127
- pending_peers << peer
128
- peer.connect
129
- iter.next
130
- end
131
- end
132
- end
133
- end
134
- end
135
- end
@@ -1,13 +0,0 @@
1
- require 'eventmachine'
2
-
3
- module Bitcoin
4
- module Network
5
-
6
- autoload :MessageHandler, 'bitcoin/network/message_handler'
7
- autoload :Connection, 'bitcoin/network/connection'
8
- autoload :Pool, 'bitcoin/network/pool'
9
- autoload :Peer, 'bitcoin/network/peer'
10
- autoload :PeerDiscovery, 'bitcoin/network/peer_discovery'
11
-
12
- end
13
- end
@@ -1,122 +0,0 @@
1
- require 'net/http'
2
- require 'thor'
3
- require 'json'
4
-
5
- module Bitcoin
6
- module Node
7
-
8
- class CLI < Thor
9
-
10
- class_option :network, aliases: '-n', default: :mainnet
11
-
12
- desc 'decodepsbt <base64 psbt string>', "Return a JSON object representing the serialized, base64-encoded partially signed Bitcoin transaction."
13
- def decodepsbt(base64)
14
- psbt = Bitcoin::PSBT::Tx.parse_from_base64(base64)
15
- puts JSON.pretty_generate(psbt.to_h)
16
- end
17
-
18
- desc 'getblockchaininfo', 'Returns an object containing various state info regarding blockchain processing.'
19
- def getblockchaininfo
20
- request('getblockchaininfo')
21
- end
22
-
23
- desc 'stop', 'Stop Bitcoin server.'
24
- def stop
25
- request('stop')
26
- end
27
-
28
- desc 'getblockheader "hash" ( verbose )', 'If verbose is false, returns a string that is serialized, hex-encoded data for blockheader "hash". If verbose is true, returns an Object with information about blockheader <hash>.'
29
- def getblockheader(hash, verbose = true)
30
- verbose = verbose.is_a?(String) ? (verbose == 'true') : verbose
31
- request('getblockheader', hash, verbose)
32
- end
33
-
34
- desc 'getpeerinfo', 'Returns data about each connected network node as a json array of objects.'
35
- def getpeerinfo
36
- request('getpeerinfo')
37
- end
38
-
39
- desc 'decoderawtransaction "hexstring"', 'Return a JSON object representing the serialized, hex-encoded transaction.'
40
- def decoderawtransaction(hexstring)
41
- request('decoderawtransaction', hexstring)
42
- end
43
-
44
- desc 'decodescript "hexstring"', 'Decode a hex-encoded script.'
45
- def decodescript(hexstring)
46
- request('decodescript', hexstring)
47
- end
48
-
49
- # wallet cli
50
-
51
- desc 'sendrawtransaction', 'Submits raw transaction (serialized, hex-encoded) to local node and network.'
52
- def sendrawtransaction(hex_tx)
53
- request('sendrawtransaction', hex_tx)
54
- end
55
-
56
- desc 'createwallet "wallet_id"', 'Create new HD wallet. It returns an error if an existing wallet_id is specified. '
57
- def createwallet(wallet_id)
58
- request('createwallet', wallet_id)
59
- end
60
-
61
- desc 'listwallets', 'Returns a list of currently loaded wallets. For full information on the wallet, use "getwalletinfo"'
62
- def listwallets
63
- request('listwallets')
64
- end
65
-
66
- desc 'getwalletinfo', 'Returns an object containing various wallet state info.'
67
- def getwalletinfo
68
- request('getwalletinfo')
69
- end
70
-
71
- desc 'listaccounts', '[WIP]Returns Object that has account names as keys, account balances as values.'
72
- def listaccounts
73
- request('listaccounts')
74
- end
75
-
76
- desc 'encryptwallet "passphrase"', 'Encrypts the wallet with "passphrase". This is for first time encryption.After this, any calls that interact with private keys such as sending or signing will require the passphrase to be set prior the making these calls.'
77
- def encryptwallet(passhphrase)
78
- request('encryptwallet', passhphrase)
79
- end
80
-
81
- desc 'getnewaddress "account"', 'Returns a new Bitcoin address for receiving payments.'
82
- def getnewaddress(account)
83
- request('getnewaddress', account)
84
- end
85
-
86
- private
87
-
88
- def config
89
- opts = {}
90
- opts[:network] = options['network'] if options['network']
91
- @conf ||= Bitcoin::Node::Configuration.new(opts)
92
- end
93
-
94
- def request(command, *params)
95
- data = {
96
- :method => command,
97
- :params => params,
98
- :id => 'jsonrpc'
99
- }
100
- begin
101
- uri = URI.parse(config.server_url)
102
- http = Net::HTTP.new(uri.hostname, uri.port)
103
- http.use_ssl = uri.scheme === "https"
104
- request = Net::HTTP::Post.new('/')
105
- request.content_type = 'application/json'
106
- request.body = data.to_json
107
- response = http.request(request)
108
- body = response.body
109
- begin
110
- json = JSON.parse(body.to_str)
111
- puts JSON.pretty_generate(json)
112
- rescue Exception
113
- puts body.to_str
114
- end
115
- rescue Exception => e
116
- puts e.message
117
- end
118
- end
119
-
120
- end
121
- end
122
- end
@@ -1,40 +0,0 @@
1
- require 'iniparse'
2
-
3
- module Bitcoin
4
- module Node
5
- class Configuration
6
-
7
- attr_reader :conf # Hash
8
-
9
- # initialize configuration
10
- # @param [Hash] opts parameter for node.
11
- def initialize(opts = {})
12
- # TODO apply configuration file.
13
- opts[:network] = :mainnet unless opts[:network]
14
- opts[:relay] = false unless opts[:relay]
15
- Bitcoin.chain_params = opts[:network]
16
-
17
- begin
18
- ini_file = IniParse.parse(File.read("#{Bitcoin.base_dir}/bitcoinrb.conf"))
19
- @conf = Hash[ ini_file.to_h['__anonymous__'].map{|k,v| [k.to_sym, v] } ]
20
- rescue => e
21
- @conf = {}
22
- end
23
- @conf.merge!(opts)
24
- end
25
-
26
- def host
27
- 'localhost'
28
- end
29
-
30
- def port
31
- Bitcoin.chain_params.default_port - 1
32
- end
33
-
34
- def server_url
35
- "http://#{host}:#{port}"
36
- end
37
-
38
- end
39
- end
40
- end
@@ -1,87 +0,0 @@
1
- module Bitcoin
2
- module Node
3
-
4
- # SPV class
5
- class SPV
6
-
7
- attr_reader :chain
8
- attr_reader :pool
9
- attr_reader :logger
10
- attr_accessor :running
11
- attr_reader :configuration
12
- attr_accessor :server
13
- attr_accessor :wallet
14
- attr_accessor :bloom
15
-
16
- # Initialize spv settings
17
- # @param [Bitcoin::Node::Configuration] configuration configuration for spv.
18
- #
19
- # ```ruby
20
- # config = Bitcoin::Node::Configuration.new(network: :mainnet)
21
- # spv = Bitcoin::Node::SPV.new(config)
22
- # spv.run
23
- # ````
24
- def initialize(configuration)
25
- @chain = Bitcoin::Store::SPVChain.new
26
- @configuration = configuration
27
- @pool = Bitcoin::Network::Pool.new(self, @chain, @configuration)
28
- @logger = Bitcoin::Logger.create(:debug)
29
- @running = false
30
- @wallet = Bitcoin::Wallet::Base.current_wallet
31
- # TODO : optimize bloom filter parameters
32
- setup_filter
33
- end
34
-
35
- # open the node.
36
- def run
37
- # TODO need process running check.
38
- return if running
39
- logger.debug 'SPV node start running.'
40
- EM.run do
41
- # EM.start_server('0.0.0.0', Bitcoin.chain_params.default_port, Bitcoin::Network::InboundConnector, self)
42
- pool.start
43
- @server = Bitcoin::RPC::HttpServer.run(self, configuration.port)
44
- end
45
- end
46
-
47
- # close the node.
48
- def shutdown
49
- pool.terminate
50
- logger.debug 'SPV node shutdown.'
51
- end
52
-
53
- # broadcast a transaction
54
- def broadcast(tx)
55
- pool.broadcast(tx)
56
- logger.debug "broadcast tx: #{tx.to_hex}"
57
- end
58
-
59
- # add filter element to bloom filter.
60
- # [String] element. the hex string of txid, public key, public key hash or outpoint.
61
- def filter_add(element)
62
- bloom.add(element)
63
- pool.filter_add(element)
64
- end
65
-
66
- # clear bloom filter.
67
- def filter_clear
68
- pool.filter_clear
69
- end
70
-
71
- def add_observer(observer)
72
- pool.add_observer(observer)
73
- end
74
-
75
- def delete_observer(observer)
76
- pool.delete_observer(observer)
77
- end
78
-
79
- private
80
-
81
- def setup_filter
82
- @bloom = Bitcoin::BloomFilter.create_filter(512, 0.01)
83
- wallet.watch_targets.each{|t|bloom.add(t.htb)} if wallet
84
- end
85
- end
86
- end
87
- end
data/lib/bitcoin/node.rb DELETED
@@ -1,7 +0,0 @@
1
- module Bitcoin
2
- module Node
3
- autoload :SPV, 'bitcoin/node/spv'
4
- autoload :CLI, 'bitcoin/node/cli'
5
- autoload :Configuration, 'bitcoin/node/configuration'
6
- end
7
- end