tapyrus 0.3.4 → 0.3.5
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.github/workflows/ruby.yml +1 -1
- data/{.prettierrc.yaml → .prettierrc.yml} +0 -1
- data/.ruby-version +1 -1
- data/Gemfile +2 -2
- data/README.md +1 -1
- data/Rakefile +2 -2
- data/exe/tapyrus-script-debugger +5 -5
- data/exe/tapyrusrb-cli +1 -1
- data/exe/tapyrusrbd +18 -17
- data/lib/openassets/payload.rb +2 -2
- data/lib/openassets/util.rb +2 -2
- data/lib/openassets.rb +4 -4
- data/lib/schnorr/sign_to_contract.rb +4 -4
- data/lib/schnorr/signature.rb +5 -5
- data/lib/schnorr.rb +14 -14
- data/lib/tapyrus/base58.rb +8 -8
- data/lib/tapyrus/bip175.rb +5 -5
- data/lib/tapyrus/block_header.rb +2 -2
- data/lib/tapyrus/bloom_filter.rb +1 -1
- data/lib/tapyrus/chain_params.rb +5 -5
- data/lib/tapyrus/constants.rb +1 -1
- data/lib/tapyrus/errors.rb +9 -9
- data/lib/tapyrus/ext/ecdsa.rb +4 -4
- data/lib/tapyrus/ext/json_parser.rb +1 -1
- data/lib/tapyrus/ext.rb +3 -3
- data/lib/tapyrus/ext_key.rb +21 -21
- data/lib/tapyrus/jws.rb +76 -0
- data/lib/tapyrus/key.rb +48 -20
- data/lib/tapyrus/key_path.rb +3 -3
- data/lib/tapyrus/logger.rb +4 -11
- data/lib/tapyrus/merkle_tree.rb +1 -1
- data/lib/tapyrus/message/addr.rb +2 -2
- data/lib/tapyrus/message/base.rb +2 -2
- data/lib/tapyrus/message/block.rb +1 -1
- data/lib/tapyrus/message/block_txn.rb +1 -1
- data/lib/tapyrus/message/cmpct_block.rb +1 -1
- data/lib/tapyrus/message/fee_filter.rb +3 -3
- data/lib/tapyrus/message/filter_add.rb +1 -1
- data/lib/tapyrus/message/filter_clear.rb +2 -2
- data/lib/tapyrus/message/filter_load.rb +7 -7
- data/lib/tapyrus/message/get_addr.rb +2 -2
- data/lib/tapyrus/message/get_block_txn.rb +1 -1
- data/lib/tapyrus/message/get_blocks.rb +1 -1
- data/lib/tapyrus/message/get_data.rb +1 -1
- data/lib/tapyrus/message/get_headers.rb +1 -1
- data/lib/tapyrus/message/header_and_short_ids.rb +6 -6
- data/lib/tapyrus/message/headers.rb +1 -1
- data/lib/tapyrus/message/headers_parser.rb +2 -2
- data/lib/tapyrus/message/inv.rb +1 -1
- data/lib/tapyrus/message/inventory.rb +3 -3
- data/lib/tapyrus/message/mem_pool.rb +2 -2
- data/lib/tapyrus/message/merkle_block.rb +3 -3
- data/lib/tapyrus/message/network_addr.rb +9 -9
- data/lib/tapyrus/message/not_found.rb +1 -1
- data/lib/tapyrus/message/ping.rb +3 -3
- data/lib/tapyrus/message/pong.rb +3 -3
- data/lib/tapyrus/message/reject.rb +6 -6
- data/lib/tapyrus/message/send_cmpct.rb +4 -4
- data/lib/tapyrus/message/send_headers.rb +2 -2
- data/lib/tapyrus/message/tx.rb +1 -1
- data/lib/tapyrus/message/ver_ack.rb +2 -2
- data/lib/tapyrus/message/version.rb +7 -7
- data/lib/tapyrus/message.rb +37 -37
- data/lib/tapyrus/mnemonic.rb +18 -16
- data/lib/tapyrus/network/connection.rb +2 -2
- data/lib/tapyrus/network/message_handler.rb +11 -11
- data/lib/tapyrus/network/peer.rb +1 -1
- data/lib/tapyrus/network/peer_discovery.rb +1 -1
- data/lib/tapyrus/network/pool.rb +4 -4
- data/lib/tapyrus/network.rb +6 -6
- data/lib/tapyrus/node/cli.rb +34 -34
- data/lib/tapyrus/node/configuration.rb +3 -3
- data/lib/tapyrus/node/spv.rb +2 -2
- data/lib/tapyrus/node.rb +3 -3
- data/lib/tapyrus/opcodes.rb +7 -7
- data/lib/tapyrus/out_point.rb +2 -2
- data/lib/tapyrus/rpc/http_server.rb +6 -6
- data/lib/tapyrus/rpc/request_handler.rb +5 -5
- data/lib/tapyrus/rpc/tapyrus_core_client.rb +10 -10
- data/lib/tapyrus/rpc.rb +4 -4
- data/lib/tapyrus/script/color.rb +3 -3
- data/lib/tapyrus/script/debugger.rb +9 -9
- data/lib/tapyrus/script/multisig.rb +2 -2
- data/lib/tapyrus/script/script.rb +28 -28
- data/lib/tapyrus/script/script_error.rb +42 -42
- data/lib/tapyrus/script/script_interpreter.rb +9 -9
- data/lib/tapyrus/script/tx_checker.rb +2 -2
- data/lib/tapyrus/secp256k1/native.rb +23 -23
- data/lib/tapyrus/secp256k1/rfc6979.rb +7 -7
- data/lib/tapyrus/secp256k1/ruby.rb +2 -2
- data/lib/tapyrus/secp256k1.rb +3 -3
- data/lib/tapyrus/slip39/share.rb +7 -7
- data/lib/tapyrus/slip39/sss.rb +24 -24
- data/lib/tapyrus/slip39.rb +514 -37
- data/lib/tapyrus/store/db/level_db.rb +2 -2
- data/lib/tapyrus/store/db.rb +1 -1
- data/lib/tapyrus/store/spv_chain.rb +7 -7
- data/lib/tapyrus/store.rb +3 -3
- data/lib/tapyrus/tip0137.rb +201 -0
- data/lib/tapyrus/tx.rb +12 -12
- data/lib/tapyrus/tx_builder.rb +3 -3
- data/lib/tapyrus/tx_in.rb +3 -3
- data/lib/tapyrus/tx_out.rb +3 -3
- data/lib/tapyrus/util.rb +21 -21
- data/lib/tapyrus/validation.rb +9 -9
- data/lib/tapyrus/version.rb +1 -1
- data/lib/tapyrus/wallet/account.rb +12 -12
- data/lib/tapyrus/wallet/base.rb +9 -8
- data/lib/tapyrus/wallet/db.rb +11 -11
- data/lib/tapyrus/wallet/master_key.rb +13 -13
- data/lib/tapyrus/wallet.rb +4 -4
- data/lib/tapyrus.rb +62 -59
- data/tapyrusrb.gemspec +33 -31
- metadata +30 -14
@@ -22,7 +22,7 @@ module Tapyrus
|
|
22
22
|
return unless command
|
23
23
|
|
24
24
|
defer_handle_command(command, payload)
|
25
|
-
@message =
|
25
|
+
@message = ""
|
26
26
|
parse(rest) if rest && rest.bytesize > 0
|
27
27
|
end
|
28
28
|
|
@@ -30,7 +30,7 @@ module Tapyrus
|
|
30
30
|
head_magic = Tapyrus.chain_params.magic_head
|
31
31
|
return if @message.nil? || @message.size < MESSAGE_HEADER_SIZE
|
32
32
|
|
33
|
-
magic, command, length, checksum = @message.unpack(
|
33
|
+
magic, command, length, checksum = @message.unpack("a4A12Va4")
|
34
34
|
raise Tapyrus::Message::Error, "invalid header magic. #{magic.bth}" unless magic.bth == head_magic
|
35
35
|
|
36
36
|
payload = @message[MESSAGE_HEADER_SIZE...(MESSAGE_HEADER_SIZE + length)]
|
@@ -115,7 +115,7 @@ module Tapyrus
|
|
115
115
|
|
116
116
|
def handshake_done
|
117
117
|
return unless @incomming_handshake && @outgoing_handshake
|
118
|
-
logger.info
|
118
|
+
logger.info "handshake finished."
|
119
119
|
@connected = true
|
120
120
|
post_handshake
|
121
121
|
end
|
@@ -129,13 +129,13 @@ module Tapyrus
|
|
129
129
|
end
|
130
130
|
|
131
131
|
def on_ver_ack
|
132
|
-
logger.info(
|
132
|
+
logger.info("receive verack message.")
|
133
133
|
@outgoing_handshake = true
|
134
134
|
handshake_done
|
135
135
|
end
|
136
136
|
|
137
137
|
def on_get_addr
|
138
|
-
logger.info(
|
138
|
+
logger.info("receive getaddr message.")
|
139
139
|
peer.send_addrs
|
140
140
|
end
|
141
141
|
|
@@ -145,7 +145,7 @@ module Tapyrus
|
|
145
145
|
end
|
146
146
|
|
147
147
|
def on_send_headers
|
148
|
-
logger.info(
|
148
|
+
logger.info("receive sendheaders message.")
|
149
149
|
@sendheaders = true
|
150
150
|
end
|
151
151
|
|
@@ -170,17 +170,17 @@ module Tapyrus
|
|
170
170
|
end
|
171
171
|
|
172
172
|
def on_get_headers(headers)
|
173
|
-
logger.info(
|
173
|
+
logger.info("receive getheaders message.")
|
174
174
|
# TODO
|
175
175
|
end
|
176
176
|
|
177
177
|
def on_headers(headers)
|
178
|
-
logger.info(
|
178
|
+
logger.info("receive headers message.")
|
179
179
|
peer.handle_headers(headers)
|
180
180
|
end
|
181
181
|
|
182
182
|
def on_block(block)
|
183
|
-
logger.info(
|
183
|
+
logger.info("receive block message.")
|
184
184
|
# TODO
|
185
185
|
end
|
186
186
|
|
@@ -195,7 +195,7 @@ module Tapyrus
|
|
195
195
|
end
|
196
196
|
|
197
197
|
def on_mem_pool
|
198
|
-
logger.info(
|
198
|
+
logger.info("receive mempool message.")
|
199
199
|
# TODO return mempool tx
|
200
200
|
end
|
201
201
|
|
@@ -210,7 +210,7 @@ module Tapyrus
|
|
210
210
|
end
|
211
211
|
|
212
212
|
def on_inv(inv)
|
213
|
-
logger.info(
|
213
|
+
logger.info("receive inv message.")
|
214
214
|
blocks = []
|
215
215
|
txs = []
|
216
216
|
inv.inventories.each do |i|
|
data/lib/tapyrus/network/peer.rb
CHANGED
data/lib/tapyrus/network/pool.rb
CHANGED
@@ -38,8 +38,8 @@ module Tapyrus
|
|
38
38
|
|
39
39
|
# connecting other peers and begin network activity.
|
40
40
|
def start
|
41
|
-
raise
|
42
|
-
logger.debug
|
41
|
+
raise "Cannot start a peer pool twice." if started
|
42
|
+
logger.debug "Start connecting other pears."
|
43
43
|
addr_list = peer_discovery.peers
|
44
44
|
|
45
45
|
connect(addr_list)
|
@@ -72,8 +72,8 @@ module Tapyrus
|
|
72
72
|
|
73
73
|
# terminate peers.
|
74
74
|
def terminate
|
75
|
-
peers.each { |peer| peer.close(
|
76
|
-
pending_peers.each { |peer| peer.close(
|
75
|
+
peers.each { |peer| peer.close("terminate") }
|
76
|
+
pending_peers.each { |peer| peer.close("terminate") }
|
77
77
|
@peers = []
|
78
78
|
@started = false
|
79
79
|
end
|
data/lib/tapyrus/network.rb
CHANGED
@@ -1,11 +1,11 @@
|
|
1
|
-
require
|
1
|
+
require "eventmachine"
|
2
2
|
|
3
3
|
module Tapyrus
|
4
4
|
module Network
|
5
|
-
autoload :MessageHandler,
|
6
|
-
autoload :Connection,
|
7
|
-
autoload :Pool,
|
8
|
-
autoload :Peer,
|
9
|
-
autoload :PeerDiscovery,
|
5
|
+
autoload :MessageHandler, "tapyrus/network/message_handler"
|
6
|
+
autoload :Connection, "tapyrus/network/connection"
|
7
|
+
autoload :Pool, "tapyrus/network/pool"
|
8
|
+
autoload :Peer, "tapyrus/network/peer"
|
9
|
+
autoload :PeerDiscovery, "tapyrus/network/peer_discovery"
|
10
10
|
end
|
11
11
|
end
|
data/lib/tapyrus/node/cli.rb
CHANGED
@@ -1,101 +1,101 @@
|
|
1
|
-
require
|
2
|
-
require
|
3
|
-
require
|
1
|
+
require "net/http"
|
2
|
+
require "thor"
|
3
|
+
require "json"
|
4
4
|
|
5
5
|
module Tapyrus
|
6
6
|
module Node
|
7
7
|
class CLI < Thor
|
8
|
-
class_option :network, aliases:
|
8
|
+
class_option :network, aliases: "-n", default: :prod
|
9
9
|
|
10
|
-
desc
|
10
|
+
desc "getblockchaininfo", "Returns an object containing various state info regarding blockchain processing."
|
11
11
|
def getblockchaininfo
|
12
|
-
request(
|
12
|
+
request("getblockchaininfo")
|
13
13
|
end
|
14
14
|
|
15
|
-
desc
|
15
|
+
desc "stop", "Stop Tapyrus server."
|
16
16
|
def stop
|
17
|
-
request(
|
17
|
+
request("stop")
|
18
18
|
end
|
19
19
|
|
20
20
|
desc 'getblockheader "hash" ( verbose )',
|
21
21
|
'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>.'
|
22
22
|
def getblockheader(hash, verbose = true)
|
23
|
-
verbose = verbose.is_a?(String) ? (verbose ==
|
24
|
-
request(
|
23
|
+
verbose = verbose.is_a?(String) ? (verbose == "true") : verbose
|
24
|
+
request("getblockheader", hash, verbose)
|
25
25
|
end
|
26
26
|
|
27
|
-
desc
|
27
|
+
desc "getpeerinfo", "Returns data about each connected network node as a json array of objects."
|
28
28
|
def getpeerinfo
|
29
|
-
request(
|
29
|
+
request("getpeerinfo")
|
30
30
|
end
|
31
31
|
|
32
32
|
desc 'decoderawtransaction "hexstring"',
|
33
|
-
|
33
|
+
"Return a JSON object representing the serialized, hex-encoded transaction."
|
34
34
|
def decoderawtransaction(hexstring)
|
35
|
-
request(
|
35
|
+
request("decoderawtransaction", hexstring)
|
36
36
|
end
|
37
37
|
|
38
|
-
desc 'decodescript "hexstring"',
|
38
|
+
desc 'decodescript "hexstring"', "Decode a hex-encoded script."
|
39
39
|
def decodescript(hexstring)
|
40
|
-
request(
|
40
|
+
request("decodescript", hexstring)
|
41
41
|
end
|
42
42
|
|
43
43
|
# wallet cli
|
44
44
|
|
45
|
-
desc
|
45
|
+
desc "sendrawtransaction", "Submits raw transaction (serialized, hex-encoded) to local node and network."
|
46
46
|
def sendrawtransaction(hex_tx)
|
47
|
-
request(
|
47
|
+
request("sendrawtransaction", hex_tx)
|
48
48
|
end
|
49
49
|
|
50
50
|
desc 'createwallet "wallet_id"',
|
51
|
-
|
51
|
+
"Create new HD wallet. It returns an error if an existing wallet_id is specified. "
|
52
52
|
def createwallet(wallet_id)
|
53
|
-
request(
|
53
|
+
request("createwallet", wallet_id)
|
54
54
|
end
|
55
55
|
|
56
|
-
desc
|
56
|
+
desc "listwallets",
|
57
57
|
'Returns a list of currently loaded wallets. For full information on the wallet, use "getwalletinfo"'
|
58
58
|
def listwallets
|
59
|
-
request(
|
59
|
+
request("listwallets")
|
60
60
|
end
|
61
61
|
|
62
|
-
desc
|
62
|
+
desc "getwalletinfo", "Returns an object containing various wallet state info."
|
63
63
|
def getwalletinfo
|
64
|
-
request(
|
64
|
+
request("getwalletinfo")
|
65
65
|
end
|
66
66
|
|
67
|
-
desc
|
67
|
+
desc "listaccounts", "[WIP]Returns Object that has account names as keys, account balances as values."
|
68
68
|
def listaccounts
|
69
|
-
request(
|
69
|
+
request("listaccounts")
|
70
70
|
end
|
71
71
|
|
72
72
|
desc 'encryptwallet "passphrase"',
|
73
73
|
'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.'
|
74
74
|
def encryptwallet(passhphrase)
|
75
|
-
request(
|
75
|
+
request("encryptwallet", passhphrase)
|
76
76
|
end
|
77
77
|
|
78
|
-
desc 'getnewaddress "account"',
|
78
|
+
desc 'getnewaddress "account"', "Returns a new Tapyrus address for receiving payments."
|
79
79
|
def getnewaddress(account)
|
80
|
-
request(
|
80
|
+
request("getnewaddress", account)
|
81
81
|
end
|
82
82
|
|
83
83
|
private
|
84
84
|
|
85
85
|
def config
|
86
86
|
opts = {}
|
87
|
-
opts[:network] = options[
|
87
|
+
opts[:network] = options["network"] if options["network"]
|
88
88
|
@conf ||= Tapyrus::Node::Configuration.new(opts)
|
89
89
|
end
|
90
90
|
|
91
91
|
def request(command, *params)
|
92
|
-
data = { method: command, params: params, id:
|
92
|
+
data = { method: command, params: params, id: "jsonrpc" }
|
93
93
|
begin
|
94
94
|
uri = URI.parse(config.server_url)
|
95
95
|
http = Net::HTTP.new(uri.hostname, uri.port)
|
96
|
-
http.use_ssl = uri.scheme ===
|
97
|
-
request = Net::HTTP::Post.new(
|
98
|
-
request.content_type =
|
96
|
+
http.use_ssl = uri.scheme === "https"
|
97
|
+
request = Net::HTTP::Post.new("/")
|
98
|
+
request.content_type = "application/json"
|
99
99
|
request.body = data.to_json
|
100
100
|
response = http.request(request)
|
101
101
|
body = response.body
|
@@ -1,4 +1,4 @@
|
|
1
|
-
require
|
1
|
+
require "iniparse"
|
2
2
|
|
3
3
|
module Tapyrus
|
4
4
|
module Node
|
@@ -13,7 +13,7 @@ module Tapyrus
|
|
13
13
|
|
14
14
|
begin
|
15
15
|
ini_file = IniParse.parse(File.read("#{Tapyrus.base_dir}/tapyrusrb.conf"))
|
16
|
-
@conf = Hash[ini_file.to_h[
|
16
|
+
@conf = Hash[ini_file.to_h["__anonymous__"].map { |k, v| [k.to_sym, v] }]
|
17
17
|
rescue => e
|
18
18
|
@conf = {}
|
19
19
|
end
|
@@ -21,7 +21,7 @@ module Tapyrus
|
|
21
21
|
end
|
22
22
|
|
23
23
|
def host
|
24
|
-
|
24
|
+
"localhost"
|
25
25
|
end
|
26
26
|
|
27
27
|
def port
|
data/lib/tapyrus/node/spv.rb
CHANGED
@@ -27,7 +27,7 @@ module Tapyrus
|
|
27
27
|
def run
|
28
28
|
# TODO need process running check.
|
29
29
|
return if running
|
30
|
-
logger.debug
|
30
|
+
logger.debug "SPV node start running."
|
31
31
|
EM.run do
|
32
32
|
# EM.start_server('0.0.0.0', Tapyrus.chain_params.default_port, Tapyrus::Network::InboundConnector, self)
|
33
33
|
pool.start
|
@@ -38,7 +38,7 @@ module Tapyrus
|
|
38
38
|
# close the node.
|
39
39
|
def shutdown
|
40
40
|
pool.terminate
|
41
|
-
logger.debug
|
41
|
+
logger.debug "SPV node shutdown."
|
42
42
|
end
|
43
43
|
|
44
44
|
# broadcast a transaction
|
data/lib/tapyrus/node.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
module Tapyrus
|
2
2
|
module Node
|
3
|
-
autoload :SPV,
|
4
|
-
autoload :CLI,
|
5
|
-
autoload :Configuration,
|
3
|
+
autoload :SPV, "tapyrus/node/spv"
|
4
|
+
autoload :CLI, "tapyrus/node/cli"
|
5
|
+
autoload :Configuration, "tapyrus/node/configuration"
|
6
6
|
end
|
7
7
|
end
|
data/lib/tapyrus/opcodes.rb
CHANGED
@@ -144,22 +144,22 @@ module Tapyrus
|
|
144
144
|
OP_CHECKDATASIGVERIFY = 0xbb
|
145
145
|
OP_COLOR = 0xbc
|
146
146
|
|
147
|
-
DUPLICATE_KEY = [
|
147
|
+
DUPLICATE_KEY = %i[OP_NOP2 OP_NOP3]
|
148
148
|
OPCODES_MAP =
|
149
149
|
Hash[
|
150
|
-
*(constants.grep(/^OP_/) - [
|
151
|
-
[const_get(c), c.to_s]
|
152
|
-
|
150
|
+
*(constants.grep(/^OP_/) - %i[OP_NOP2 OP_NOP3 OP_CHECKLOCKTIMEVERIFY OP_CHECKSEQUENCEVERIFY])
|
151
|
+
.map { |c| [const_get(c), c.to_s] }
|
152
|
+
.flatten
|
153
153
|
]
|
154
154
|
NAME_MAP = Hash[*constants.grep(/^OP_/).map { |c| [c.to_s, const_get(c)] }.flatten]
|
155
155
|
|
156
156
|
def opcode_to_name(opcode)
|
157
|
-
return OPCODES_MAP[opcode].delete(
|
157
|
+
return OPCODES_MAP[opcode].delete("OP_") if opcode == OP_0 || (opcode <= OP_16 && opcode >= OP_1)
|
158
158
|
OPCODES_MAP[opcode]
|
159
159
|
end
|
160
160
|
|
161
161
|
def name_to_opcode(name)
|
162
|
-
return NAME_MAP[
|
162
|
+
return NAME_MAP["OP_" + name] if name =~ /^\d/ && name.to_i < 17 && name.to_i > -1
|
163
163
|
NAME_MAP[name]
|
164
164
|
end
|
165
165
|
|
@@ -176,7 +176,7 @@ module Tapyrus
|
|
176
176
|
end
|
177
177
|
|
178
178
|
def opcode_to_small_int(opcode)
|
179
|
-
return 0 if opcode ==
|
179
|
+
return 0 if opcode == "".b || opcode == OP_0
|
180
180
|
return -1 if opcode == OP_1NEGATE
|
181
181
|
return opcode - (OP_1 - 1) if opcode >= OP_1 && opcode <= OP_16
|
182
182
|
nil
|
data/lib/tapyrus/out_point.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
module Tapyrus
|
2
2
|
# outpoint class
|
3
3
|
class OutPoint
|
4
|
-
COINBASE_HASH =
|
4
|
+
COINBASE_HASH = "0000000000000000000000000000000000000000000000000000000000000000"
|
5
5
|
COINBASE_INDEX = 4_294_967_295
|
6
6
|
|
7
7
|
attr_reader :tx_hash
|
@@ -21,7 +21,7 @@ module Tapyrus
|
|
21
21
|
end
|
22
22
|
|
23
23
|
def to_payload
|
24
|
-
[tx_hash.htb, index].pack(
|
24
|
+
[tx_hash.htb, index].pack("a32V")
|
25
25
|
end
|
26
26
|
|
27
27
|
def self.create_coinbase_outpoint
|
@@ -1,5 +1,5 @@
|
|
1
|
-
require
|
2
|
-
require
|
1
|
+
require "evma_httpserver"
|
2
|
+
require "json"
|
3
3
|
|
4
4
|
module Tapyrus
|
5
5
|
module RPC
|
@@ -18,11 +18,11 @@ module Tapyrus
|
|
18
18
|
|
19
19
|
def post_init
|
20
20
|
super
|
21
|
-
logger.debug
|
21
|
+
logger.debug "start http server."
|
22
22
|
end
|
23
23
|
|
24
24
|
def self.run(node, port = 8332)
|
25
|
-
EM.start_server(
|
25
|
+
EM.start_server("0.0.0.0", port, HttpServer, node)
|
26
26
|
end
|
27
27
|
|
28
28
|
# process http request.
|
@@ -47,7 +47,7 @@ module Tapyrus
|
|
47
47
|
response.status = 200
|
48
48
|
response.content = result
|
49
49
|
end
|
50
|
-
response.content_type
|
50
|
+
response.content_type "application/json"
|
51
51
|
response.send_response
|
52
52
|
end
|
53
53
|
EM.defer(operation, callback)
|
@@ -57,7 +57,7 @@ module Tapyrus
|
|
57
57
|
# @return [Array] the array of command and args
|
58
58
|
def parse_json_params
|
59
59
|
params = JSON.parse(@http_post_content)
|
60
|
-
[params[
|
60
|
+
[params["method"], params["params"]]
|
61
61
|
end
|
62
62
|
end
|
63
63
|
end
|
@@ -23,13 +23,13 @@ module Tapyrus
|
|
23
23
|
def getblockheader(block_id, verbose)
|
24
24
|
block_hash = block_id.rhex
|
25
25
|
entry = node.chain.find_entry_by_hash(block_hash)
|
26
|
-
raise ArgumentError.new(
|
26
|
+
raise ArgumentError.new("Block not found") unless entry
|
27
27
|
if verbose
|
28
28
|
{
|
29
29
|
hash: block_id,
|
30
30
|
height: entry.height,
|
31
31
|
features: entry.header.features,
|
32
|
-
featuresHex: entry.header.features.to_even_length_hex.ljust(8,
|
32
|
+
featuresHex: entry.header.features.to_even_length_hex.ljust(8, "0"),
|
33
33
|
merkleroot: entry.header.merkle_root.rhex,
|
34
34
|
immutablemerkleroot: entry.header.im_merkle_root.rhex,
|
35
35
|
time: entry.header.time,
|
@@ -53,7 +53,7 @@ module Tapyrus
|
|
53
53
|
id: peer.id,
|
54
54
|
addr: "#{peer.host}:#{peer.port}",
|
55
55
|
addrlocal: local_addr,
|
56
|
-
services: peer.remote_version.services.to_even_length_hex.rjust(16,
|
56
|
+
services: peer.remote_version.services.to_even_length_hex.rjust(16, "0"),
|
57
57
|
relaytxes: peer.remote_version.relay,
|
58
58
|
lastsend: peer.last_send,
|
59
59
|
lastrecv: peer.last_recv,
|
@@ -86,7 +86,7 @@ module Tapyrus
|
|
86
86
|
begin
|
87
87
|
Tapyrus::Tx.parse_from_payload(hex_tx.htb).to_h
|
88
88
|
rescue Exception
|
89
|
-
raise ArgumentError.new(
|
89
|
+
raise ArgumentError.new("TX decode failed")
|
90
90
|
end
|
91
91
|
end
|
92
92
|
|
@@ -99,7 +99,7 @@ module Tapyrus
|
|
99
99
|
h[:p2sh] = script.to_p2sh.to_addr unless script.p2sh?
|
100
100
|
h
|
101
101
|
rescue Exception
|
102
|
-
raise ArgumentError.new(
|
102
|
+
raise ArgumentError.new("Script decode failed")
|
103
103
|
end
|
104
104
|
end
|
105
105
|
|
@@ -1,5 +1,5 @@
|
|
1
|
-
require
|
2
|
-
require
|
1
|
+
require "net/http"
|
2
|
+
require "json/pure"
|
3
3
|
|
4
4
|
module Tapyrus
|
5
5
|
module RPC
|
@@ -71,7 +71,7 @@ module Tapyrus
|
|
71
71
|
request(:help)
|
72
72
|
.split("\n")
|
73
73
|
.inject([]) do |memo_ary, line|
|
74
|
-
memo_ary << line.split(
|
74
|
+
memo_ary << line.split(" ").first.to_sym if !line.empty? && !line.start_with?("==")
|
75
75
|
memo_ary
|
76
76
|
end
|
77
77
|
TapyrusCoreClient.class_eval do
|
@@ -88,24 +88,24 @@ module Tapyrus
|
|
88
88
|
end
|
89
89
|
|
90
90
|
def request(command, *params)
|
91
|
-
data = { method: command, params: params, id:
|
91
|
+
data = { method: command, params: params, id: "jsonrpc" }
|
92
92
|
uri = URI.parse(server_url)
|
93
93
|
http = Net::HTTP.new(uri.hostname, uri.port)
|
94
|
-
http.use_ssl = uri.scheme ===
|
95
|
-
request = Net::HTTP::Post.new(uri.path.empty? ?
|
94
|
+
http.use_ssl = uri.scheme === "https"
|
95
|
+
request = Net::HTTP::Post.new(uri.path.empty? ? "/" : uri.path)
|
96
96
|
request.basic_auth(uri.user, uri.password)
|
97
|
-
request.content_type =
|
97
|
+
request.content_type = "application/json"
|
98
98
|
request.body = data.to_json
|
99
99
|
response = http.request(request)
|
100
100
|
raise error!(response) unless response.is_a? Net::HTTPOK
|
101
101
|
response = Tapyrus::RPC.response_body2json(response.body)
|
102
|
-
response[
|
102
|
+
response["result"]
|
103
103
|
end
|
104
104
|
|
105
105
|
def error!(response)
|
106
106
|
rpc_error =
|
107
107
|
begin
|
108
|
-
Tapyrus::RPC.response_body2json(response.body)[
|
108
|
+
Tapyrus::RPC.response_body2json(response.body)["error"]
|
109
109
|
rescue JSON::ParserError => _
|
110
110
|
# if RPC server don't send error message.
|
111
111
|
end
|
@@ -117,7 +117,7 @@ module Tapyrus
|
|
117
117
|
def response_body2json(body)
|
118
118
|
Tapyrus::Ext::JsonParser.new(
|
119
119
|
body.gsub(/\\u([\da-fA-F]{4})/) do
|
120
|
-
[$1].pack(
|
120
|
+
[$1].pack("H*").unpack("n*").pack("U*").encode("ISO-8859-1").force_encoding("UTF-8")
|
121
121
|
end
|
122
122
|
).parse
|
123
123
|
end
|
data/lib/tapyrus/rpc.rb
CHANGED
@@ -1,8 +1,8 @@
|
|
1
1
|
module Tapyrus
|
2
2
|
module RPC
|
3
|
-
autoload :HttpServer,
|
4
|
-
autoload :RequestHandler,
|
5
|
-
autoload :TapyrusCoreClient,
|
6
|
-
autoload :Error,
|
3
|
+
autoload :HttpServer, "tapyrus/rpc/http_server"
|
4
|
+
autoload :RequestHandler, "tapyrus/rpc/request_handler"
|
5
|
+
autoload :TapyrusCoreClient, "tapyrus/rpc/tapyrus_core_client"
|
6
|
+
autoload :Error, "tapyrus/rpc/tapyrus_core_client"
|
7
7
|
end
|
8
8
|
end
|
data/lib/tapyrus/script/color.rb
CHANGED
@@ -26,15 +26,15 @@ module Tapyrus
|
|
26
26
|
|
27
27
|
# Return ColorIdentifier for native token(i.e TPC)
|
28
28
|
def self.default
|
29
|
-
new(TokenTypes::NONE,
|
29
|
+
new(TokenTypes::NONE, "0000000000000000000000000000000000000000000000000000000000000000".htb)
|
30
30
|
end
|
31
31
|
|
32
32
|
def to_payload
|
33
|
-
[type, payload].pack(
|
33
|
+
[type, payload].pack("Ca*")
|
34
34
|
end
|
35
35
|
|
36
36
|
def self.parse_from_payload(payload)
|
37
|
-
type, payload = payload.unpack(
|
37
|
+
type, payload = payload.unpack("Ca*")
|
38
38
|
new(type, payload)
|
39
39
|
end
|
40
40
|
|
@@ -21,7 +21,7 @@ module Tapyrus
|
|
21
21
|
@script_pubkey = script_pubkey
|
22
22
|
@script_sig = script_sig
|
23
23
|
if tx
|
24
|
-
raise ArgumentError,
|
24
|
+
raise ArgumentError, "index should be specified" if index.nil?
|
25
25
|
@tx_checker = Tapyrus::TxChecker.new(tx: tx, input_index: index)
|
26
26
|
if (tx_checker.tx.in.size - 1) < tx_checker.input_index
|
27
27
|
raise ArgumentError, "Tx does not have #{tx_checker.input_index}-th input."
|
@@ -52,7 +52,7 @@ module Tapyrus
|
|
52
52
|
return(
|
53
53
|
StepResult.error(
|
54
54
|
current_stack: interpreter.stack.dup,
|
55
|
-
error:
|
55
|
+
error: "Script evaluated without error but finished with a false/empty top stack element"
|
56
56
|
)
|
57
57
|
)
|
58
58
|
end
|
@@ -96,9 +96,9 @@ module Tapyrus
|
|
96
96
|
end
|
97
97
|
|
98
98
|
class StepResult
|
99
|
-
STATUS_RUNNING =
|
100
|
-
STATUS_HALT =
|
101
|
-
STATUS_FINISHED =
|
99
|
+
STATUS_RUNNING = "running"
|
100
|
+
STATUS_HALT = "halt"
|
101
|
+
STATUS_FINISHED = "finished"
|
102
102
|
|
103
103
|
STATUSES = [STATUS_RUNNING, STATUS_HALT, STATUS_FINISHED]
|
104
104
|
|
@@ -112,7 +112,7 @@ module Tapyrus
|
|
112
112
|
# @param [String] message
|
113
113
|
# @param [String] error an error message.
|
114
114
|
def initialize(status, current_stack: [], message: nil, error: nil)
|
115
|
-
raise ArgumentError,
|
115
|
+
raise ArgumentError, "Unsupported status specified." unless STATUSES.include?(status)
|
116
116
|
@status = status
|
117
117
|
@current_stack = current_stack
|
118
118
|
@error = error
|
@@ -141,7 +141,7 @@ module Tapyrus
|
|
141
141
|
|
142
142
|
def stack_table
|
143
143
|
rows = current_stack.map { |s| [s] }.reverse
|
144
|
-
Terminal::Table.new(title:
|
144
|
+
Terminal::Table.new(title: "Current Stack", rows: rows)
|
145
145
|
end
|
146
146
|
|
147
147
|
def print_result
|
@@ -155,10 +155,10 @@ module Tapyrus
|
|
155
155
|
|
156
156
|
class EmptyTxChecker
|
157
157
|
def check_sig(script_sig, pubkey, script_code)
|
158
|
-
raise TxUnspecifiedError,
|
158
|
+
raise TxUnspecifiedError, "Signature verification failed. You need to enter tx and input index."
|
159
159
|
end
|
160
160
|
def verify_sig(sig, pubkey, digest, allow_hybrid: false)
|
161
|
-
raise TxUnspecifiedError,
|
161
|
+
raise TxUnspecifiedError, "Signature verification failed. You need to enter tx and input index."
|
162
162
|
end
|
163
163
|
end
|
164
164
|
end
|
@@ -4,7 +4,7 @@ module Tapyrus
|
|
4
4
|
include Tapyrus::Opcodes
|
5
5
|
|
6
6
|
def self.prefix
|
7
|
-
[OP_0].pack(
|
7
|
+
[OP_0].pack("C*")
|
8
8
|
end
|
9
9
|
|
10
10
|
# generate input script sig spending a multisig output script.
|
@@ -22,7 +22,7 @@ module Tapyrus
|
|
22
22
|
# multiple parties. Signatures must be in the same order as the
|
23
23
|
# pubkeys in the output script being redeemed.
|
24
24
|
def self.add_sig_to_multisig_script_sig(sig_to_add, script_sig, hash_type = SIGHASH_TYPE[:all])
|
25
|
-
signature = sig_to_add + [hash_type].pack(
|
25
|
+
signature = sig_to_add + [hash_type].pack("C*")
|
26
26
|
offset = script_sig.empty? ? 0 : 1
|
27
27
|
script_sig.insert(offset, Tapyrus::Script.pack_pushdata(signature))
|
28
28
|
end
|