solace-zar-trustless-escrow 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/lib/solace/zar_trustless_escrow/codecs_extensions.rb +101 -0
- data/lib/solace/zar_trustless_escrow/composers/claim_composer.rb +136 -0
- data/lib/solace/zar_trustless_escrow/composers/deposit_composer.rb +145 -0
- data/lib/solace/zar_trustless_escrow/composers/mediated_deposit_composer.rb +173 -0
- data/lib/solace/zar_trustless_escrow/composers/mediated_reclaim_composer.rb +137 -0
- data/lib/solace/zar_trustless_escrow/composers/mediated_release_composer.rb +157 -0
- data/lib/solace/zar_trustless_escrow/composers/reclaim_composer.rb +135 -0
- data/lib/solace/zar_trustless_escrow/composers/token_account_init_composer.rb +88 -0
- data/lib/solace/zar_trustless_escrow/constants.rb +47 -0
- data/lib/solace/zar_trustless_escrow/errors/program_error.rb +30 -0
- data/lib/solace/zar_trustless_escrow/errors.rb +104 -0
- data/lib/solace/zar_trustless_escrow/instructions/claim_instruction.rb +60 -0
- data/lib/solace/zar_trustless_escrow/instructions/deposit_instruction.rb +65 -0
- data/lib/solace/zar_trustless_escrow/instructions/mediated_deposit_instruction.rb +74 -0
- data/lib/solace/zar_trustless_escrow/instructions/mediated_reclaim_instruction.rb +60 -0
- data/lib/solace/zar_trustless_escrow/instructions/mediated_release_instruction.rb +65 -0
- data/lib/solace/zar_trustless_escrow/instructions/reclaim_instruction.rb +60 -0
- data/lib/solace/zar_trustless_escrow/instructions/token_account_init_instruction.rb +48 -0
- data/lib/solace/zar_trustless_escrow/programs/zar_trustless_escrow/escrow_deposit_operations.rb +243 -0
- data/lib/solace/zar_trustless_escrow/programs/zar_trustless_escrow/mediated_escrow_deposit_operations.rb +259 -0
- data/lib/solace/zar_trustless_escrow/programs/zar_trustless_escrow.rb +148 -0
- data/lib/solace/zar_trustless_escrow/types/escrow_deposit.rb +44 -0
- data/lib/solace/zar_trustless_escrow/types/mediated_escrow_deposit.rb +50 -0
- data/lib/solace/zar_trustless_escrow/version.rb +7 -0
- data/lib/solace/zar_trustless_escrow.rb +38 -0
- metadata +171 -0
checksums.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
---
|
|
2
|
+
SHA256:
|
|
3
|
+
metadata.gz: cdaf827139b0191b39f2e86adf1e2bb5a714ceca4809e0ce35fd912662e90878
|
|
4
|
+
data.tar.gz: 7b4c7dbf1a9544a78f2bdbce3c14965caa75c96d15bd2380aeffed6e8f4acc70
|
|
5
|
+
SHA512:
|
|
6
|
+
metadata.gz: 0dcbcd5f20e0d349eed662845453561788d0c4a32a16edea05117d64d2621e6a51508bd7449370f15f7abf3e0d40e9b3e266a3bce3203e123f4dbac9a4514235
|
|
7
|
+
data.tar.gz: d3acc72bf804af39aadb54e0ff78f857f8c26ad87e51fdb924e5370eac60161f8c3105243e611b268df079bb94e7c978a3276eeab09ce0d0ca31719f083c10ec
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Solace
|
|
4
|
+
module Utils
|
|
5
|
+
# Extensions to Solace::Utils::Codecs for the Borsh/Anchor types used by the
|
|
6
|
+
# ZAR Trustless Escrow program that the base solace gem does not provide.
|
|
7
|
+
#
|
|
8
|
+
# The base gem (>= 0.1.5) already provides encode_le_u64 / decode_le_u64 and
|
|
9
|
+
# the base58 helpers as module (self.) methods; this module reopens Codecs and
|
|
10
|
+
# uses `extend self` so the helpers below are callable both as instance methods
|
|
11
|
+
# (within composed encoders) and as Solace::Utils::Codecs.<method>.
|
|
12
|
+
module Codecs
|
|
13
|
+
extend self
|
|
14
|
+
|
|
15
|
+
# Encodes an i64 as 8 little-endian bytes (two's complement).
|
|
16
|
+
#
|
|
17
|
+
# @param i64 [Integer] Value in range -2**63..2**63-1.
|
|
18
|
+
# @return [String] 8-byte little-endian binary string.
|
|
19
|
+
def encode_le_i64(i64)
|
|
20
|
+
[i64].pack('q<')
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
# Encodes a public key as 32 bytes. Accepts any representation that resolves
|
|
24
|
+
# to a base58 string via #to_s (String, Keypair, PublicKey).
|
|
25
|
+
#
|
|
26
|
+
# @param pubkey [#to_s] The public key in any representation.
|
|
27
|
+
# @return [Array<Integer>] 32 bytes.
|
|
28
|
+
def encode_pubkey(pubkey)
|
|
29
|
+
Solace::Utils::Codecs.base58_to_bytes(pubkey.to_s)
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
# Encodes an Option<publicKey> in Borsh format.
|
|
33
|
+
# None → [0], Some(key) → [1] + 32 bytes.
|
|
34
|
+
#
|
|
35
|
+
# @param pubkey [#to_s, nil] Base58 public key or nil.
|
|
36
|
+
# @return [Array<Integer>]
|
|
37
|
+
def encode_option_pubkey(pubkey)
|
|
38
|
+
return [0] if pubkey.nil?
|
|
39
|
+
|
|
40
|
+
[1] + encode_pubkey(pubkey)
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
# Encodes an Option<i64> in Borsh format.
|
|
44
|
+
# None → [0], Some(i64) → [1] + 8 little-endian bytes.
|
|
45
|
+
#
|
|
46
|
+
# @param i64 [Integer, nil]
|
|
47
|
+
# @return [Array<Integer>]
|
|
48
|
+
def encode_option_i64(i64)
|
|
49
|
+
return [0] if i64.nil?
|
|
50
|
+
|
|
51
|
+
[1] + encode_le_i64(i64).bytes
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
# Decodes a u8 from 1 byte.
|
|
55
|
+
#
|
|
56
|
+
# @param stream [IO, StringIO] The stream to read from.
|
|
57
|
+
# @return [Integer] Value in range 0..255.
|
|
58
|
+
def decode_u8(stream)
|
|
59
|
+
stream.read(1).unpack1('C')
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
# Decodes an i64 from 8 little-endian bytes (two's complement).
|
|
63
|
+
#
|
|
64
|
+
# @param stream [IO, StringIO] The stream to read from.
|
|
65
|
+
# @return [Integer] Value in range -2**63..2**63-1.
|
|
66
|
+
def decode_le_i64(stream)
|
|
67
|
+
stream.read(8).unpack1('q<')
|
|
68
|
+
end
|
|
69
|
+
|
|
70
|
+
# Decodes a public key from 32 bytes.
|
|
71
|
+
#
|
|
72
|
+
# @param stream [IO, StringIO] The stream to read from.
|
|
73
|
+
# @return [String] Base58 public key.
|
|
74
|
+
def decode_pubkey(stream)
|
|
75
|
+
Solace::Utils::Codecs.bytes_to_base58(stream.read(32).bytes)
|
|
76
|
+
end
|
|
77
|
+
|
|
78
|
+
# Decodes an Option<publicKey> in Borsh format.
|
|
79
|
+
# None → nil, Some(key) → base58 pubkey.
|
|
80
|
+
#
|
|
81
|
+
# @param stream [IO, StringIO] The stream to read from.
|
|
82
|
+
# @return [String, nil] Base58 public key or nil.
|
|
83
|
+
def decode_option_pubkey(stream)
|
|
84
|
+
return nil if decode_u8(stream).zero?
|
|
85
|
+
|
|
86
|
+
decode_pubkey(stream)
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
# Decodes an Option<i64> in Borsh format.
|
|
90
|
+
# None → nil, Some(i64) → integer.
|
|
91
|
+
#
|
|
92
|
+
# @param stream [IO, StringIO] The stream to read from.
|
|
93
|
+
# @return [Integer, nil]
|
|
94
|
+
def decode_option_i64(stream)
|
|
95
|
+
return nil if decode_u8(stream).zero?
|
|
96
|
+
|
|
97
|
+
decode_le_i64(stream)
|
|
98
|
+
end
|
|
99
|
+
end
|
|
100
|
+
end
|
|
101
|
+
end
|
|
@@ -0,0 +1,136 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Solace
|
|
4
|
+
module Composers
|
|
5
|
+
# Composes a `claim` instruction for the ZAR Trustless Escrow program.
|
|
6
|
+
#
|
|
7
|
+
# The claim authority releases an EscrowDeposit to the claimant and closes the
|
|
8
|
+
# deposit account (rent returns to the fee payer).
|
|
9
|
+
#
|
|
10
|
+
# Required params:
|
|
11
|
+
# :mint [#to_s] Mint of the escrowed tokens.
|
|
12
|
+
# :claim_authority [#to_s, Keypair] Claim authority (readonly signer).
|
|
13
|
+
# :claimant [#to_s] Recipient of the released tokens.
|
|
14
|
+
# :claimant_token_account [#to_s] Claimant's destination token account (ATA).
|
|
15
|
+
# :escrow_deposit [#to_s] EscrowDeposit PDA.
|
|
16
|
+
# :program_token_account [#to_s] Per-mint program vault PDA.
|
|
17
|
+
# :fee_payer [#to_s, Keypair] Fee payer (writable signer).
|
|
18
|
+
#
|
|
19
|
+
# Optional params:
|
|
20
|
+
# :program_id [#to_s] Escrow program id (default: PROGRAM_ID, mainnet).
|
|
21
|
+
# :token_program_id [#to_s] Token program (default: legacy SPL Token).
|
|
22
|
+
class ZarTrustlessEscrowClaimComposer < Base
|
|
23
|
+
# Extracts the mint address from the params
|
|
24
|
+
#
|
|
25
|
+
# @return [String] The mint address
|
|
26
|
+
def mint
|
|
27
|
+
params[:mint].to_s
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
# Extracts the claim authority from the params
|
|
31
|
+
#
|
|
32
|
+
# @return [String] The claim authority address
|
|
33
|
+
def claim_authority
|
|
34
|
+
params[:claim_authority].to_s
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
# Extracts the claimant address from the params
|
|
38
|
+
#
|
|
39
|
+
# @return [String] The claimant address
|
|
40
|
+
def claimant
|
|
41
|
+
params[:claimant].to_s
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# Extracts the claimant's destination token account from the params
|
|
45
|
+
#
|
|
46
|
+
# @return [String] The claimant token account address
|
|
47
|
+
def claimant_token_account
|
|
48
|
+
params[:claimant_token_account].to_s
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
# Extracts the EscrowDeposit PDA address from the params
|
|
52
|
+
#
|
|
53
|
+
# @return [String] The escrow deposit address
|
|
54
|
+
def escrow_deposit
|
|
55
|
+
params[:escrow_deposit].to_s
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
# Extracts the per-mint program vault address from the params
|
|
59
|
+
#
|
|
60
|
+
# @return [String] The program token account address
|
|
61
|
+
def program_token_account
|
|
62
|
+
params[:program_token_account].to_s
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
# Extracts the fee payer address from the params
|
|
66
|
+
#
|
|
67
|
+
# @return [String] The fee payer address
|
|
68
|
+
def fee_payer
|
|
69
|
+
params[:fee_payer].to_s
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
# Returns the escrow program id (defaults to the mainnet PROGRAM_ID)
|
|
73
|
+
#
|
|
74
|
+
# @return [String] The escrow program id
|
|
75
|
+
def program_id
|
|
76
|
+
(params[:program_id] || Solace::ZarTrustlessEscrow::PROGRAM_ID).to_s
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
# Returns the token program id (defaults to the legacy SPL Token program)
|
|
80
|
+
#
|
|
81
|
+
# @return [String] The token program id
|
|
82
|
+
def token_program_id
|
|
83
|
+
(params[:token_program_id] || Solace::Constants::TOKEN_PROGRAM_ID).to_s
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
# Returns the System Program id
|
|
87
|
+
#
|
|
88
|
+
# @return [String] The System Program id
|
|
89
|
+
def system_program
|
|
90
|
+
Solace::Constants::SYSTEM_PROGRAM_ID
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
# Returns the Associated Token Account Program id
|
|
94
|
+
#
|
|
95
|
+
# @return [String] The Associated Token Account Program id
|
|
96
|
+
def associated_token_program
|
|
97
|
+
Solace::Constants::ASSOCIATED_TOKEN_ACCOUNT_PROGRAM_ID
|
|
98
|
+
end
|
|
99
|
+
|
|
100
|
+
# Declares all accounts required by this instruction.
|
|
101
|
+
def setup_accounts
|
|
102
|
+
account_context.add_readonly_nonsigner(mint)
|
|
103
|
+
account_context.add_readonly_signer(claim_authority)
|
|
104
|
+
account_context.add_readonly_nonsigner(claimant)
|
|
105
|
+
account_context.add_writable_nonsigner(claimant_token_account)
|
|
106
|
+
account_context.add_writable_nonsigner(escrow_deposit)
|
|
107
|
+
account_context.add_writable_nonsigner(program_token_account)
|
|
108
|
+
account_context.add_writable_signer(fee_payer)
|
|
109
|
+
account_context.add_readonly_nonsigner(system_program)
|
|
110
|
+
account_context.add_readonly_nonsigner(token_program_id)
|
|
111
|
+
account_context.add_readonly_nonsigner(associated_token_program)
|
|
112
|
+
account_context.add_readonly_nonsigner(program_id)
|
|
113
|
+
end
|
|
114
|
+
|
|
115
|
+
# Builds the instruction with resolved account indices.
|
|
116
|
+
#
|
|
117
|
+
# @param context [Solace::Utils::AccountContext] Merged context from TransactionComposer.
|
|
118
|
+
# @return [Solace::Instruction]
|
|
119
|
+
def build_instruction(context)
|
|
120
|
+
Solace::ZarTrustlessEscrow::Instructions::ClaimInstruction.build(
|
|
121
|
+
mint_index: context.index_of(mint),
|
|
122
|
+
claim_authority_index: context.index_of(claim_authority),
|
|
123
|
+
claimant_index: context.index_of(claimant),
|
|
124
|
+
claimant_token_account_index: context.index_of(claimant_token_account),
|
|
125
|
+
escrow_deposit_index: context.index_of(escrow_deposit),
|
|
126
|
+
program_token_account_index: context.index_of(program_token_account),
|
|
127
|
+
fee_payer_index: context.index_of(fee_payer),
|
|
128
|
+
system_program_index: context.index_of(system_program),
|
|
129
|
+
token_program_index: context.index_of(token_program_id),
|
|
130
|
+
associated_token_program_index: context.index_of(associated_token_program),
|
|
131
|
+
program_index: context.index_of(program_id)
|
|
132
|
+
)
|
|
133
|
+
end
|
|
134
|
+
end
|
|
135
|
+
end
|
|
136
|
+
end
|
|
@@ -0,0 +1,145 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Solace
|
|
4
|
+
module Composers
|
|
5
|
+
# Composes a `deposit` instruction for the ZAR Trustless Escrow program.
|
|
6
|
+
#
|
|
7
|
+
# Locks `amount` tokens from the depositor into a per-claim-authority
|
|
8
|
+
# EscrowDeposit PDA and the per-mint program vault. When a sponsor pays, the
|
|
9
|
+
# fee payer is the sponsor; otherwise the depositor pays.
|
|
10
|
+
#
|
|
11
|
+
# Required params:
|
|
12
|
+
# :mint [#to_s] Mint of the escrowed tokens.
|
|
13
|
+
# :depositor [#to_s, Keypair] Depositor (writable signer).
|
|
14
|
+
# :depositor_token_account [#to_s] Depositor's source token account.
|
|
15
|
+
# :escrow_deposit [#to_s] EscrowDeposit PDA.
|
|
16
|
+
# :program_token_account [#to_s] Per-mint program vault PDA.
|
|
17
|
+
# :fee_payer [#to_s, Keypair] Fee payer (writable signer).
|
|
18
|
+
# :amount [Integer] u64 amount to deposit.
|
|
19
|
+
# :claim_authority [#to_s] Authority that can claim the deposit.
|
|
20
|
+
#
|
|
21
|
+
# Optional params:
|
|
22
|
+
# :sponsor [#to_s] Optional fee sponsor (default: nil).
|
|
23
|
+
# :program_id [#to_s] Escrow program id (default: PROGRAM_ID, mainnet).
|
|
24
|
+
# :token_program_id [#to_s] Token program (default: legacy SPL Token).
|
|
25
|
+
class ZarTrustlessEscrowDepositComposer < Base
|
|
26
|
+
# Extracts the mint address from the params
|
|
27
|
+
#
|
|
28
|
+
# @return [String] The mint address
|
|
29
|
+
def mint
|
|
30
|
+
params[:mint].to_s
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
# Extracts the depositor address from the params
|
|
34
|
+
#
|
|
35
|
+
# @return [String] The depositor address
|
|
36
|
+
def depositor
|
|
37
|
+
params[:depositor].to_s
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
# Extracts the depositor's source token account address from the params
|
|
41
|
+
#
|
|
42
|
+
# @return [String] The depositor token account address
|
|
43
|
+
def depositor_token_account
|
|
44
|
+
params[:depositor_token_account].to_s
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
# Extracts the EscrowDeposit PDA address from the params
|
|
48
|
+
#
|
|
49
|
+
# @return [String] The escrow deposit address
|
|
50
|
+
def escrow_deposit
|
|
51
|
+
params[:escrow_deposit].to_s
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
# Extracts the per-mint program vault address from the params
|
|
55
|
+
#
|
|
56
|
+
# @return [String] The program token account address
|
|
57
|
+
def program_token_account
|
|
58
|
+
params[:program_token_account].to_s
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
# Extracts the fee payer address from the params
|
|
62
|
+
#
|
|
63
|
+
# @return [String] The fee payer address
|
|
64
|
+
def fee_payer
|
|
65
|
+
params[:fee_payer].to_s
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
# Extracts the deposit amount from the params
|
|
69
|
+
#
|
|
70
|
+
# @return [Integer] The u64 amount to deposit
|
|
71
|
+
def amount
|
|
72
|
+
params[:amount]
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
# Extracts the claim authority from the params
|
|
76
|
+
#
|
|
77
|
+
# @return [String] The claim authority address
|
|
78
|
+
def claim_authority
|
|
79
|
+
params[:claim_authority].to_s
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
# Extracts the optional fee sponsor from the params
|
|
83
|
+
#
|
|
84
|
+
# @return [String, nil] The sponsor address, or nil
|
|
85
|
+
def sponsor
|
|
86
|
+
params[:sponsor]&.to_s
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
# Returns the escrow program id (defaults to the mainnet PROGRAM_ID)
|
|
90
|
+
#
|
|
91
|
+
# @return [String] The escrow program id
|
|
92
|
+
def program_id
|
|
93
|
+
(params[:program_id] || Solace::ZarTrustlessEscrow::PROGRAM_ID).to_s
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
# Returns the token program id (defaults to the legacy SPL Token program)
|
|
97
|
+
#
|
|
98
|
+
# @return [String] The token program id
|
|
99
|
+
def token_program_id
|
|
100
|
+
(params[:token_program_id] || Solace::Constants::TOKEN_PROGRAM_ID).to_s
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
# Returns the System Program id
|
|
104
|
+
#
|
|
105
|
+
# @return [String] The System Program id
|
|
106
|
+
def system_program
|
|
107
|
+
Solace::Constants::SYSTEM_PROGRAM_ID
|
|
108
|
+
end
|
|
109
|
+
|
|
110
|
+
# Declares all accounts required by this instruction.
|
|
111
|
+
def setup_accounts
|
|
112
|
+
account_context.add_readonly_nonsigner(mint)
|
|
113
|
+
account_context.add_writable_signer(depositor)
|
|
114
|
+
account_context.add_writable_nonsigner(depositor_token_account)
|
|
115
|
+
account_context.add_writable_nonsigner(escrow_deposit)
|
|
116
|
+
account_context.add_writable_nonsigner(program_token_account)
|
|
117
|
+
account_context.add_writable_signer(fee_payer)
|
|
118
|
+
account_context.add_readonly_nonsigner(system_program)
|
|
119
|
+
account_context.add_readonly_nonsigner(token_program_id)
|
|
120
|
+
account_context.add_readonly_nonsigner(program_id)
|
|
121
|
+
end
|
|
122
|
+
|
|
123
|
+
# Builds the instruction with resolved account indices.
|
|
124
|
+
#
|
|
125
|
+
# @param context [Solace::Utils::AccountContext] Merged context from TransactionComposer.
|
|
126
|
+
# @return [Solace::Instruction]
|
|
127
|
+
def build_instruction(context)
|
|
128
|
+
Solace::ZarTrustlessEscrow::Instructions::DepositInstruction.build(
|
|
129
|
+
amount:,
|
|
130
|
+
claim_authority:,
|
|
131
|
+
sponsor:,
|
|
132
|
+
mint_index: context.index_of(mint),
|
|
133
|
+
depositor_index: context.index_of(depositor),
|
|
134
|
+
depositor_token_account_index: context.index_of(depositor_token_account),
|
|
135
|
+
escrow_deposit_index: context.index_of(escrow_deposit),
|
|
136
|
+
program_token_account_index: context.index_of(program_token_account),
|
|
137
|
+
fee_payer_index: context.index_of(fee_payer),
|
|
138
|
+
system_program_index: context.index_of(system_program),
|
|
139
|
+
token_program_index: context.index_of(token_program_id),
|
|
140
|
+
program_index: context.index_of(program_id)
|
|
141
|
+
)
|
|
142
|
+
end
|
|
143
|
+
end
|
|
144
|
+
end
|
|
145
|
+
end
|
|
@@ -0,0 +1,173 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Solace
|
|
4
|
+
module Composers
|
|
5
|
+
# Composes a `mediated_deposit` instruction for the ZAR Trustless Escrow
|
|
6
|
+
# program.
|
|
7
|
+
#
|
|
8
|
+
# Locks `amount` tokens into a three-party MediatedEscrowDeposit PDA (keyed by
|
|
9
|
+
# `id`) and the per-mint program vault. The mediator decides the outcome; an
|
|
10
|
+
# optional expiry lets the depositor reclaim after the timestamp passes.
|
|
11
|
+
#
|
|
12
|
+
# Required params:
|
|
13
|
+
# :mint [#to_s] Mint of the escrowed tokens.
|
|
14
|
+
# :depositor [#to_s, Keypair] Depositor (writable signer).
|
|
15
|
+
# :depositor_token_account [#to_s] Depositor's source token account.
|
|
16
|
+
# :mediated_escrow_deposit [#to_s] MediatedEscrowDeposit PDA.
|
|
17
|
+
# :program_token_account [#to_s] Per-mint program vault PDA.
|
|
18
|
+
# :fee_payer [#to_s, Keypair] Fee payer (writable signer).
|
|
19
|
+
# :amount [Integer] u64 amount to deposit.
|
|
20
|
+
# :id [#to_s] Unique id used to derive the escrow PDA.
|
|
21
|
+
# :mediator [#to_s] Mediator who decides the outcome.
|
|
22
|
+
# :beneficiary [#to_s] Beneficiary the mediator may release to.
|
|
23
|
+
#
|
|
24
|
+
# Optional params:
|
|
25
|
+
# :rent_collector [#to_s] Optional rent collector on close (default: nil).
|
|
26
|
+
# :expires_at [Integer] Optional unix timestamp for reclaim (default: nil).
|
|
27
|
+
# :program_id [#to_s] Escrow program id (default: PROGRAM_ID, mainnet).
|
|
28
|
+
# :token_program_id [#to_s] Token program (default: legacy SPL Token).
|
|
29
|
+
class ZarTrustlessEscrowMediatedDepositComposer < Base
|
|
30
|
+
# Extracts the mint address from the params
|
|
31
|
+
#
|
|
32
|
+
# @return [String] The mint address
|
|
33
|
+
def mint
|
|
34
|
+
params[:mint].to_s
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
# Extracts the depositor address from the params
|
|
38
|
+
#
|
|
39
|
+
# @return [String] The depositor address
|
|
40
|
+
def depositor
|
|
41
|
+
params[:depositor].to_s
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# Extracts the depositor's source token account from the params
|
|
45
|
+
#
|
|
46
|
+
# @return [String] The depositor token account address
|
|
47
|
+
def depositor_token_account
|
|
48
|
+
params[:depositor_token_account].to_s
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
# Extracts the MediatedEscrowDeposit PDA address from the params
|
|
52
|
+
#
|
|
53
|
+
# @return [String] The mediated escrow deposit address
|
|
54
|
+
def mediated_escrow_deposit
|
|
55
|
+
params[:mediated_escrow_deposit].to_s
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
# Extracts the per-mint program vault address from the params
|
|
59
|
+
#
|
|
60
|
+
# @return [String] The program token account address
|
|
61
|
+
def program_token_account
|
|
62
|
+
params[:program_token_account].to_s
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
# Extracts the fee payer address from the params
|
|
66
|
+
#
|
|
67
|
+
# @return [String] The fee payer address
|
|
68
|
+
def fee_payer
|
|
69
|
+
params[:fee_payer].to_s
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
# Extracts the deposit amount from the params
|
|
73
|
+
#
|
|
74
|
+
# @return [Integer] The u64 amount to deposit
|
|
75
|
+
def amount
|
|
76
|
+
params[:amount]
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
# Extracts the unique escrow id from the params
|
|
80
|
+
#
|
|
81
|
+
# @return [String] The escrow id
|
|
82
|
+
def id
|
|
83
|
+
params[:id].to_s
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
# Extracts the mediator from the params
|
|
87
|
+
#
|
|
88
|
+
# @return [String] The mediator address
|
|
89
|
+
def mediator
|
|
90
|
+
params[:mediator].to_s
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
# Extracts the beneficiary from the params
|
|
94
|
+
#
|
|
95
|
+
# @return [String] The beneficiary address
|
|
96
|
+
def beneficiary
|
|
97
|
+
params[:beneficiary].to_s
|
|
98
|
+
end
|
|
99
|
+
|
|
100
|
+
# Extracts the optional rent collector from the params
|
|
101
|
+
#
|
|
102
|
+
# @return [String, nil] The rent collector address, or nil
|
|
103
|
+
def rent_collector
|
|
104
|
+
params[:rent_collector]&.to_s
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
# Extracts the optional expiry timestamp from the params
|
|
108
|
+
#
|
|
109
|
+
# @return [Integer, nil] The unix expiry timestamp, or nil
|
|
110
|
+
def expires_at
|
|
111
|
+
params[:expires_at]
|
|
112
|
+
end
|
|
113
|
+
|
|
114
|
+
# Returns the escrow program id (defaults to the mainnet PROGRAM_ID)
|
|
115
|
+
#
|
|
116
|
+
# @return [String] The escrow program id
|
|
117
|
+
def program_id
|
|
118
|
+
(params[:program_id] || Solace::ZarTrustlessEscrow::PROGRAM_ID).to_s
|
|
119
|
+
end
|
|
120
|
+
|
|
121
|
+
# Returns the token program id (defaults to the legacy SPL Token program)
|
|
122
|
+
#
|
|
123
|
+
# @return [String] The token program id
|
|
124
|
+
def token_program_id
|
|
125
|
+
(params[:token_program_id] || Solace::Constants::TOKEN_PROGRAM_ID).to_s
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
# Returns the System Program id
|
|
129
|
+
#
|
|
130
|
+
# @return [String] The System Program id
|
|
131
|
+
def system_program
|
|
132
|
+
Solace::Constants::SYSTEM_PROGRAM_ID
|
|
133
|
+
end
|
|
134
|
+
|
|
135
|
+
# Declares all accounts required by this instruction.
|
|
136
|
+
def setup_accounts
|
|
137
|
+
account_context.add_readonly_nonsigner(mint)
|
|
138
|
+
account_context.add_writable_signer(depositor)
|
|
139
|
+
account_context.add_writable_nonsigner(depositor_token_account)
|
|
140
|
+
account_context.add_writable_nonsigner(mediated_escrow_deposit)
|
|
141
|
+
account_context.add_writable_nonsigner(program_token_account)
|
|
142
|
+
account_context.add_writable_signer(fee_payer)
|
|
143
|
+
account_context.add_readonly_nonsigner(system_program)
|
|
144
|
+
account_context.add_readonly_nonsigner(token_program_id)
|
|
145
|
+
account_context.add_readonly_nonsigner(program_id)
|
|
146
|
+
end
|
|
147
|
+
|
|
148
|
+
# Builds the instruction with resolved account indices.
|
|
149
|
+
#
|
|
150
|
+
# @param context [Solace::Utils::AccountContext] Merged context from TransactionComposer.
|
|
151
|
+
# @return [Solace::Instruction]
|
|
152
|
+
def build_instruction(context)
|
|
153
|
+
Solace::ZarTrustlessEscrow::Instructions::MediatedDepositInstruction.build(
|
|
154
|
+
amount:,
|
|
155
|
+
id:,
|
|
156
|
+
mediator:,
|
|
157
|
+
beneficiary:,
|
|
158
|
+
rent_collector:,
|
|
159
|
+
expires_at:,
|
|
160
|
+
mint_index: context.index_of(mint),
|
|
161
|
+
depositor_index: context.index_of(depositor),
|
|
162
|
+
depositor_token_account_index: context.index_of(depositor_token_account),
|
|
163
|
+
mediated_escrow_deposit_index: context.index_of(mediated_escrow_deposit),
|
|
164
|
+
program_token_account_index: context.index_of(program_token_account),
|
|
165
|
+
fee_payer_index: context.index_of(fee_payer),
|
|
166
|
+
system_program_index: context.index_of(system_program),
|
|
167
|
+
token_program_index: context.index_of(token_program_id),
|
|
168
|
+
program_index: context.index_of(program_id)
|
|
169
|
+
)
|
|
170
|
+
end
|
|
171
|
+
end
|
|
172
|
+
end
|
|
173
|
+
end
|
|
@@ -0,0 +1,137 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Solace
|
|
4
|
+
module Composers
|
|
5
|
+
# Composes a `mediated_reclaim` instruction for the ZAR Trustless Escrow
|
|
6
|
+
# program.
|
|
7
|
+
#
|
|
8
|
+
# After the escrow's expiry passes, the original depositor reclaims a
|
|
9
|
+
# MediatedEscrowDeposit and closes the deposit account (rent returns to the
|
|
10
|
+
# depositor). Requires the escrow to have been created with an expiry.
|
|
11
|
+
#
|
|
12
|
+
# Required params:
|
|
13
|
+
# :mint [#to_s] Mint of the escrowed tokens.
|
|
14
|
+
# :depositor [#to_s, Keypair] Depositor (writable signer, receives rent).
|
|
15
|
+
# :depositor_token_account [#to_s] Depositor's destination token account (ATA).
|
|
16
|
+
# :mediated_escrow_deposit [#to_s] MediatedEscrowDeposit PDA.
|
|
17
|
+
# :program_token_account [#to_s] Per-mint program vault PDA.
|
|
18
|
+
# :fee_payer [#to_s, Keypair] Fee payer (writable signer).
|
|
19
|
+
# :id [#to_s] Unique id used to derive the escrow PDA.
|
|
20
|
+
#
|
|
21
|
+
# Optional params:
|
|
22
|
+
# :program_id [#to_s] Escrow program id (default: PROGRAM_ID, mainnet).
|
|
23
|
+
# :token_program_id [#to_s] Token program (default: legacy SPL Token).
|
|
24
|
+
class ZarTrustlessEscrowMediatedReclaimComposer < Base
|
|
25
|
+
# Extracts the mint address from the params
|
|
26
|
+
#
|
|
27
|
+
# @return [String] The mint address
|
|
28
|
+
def mint
|
|
29
|
+
params[:mint].to_s
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
# Extracts the depositor address from the params
|
|
33
|
+
#
|
|
34
|
+
# @return [String] The depositor address
|
|
35
|
+
def depositor
|
|
36
|
+
params[:depositor].to_s
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
# Extracts the depositor's destination token account from the params
|
|
40
|
+
#
|
|
41
|
+
# @return [String] The depositor token account address
|
|
42
|
+
def depositor_token_account
|
|
43
|
+
params[:depositor_token_account].to_s
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
# Extracts the MediatedEscrowDeposit PDA address from the params
|
|
47
|
+
#
|
|
48
|
+
# @return [String] The mediated escrow deposit address
|
|
49
|
+
def mediated_escrow_deposit
|
|
50
|
+
params[:mediated_escrow_deposit].to_s
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
# Extracts the per-mint program vault address from the params
|
|
54
|
+
#
|
|
55
|
+
# @return [String] The program token account address
|
|
56
|
+
def program_token_account
|
|
57
|
+
params[:program_token_account].to_s
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
# Extracts the fee payer address from the params
|
|
61
|
+
#
|
|
62
|
+
# @return [String] The fee payer address
|
|
63
|
+
def fee_payer
|
|
64
|
+
params[:fee_payer].to_s
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
# Extracts the unique escrow id from the params
|
|
68
|
+
#
|
|
69
|
+
# @return [String] The escrow id
|
|
70
|
+
def id
|
|
71
|
+
params[:id].to_s
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
# Returns the escrow program id (defaults to the mainnet PROGRAM_ID)
|
|
75
|
+
#
|
|
76
|
+
# @return [String] The escrow program id
|
|
77
|
+
def program_id
|
|
78
|
+
(params[:program_id] || Solace::ZarTrustlessEscrow::PROGRAM_ID).to_s
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
# Returns the token program id (defaults to the legacy SPL Token program)
|
|
82
|
+
#
|
|
83
|
+
# @return [String] The token program id
|
|
84
|
+
def token_program_id
|
|
85
|
+
(params[:token_program_id] || Solace::Constants::TOKEN_PROGRAM_ID).to_s
|
|
86
|
+
end
|
|
87
|
+
|
|
88
|
+
# Returns the System Program id
|
|
89
|
+
#
|
|
90
|
+
# @return [String] The System Program id
|
|
91
|
+
def system_program
|
|
92
|
+
Solace::Constants::SYSTEM_PROGRAM_ID
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
# Returns the Associated Token Account Program id
|
|
96
|
+
#
|
|
97
|
+
# @return [String] The Associated Token Account Program id
|
|
98
|
+
def associated_token_program
|
|
99
|
+
Solace::Constants::ASSOCIATED_TOKEN_ACCOUNT_PROGRAM_ID
|
|
100
|
+
end
|
|
101
|
+
|
|
102
|
+
# Declares all accounts required by this instruction.
|
|
103
|
+
def setup_accounts
|
|
104
|
+
account_context.add_readonly_nonsigner(mint)
|
|
105
|
+
account_context.add_writable_signer(depositor)
|
|
106
|
+
account_context.add_writable_nonsigner(depositor_token_account)
|
|
107
|
+
account_context.add_writable_nonsigner(mediated_escrow_deposit)
|
|
108
|
+
account_context.add_writable_nonsigner(program_token_account)
|
|
109
|
+
account_context.add_writable_signer(fee_payer)
|
|
110
|
+
account_context.add_readonly_nonsigner(system_program)
|
|
111
|
+
account_context.add_readonly_nonsigner(token_program_id)
|
|
112
|
+
account_context.add_readonly_nonsigner(associated_token_program)
|
|
113
|
+
account_context.add_readonly_nonsigner(program_id)
|
|
114
|
+
end
|
|
115
|
+
|
|
116
|
+
# Builds the instruction with resolved account indices.
|
|
117
|
+
#
|
|
118
|
+
# @param context [Solace::Utils::AccountContext] Merged context from TransactionComposer.
|
|
119
|
+
# @return [Solace::Instruction]
|
|
120
|
+
def build_instruction(context)
|
|
121
|
+
Solace::ZarTrustlessEscrow::Instructions::MediatedReclaimInstruction.build(
|
|
122
|
+
id:,
|
|
123
|
+
mint_index: context.index_of(mint),
|
|
124
|
+
depositor_index: context.index_of(depositor),
|
|
125
|
+
depositor_token_account_index: context.index_of(depositor_token_account),
|
|
126
|
+
mediated_escrow_deposit_index: context.index_of(mediated_escrow_deposit),
|
|
127
|
+
program_token_account_index: context.index_of(program_token_account),
|
|
128
|
+
fee_payer_index: context.index_of(fee_payer),
|
|
129
|
+
system_program_index: context.index_of(system_program),
|
|
130
|
+
token_program_index: context.index_of(token_program_id),
|
|
131
|
+
associated_token_program_index: context.index_of(associated_token_program),
|
|
132
|
+
program_index: context.index_of(program_id)
|
|
133
|
+
)
|
|
134
|
+
end
|
|
135
|
+
end
|
|
136
|
+
end
|
|
137
|
+
end
|