Class: Glueby::Contract::AR::Timestamp

Inherits:
ActiveRecord::Base
  • Object
show all
Includes:
GluebyLogger
Defined in:
lib/glueby/contract/active_record/timestamp.rb

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Methods included from GluebyLogger

#logger

Constructor Details

#initialize(attributes = nil) ⇒ Timestamp

  • wallet_id

  • content

  • prefix(optional)

  • timestamp_type(optional)

  • version [String] Version of the timestamp recording method.

    The format in which the timestamp is recorded differs depending on the version.
    Version "1" treats the specified content and prefix as a binary string.
    Version "2" treats the specified content and prefix as a hexadecimal string with the string set to prefix and content.
    

Parameters:

  • attributes (Hash) (defaults to: nil)

    attributes which consist of:

Raises:



50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
# File 'lib/glueby/contract/active_record/timestamp.rb', line 50

def initialize(attributes = nil)
  # Set content_hash from :content attribute
  hex = attributes[:version] == '1' ? false : true
  content_hash = Timestamp.digest_content(attributes[:content], attributes[:digest] || :sha256, hex)
  super(
    wallet_id: attributes[:wallet_id],
    content_hash: content_hash,
    prefix: attributes[:prefix] || '',
    status: :init,
    timestamp_type: attributes[:timestamp_type] || :simple,
    prev_id: attributes[:prev_id],
    version: attributes[:version]
  )
rescue ::ArgumentError => e
  raise Glueby::ArgumentError, e.message
end

Instance Attribute Details

#txObject (readonly)

Returns the value of attribute tx.



10
11
12
# File 'lib/glueby/contract/active_record/timestamp.rb', line 10

def tx
  @tx
end

Class Method Details

.digest_content(content, digest, hex = false) ⇒ Object



24
25
26
27
28
29
30
31
32
33
34
35
36
37
# File 'lib/glueby/contract/active_record/timestamp.rb', line 24

def digest_content(content, digest, hex = false)
  case digest&.downcase
  when :sha256
    content = hex ? content.htb : content
    Tapyrus.sha256(content).bth
  when :double_sha256
    content = hex ? content.htb : content
    Tapyrus.double_sha256(content).bth
  when :none
    content
  else
    raise Glueby::Contract::Errors::UnsupportedDigestType
  end
end

Instance Method Details

#hex?Boolean Also known as: hex

Returns:

  • (Boolean)


143
144
145
# File 'lib/glueby/contract/active_record/timestamp.rb', line 143

def hex?
  version != '1'
end

#latest?Boolean Also known as: latest

Return true if timestamp type is ‘trackable’ and output in timestamp transaction has not been spent yet, otherwise return false.

Returns:

  • (Boolean)


68
69
70
# File 'lib/glueby/contract/active_record/timestamp.rb', line 68

def latest?
  trackable? && attributes['latest']
end

#next_idObject



17
18
19
# File 'lib/glueby/contract/active_record/timestamp.rb', line 17

def next_id
  self.next&.id
end

#save_with_broadcast(fee_estimator: Glueby::Contract::FeeEstimator::Fixed.new, utxo_provider: nil) ⇒ Object

Broadcast and save timestamp

Parameters:

Returns:

  • true if tapyrus transactions were broadcasted and the timestamp was updated successfully, otherwise false.



92
93
94
95
96
97
98
99
100
# File 'lib/glueby/contract/active_record/timestamp.rb', line 92

def save_with_broadcast(fee_estimator: Glueby::Contract::FeeEstimator::Fixed.new, utxo_provider: nil)
  save_with_broadcast!(fee_estimator: fee_estimator, utxo_provider: utxo_provider)
rescue Errors::FailedToBroadcast => e
  logger.error("failed to broadcast (id=#{id}, reason=#{e.message})")
  false
rescue Errors::ArgumentError => e
  logger.info("failed to broadcast by argument error (id=#{id}, reason=#{e.message})")
  false
end

#save_with_broadcast!(fee_estimator: Glueby::Contract::FeeEstimator::Fixed.new, utxo_provider: nil) ⇒ Object

Broadcast and save timestamp, and it raises errors

Parameters:

Returns:

  • true if tapyrus transactions were broadcasted and the timestamp was updated successfully

Raises:



110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
# File 'lib/glueby/contract/active_record/timestamp.rb', line 110

def save_with_broadcast!(fee_estimator: Glueby::Contract::FeeEstimator::Fixed.new, utxo_provider: nil)
  validate_prev!
  utxo_provider = Glueby::UtxoProvider.new if !utxo_provider && Glueby.configuration.use_utxo_provider?

  funding_tx, tx, p2c_address, payment_base = create_txs(fee_estimator, utxo_provider)

  if funding_tx
    logger.info("funding tx was broadcasted(id=#{id}, funding_tx.txid=#{funding_tx.txid})")
  end
  ::ActiveRecord::Base.transaction(joinable: false, requires_new: true) do
    wallet.internal_wallet.broadcast(tx) do |tx|
      assign_attributes(txid: tx.txid, status: :unconfirmed, p2c_address: p2c_address, payment_base: payment_base)
      @tx = tx
      save!(validate: false) # The validation is already executed at head of #save_with_broadcast!

      if update_trackable?
        prev.latest = false
        prev.next = self
        prev.save!
      end
    end
  end
  logger.info("timestamp tx was broadcasted (id=#{id}, txid=#{tx.txid})")
  true
rescue Tapyrus::RPC::Error,
       Internal::Wallet::Errors::WalletAlreadyLoaded,
       Internal::Wallet::Errors::WalletNotFound,
       Glueby::Internal::Wallet::Errors::InvalidSigner,
       Errors::InsufficientFunds => e
  errors.add(:base, "failed to broadcast (id=#{id}, reason=#{e.message})")
  raise Errors::FailedToBroadcast, "failed to broadcast (id=#{id}, reason=#{e.message})"
end

#utxoHash

Returns a UTXO that corresponds to the timestamp

Returns:

  • (Hash)

    UTXO

    • String

      script_pubkey A script pubkey hex string

    • String

      txid A txid

    • Integer

      vout An index of the tx

    • Integer

      amount A value of



79
80
81
82
83
84
85
86
# File 'lib/glueby/contract/active_record/timestamp.rb', line 79

def utxo
  {
    script_pubkey: Tapyrus::Script.parse_from_addr(p2c_address).to_hex,
    txid: txid,
    vout: Contract::Timestamp::TxBuilder::PAY_TO_CONTRACT_INPUT_INDEX,
    amount: Glueby::Contract::Timestamp::P2C_DEFAULT_VALUE
  }
end