class Glueby::Internal::Wallet::TapyrusCoreWalletAdapter

Constants

RPC_WALLET_ERROR_ERROR_CODE
RPC_WALLET_NOT_FOUND_ERROR_CODE
WALLET_PREFIX

Public Instance Methods

balance(wallet_id, only_finalized = true) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 76
def balance(wallet_id, only_finalized = true)
  perform_as(wallet_id) do |client|
    confirmed = tpc_to_tapyrus(client.getbalance)
    return confirmed if only_finalized

    confirmed + tpc_to_tapyrus(client.getunconfirmedbalance)
  end
end
broadcast(wallet_id, tx, &block) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 121
def broadcast(wallet_id, tx, &block)
  perform_as(wallet_id) do |client|
    block.call(tx) if block
    client.sendrawtransaction(tx.to_hex)
  end
end
change_address(wallet_id) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 134
def change_address(wallet_id)
  perform_as(wallet_id) do |client|
    client.getrawchangeaddress
  end
end
create_pubkey(wallet_id) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 140
def create_pubkey(wallet_id)
  perform_as(wallet_id) do |client|
    address = client.getnewaddress('')
    info = client.getaddressinfo(address)
    Tapyrus::Key.new(pubkey: info['pubkey'])
  end
end
create_wallet(wallet_id = nil) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 30
def create_wallet(wallet_id = nil)
  wallet_id = SecureRandom.hex(16) unless wallet_id
  begin
    RPC.client.createwallet(wallet_name(wallet_id))
  rescue Tapyrus::RPC::Error => ex
    if ex.rpc_error && ex.rpc_error['code'] == RPC_WALLET_ERROR_ERROR_CODE && /Wallet wallet-#{wallet_id} already exists\./ =~ ex.rpc_error['message']
      raise Errors::WalletAlreadyCreated, "Wallet #{wallet_id} has been already created."
    else
      raise ex
    end
  end

  wallet_id
end
delete_wallet(wallet_id) click to toggle source

On TapyrusCoreWallet, there are no way to delete real wallet via RPC. So, here just unload.

# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 47
def delete_wallet(wallet_id)
  unload_wallet(wallet_id)
end
list_unspent(wallet_id, only_finalized = true, label = nil) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 85
def list_unspent(wallet_id, only_finalized = true, label = nil)
  perform_as(wallet_id) do |client|
    min_conf = only_finalized ? 1 : 0
    res = client.listunspent(min_conf)

    res = res.filter { |i| i['label'] == label } if label && (label != :unlabeled)
    res = res.filter { |i| i['label'] == "" } if label == :unlabeled
 
    res.map do |i|
      script = Tapyrus::Script.parse_from_payload(i['scriptPubKey'].htb)
      color_id = if script.cp2pkh? || script.cp2sh?
        Tapyrus::Color::ColorIdentifier.parse_from_payload(script.chunks[0].pushed_data).to_hex
      end
      {
        txid: i['txid'],
        vout: i['vout'],
        script_pubkey: i['scriptPubKey'],
        color_id: color_id,
        amount: tpc_to_tapyrus(i['amount']),
        finalized: i['confirmations'] != 0
      }
    end
  end
end
load_wallet(wallet_id) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 51
def load_wallet(wallet_id)
  RPC.client.loadwallet(wallet_name(wallet_id))
rescue Tapyrus::RPC::Error => ex
  if ex.rpc_error && ex.rpc_error['code'] == RPC_WALLET_ERROR_ERROR_CODE && /Duplicate -wallet filename specified/ =~ ex.rpc_error['message']
    raise Errors::WalletAlreadyLoaded, "Wallet #{wallet_id} has been already loaded."
  elsif ex.rpc_error && ex.rpc_error['code'] == RPC_WALLET_NOT_FOUND_ERROR_CODE
    raise Errors::WalletNotFound, "Wallet #{wallet_id} does not found"
  else
    raise ex
  end
end
receive_address(wallet_id, label = nil) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 128
def receive_address(wallet_id, label = nil)
  perform_as(wallet_id) do |client|
    client.getnewaddress(label || '')
  end
end
sign_tx(wallet_id, tx, prevtxs = [], sighashtype: Tapyrus::SIGHASH_TYPE[:all]) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 110
def sign_tx(wallet_id, tx, prevtxs = [], sighashtype: Tapyrus::SIGHASH_TYPE[:all])
  perform_as(wallet_id) do |client|
    res = client.signrawtransactionwithwallet(tx.to_hex, prevtxs, encode_sighashtype(sighashtype))
    if res['complete']
      Tapyrus::Tx.parse_from_payload(res['hex'].htb)
    else
      raise res['errors'].to_json
    end
  end
end
unload_wallet(wallet_id) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 63
def unload_wallet(wallet_id)
  RPC.client.unloadwallet(wallet_name(wallet_id))
end
wallets() click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 67
def wallets
  RPC.client.listwallets.map do |wallet_name|
    match = /\A#{WALLET_PREFIX}(?<wallet_id>[0-9A-Fa-f]{32})\z/.match(wallet_name)
    next unless match

    match[:wallet_id]
  end.compact
end

Private Instance Methods

encode_sighashtype(sighashtype) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 168
def encode_sighashtype(sighashtype)
  type = case sighashtype & (~(Tapyrus::SIGHASH_TYPE[:anyonecanpay]))
         when Tapyrus::SIGHASH_TYPE[:all] then 'ALL'
         when Tapyrus::SIGHASH_TYPE[:none] then 'NONE'
         when Tapyrus::SIGHASH_TYPE[:single] then 'SIGNLE'
         else
           raise Errors::InvalidSighashType, "Invalid sighash type '#{sighashtype}'"
         end

  if sighashtype & Tapyrus::SIGHASH_TYPE[:anyonecanpay] == 0x80
    type += '|ANYONECANPAY'
  end

  type
end
perform_as(wallet_id) { |client| ... } click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 150
def perform_as(wallet_id)
  RPC.perform_as(wallet_name(wallet_id)) do |client|
    begin
      yield(client)
    rescue Tapyrus::RPC::Error => ex
      if ex.rpc_error && ex.rpc_error['code'] == RPC_WALLET_NOT_FOUND_ERROR_CODE
        raise Errors::WalletUnloaded, "The wallet #{wallet_id} is unloaded. You should load before use it."
      else
        raise ex
      end
    end
  end
end
wallet_name(wallet_id) click to toggle source
# File lib/glueby/internal/wallet/tapyrus_core_wallet_adapter.rb, line 164
def wallet_name(wallet_id)
  "#{WALLET_PREFIX}#{wallet_id}"
end