Class: Solana::NonceAccount

Inherits:
Object
  • Object
show all
Defined in:
lib/solana/nonce_account.rb

Overview

Parser for a System-Program durable NONCE account’s on-chain data (80 bytes):

version                u32  (offset 0)
state                  u32  (offset 4)   0 = Uninitialized, 1 = Initialized
authority              [32] (offset 8)
stored_nonce/blockhash [32] (offset 40)  ← anchor a tx's recentBlockhash on this
fee_calculator         u64  (offset 72)  lamports_per_signature

Used to read the value a durable-nonce-anchored tx must use, and to verify the account is initialized + owned by the expected authority before trusting it.

Constant Summary collapse

UNINITIALIZED =
0
INITIALIZED =
1
NonceLength =
80

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(version:, state:, authority:, nonce:, lamports_per_signature:) ⇒ NonceAccount

Returns a new instance of NonceAccount.



18
19
20
21
22
23
24
# File 'lib/solana/nonce_account.rb', line 18

def initialize(version:, state:, authority:, nonce:, lamports_per_signature:)
  @version = version
  @state = state
  @authority = authority # base58
  @nonce = nonce         # base58 — use as the tx recentBlockhash
  @lamports_per_signature = lamports_per_signature
end

Instance Attribute Details

#authorityObject (readonly)

Returns the value of attribute authority.



16
17
18
# File 'lib/solana/nonce_account.rb', line 16

def authority
  @authority
end

#lamports_per_signatureObject (readonly)

Returns the value of attribute lamports_per_signature.



16
17
18
# File 'lib/solana/nonce_account.rb', line 16

def lamports_per_signature
  @lamports_per_signature
end

#nonceObject (readonly)

Returns the value of attribute nonce.



16
17
18
# File 'lib/solana/nonce_account.rb', line 16

def nonce
  @nonce
end

#stateObject (readonly)

Returns the value of attribute state.



16
17
18
# File 'lib/solana/nonce_account.rb', line 16

def state
  @state
end

#versionObject (readonly)

Returns the value of attribute version.



16
17
18
# File 'lib/solana/nonce_account.rb', line 16

def version
  @version
end

Class Method Details

.looks_base64?(str) ⇒ Boolean

Returns:

  • (Boolean)


50
51
52
# File 'lib/solana/nonce_account.rb', line 50

def self.looks_base64?(str)
  str.bytesize > 80 && str.match?(%r{\A[A-Za-z0-9+/=\r\n]+\z})
end

.parse(data) ⇒ Object

‘data` is the raw account bytes (binary). Accepts a base64 string too.

Raises:

  • (ArgumentError)


27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
# File 'lib/solana/nonce_account.rb', line 27

def self.parse(data)
  bytes = data
  if bytes.is_a?(String) && bytes.encoding != Encoding::ASCII_8BIT
    bytes = bytes.b
  end
  # Tolerate a base64-encoded blob (what getAccountInfo returns in data[0]).
  if bytes.bytesize != NonceLength && looks_base64?(bytes)
    require "base64"
    bytes = Base64.decode64(bytes).b
  end
  raise ArgumentError, "nonce account too small (#{bytes.bytesize} bytes, need >= 80)" if bytes.bytesize < 80

  new(
    version:                bytes[0, 4].unpack1("V"),
    state:                  bytes[4, 4].unpack1("V"),
    authority:              Keypair.encode_base58(bytes.byteslice(8, 32)),
    nonce:                  Keypair.encode_base58(bytes.byteslice(40, 32)),
    lamports_per_signature: bytes[72, 8].unpack1("Q<")
  )
end

Instance Method Details

#authority?(expected) ⇒ Boolean

True when the account is initialized AND its authority matches ‘expected` (base58). The guard before anchoring any tx on this nonce.

Returns:

  • (Boolean)


60
61
62
# File 'lib/solana/nonce_account.rb', line 60

def authority?(expected)
  initialized? && authority == expected.to_s
end

#initialized?Boolean

Returns:

  • (Boolean)


54
55
56
# File 'lib/solana/nonce_account.rb', line 54

def initialized?
  state == INITIALIZED
end