Class: Bitcoin::Descriptor::Expression
- Inherits:
-
Object
- Object
- Bitcoin::Descriptor::Expression
- Defined in:
- lib/bitcoin/descriptor/expression.rb
Overview
Expression for descriptor.
Direct Known Subclasses
Instance Method Summary collapse
- #==(other) ⇒ Object
-
#args ⇒ String
Get args for this expression.
-
#compressed_key?(key) ⇒ Boolean
Check whether
key
is compressed public key or not. -
#derive_path(key, paths) ⇒ Bitcoin::Key
Derive key using
paths
. -
#extract_pubkey(key) ⇒ Bitcoin::Key
Extract public key from KEY format.
-
#to_hex ⇒ String
Convert to bitcoin script as hex string.
-
#to_s(checksum: false) ⇒ String
Get descriptor string.
-
#to_script ⇒ Bitcoin::Script
Convert to bitcoin script.
-
#top_level? ⇒ Boolean
Whether this is top level or not.
-
#type ⇒ Symbol
Get expression type.
Instance Method Details
#==(other) ⇒ Object
116 117 118 119 |
# File 'lib/bitcoin/descriptor/expression.rb', line 116 def ==(other) return false unless other.is_a?(Expression) type == other.type && to_script == other.to_script end |
#args ⇒ String
Get args for this expression.
26 27 28 |
# File 'lib/bitcoin/descriptor/expression.rb', line 26 def args raise NotImplementedError end |
#compressed_key?(key) ⇒ Boolean
Check whether key
is compressed public key or not.
46 47 48 |
# File 'lib/bitcoin/descriptor/expression.rb', line 46 def compressed_key?(key) %w(02 03).include?(key[0..1]) && [key].pack("H*").bytesize == 33 end |
#derive_path(key, paths) ⇒ Bitcoin::Key
Derive key using paths
.
97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 |
# File 'lib/bitcoin/descriptor/expression.rb', line 97 def derive_path(key, paths) is_private = key.is_a?(Bitcoin::ExtKey) paths.each do |path| raise ArgumentError, 'xpub can not derive hardened key.' if !is_private && path.end_with?("'") if is_private hardened = path.end_with?("'") path = hardened ? path[0..-2] : path raise ArgumentError, 'Key path value is not a valid value.' unless path =~ /^[0-9]+$/ raise ArgumentError, 'Key path value is out of range.' if !hardened && path.to_i >= Bitcoin::HARDENED_THRESHOLD key = key.derive(path.to_i, hardened) else raise ArgumentError, 'Key path value is not a valid value.' unless path =~ /^[0-9]+$/ raise ArgumentError, 'Key path value is out of range.' if path.to_i >= Bitcoin::HARDENED_THRESHOLD key = key.derive(path.to_i) end end key end |
#extract_pubkey(key) ⇒ Bitcoin::Key
Extract public key from KEY format.
53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 |
# File 'lib/bitcoin/descriptor/expression.rb', line 53 def extract_pubkey(key) if key.start_with?('[') # BIP32 fingerprint raise ArgumentError, "Multiple ']' characters found for a single pubkey." if key.count('[') > 1 || key.count(']') > 1 info = key[1...key.index(']')] fingerprint, *paths = info.split('/') raise ArgumentError, "Fingerprint '#{fingerprint}' is not hex." unless fingerprint.valid_hex? raise ArgumentError, "Fingerprint '#{fingerprint}' is not 4 bytes." unless fingerprint.size == 8 key = key[(key.index(']') + 1)..-1] else raise ArgumentError, 'Invalid key origin.' if key.include?(']') end # check BIP32 derivation path key, *paths = key.split('/') raise ArgumentError, "No key provided." unless key if key.start_with?('xprv') key = Bitcoin::ExtKey.from_base58(key) key = derive_path(key, paths) if paths elsif key.start_with?('xpub') key = Bitcoin::ExtPubkey.from_base58(key) key = derive_path(key, paths) if paths else begin key = Bitcoin::Key.from_wif(key) rescue ArgumentError key = if key.length == 64 Bitcoin::Key.from_xonly_pubkey(key) else key_type = compressed_key?(key) ? Bitcoin::Key::TYPES[:compressed] : Bitcoin::Key::TYPES[:uncompressed] Bitcoin::Key.new(pubkey: key, key_type: key_type) end end end key = key.is_a?(Bitcoin::Key) ? key : key.key raise ArgumentError, Errors::Messages::INVALID_PUBLIC_KEY unless key.fully_valid_pubkey? key end |
#to_hex ⇒ String
Convert to bitcoin script as hex string.
40 41 42 |
# File 'lib/bitcoin/descriptor/expression.rb', line 40 def to_hex to_script.to_hex end |
#to_s(checksum: false) ⇒ String
Get descriptor string.
33 34 35 36 |
# File 'lib/bitcoin/descriptor/expression.rb', line 33 def to_s(checksum: false) desc = "#{type.to_s}(#{args})" checksum ? Checksum.descsum_create(desc) : desc end |
#to_script ⇒ Bitcoin::Script
Convert to bitcoin script
14 15 16 |
# File 'lib/bitcoin/descriptor/expression.rb', line 14 def to_script raise NotImplementedError end |
#top_level? ⇒ Boolean
Whether this is top level or not.
20 21 22 |
# File 'lib/bitcoin/descriptor/expression.rb', line 20 def top_level? raise NotImplementedError end |
#type ⇒ Symbol
Get expression type.
8 9 10 |
# File 'lib/bitcoin/descriptor/expression.rb', line 8 def type raise NotImplementedError end |