Skip to content

Commit fd5baa6

Browse files
committed
chore: update composers
1 parent 29f5774 commit fd5baa6

File tree

6 files changed

+145
-147
lines changed

6 files changed

+145
-147
lines changed

examples/oft-solana-composer-library/Cargo.lock

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

examples/oft-solana-composer-library/programs/composer/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,4 +22,5 @@ anchor-spl = "0.29.0"
2222
raydium-clmm-cpi = { git = "https://github.com/St0rmBr3w/raydium-cpi/", package = "raydium-clmm-cpi", branch = "anchor-0.29.0" }
2323
oapp = { git = "https://github.com/LayerZero-Labs/LayerZero-v2.git", rev = "34321ac15e47e0dafd25d66659e2f3d1b9b6db8f" }
2424
utils = { git = "https://github.com/LayerZero-Labs/LayerZero-v2.git", rev = "34321ac15e47e0dafd25d66659e2f3d1b9b6db8f" }
25+
spl-memo = "=4.0.0"
2526
solana-helper = "0.1.0"
Lines changed: 84 additions & 62 deletions
Original file line numberDiff line numberDiff line change
@@ -1,63 +1,91 @@
1+
use crate::*;
12
use anchor_lang::prelude::*;
2-
use anchor_spl::token::{Token, TokenAccount};
3-
use anchor_spl::token_interface::{Token2022};
3+
use anchor_spl::token::{Token};
4+
use anchor_spl::token_interface::{Token2022, TokenAccount, Mint};
45
use raydium_clmm_cpi::cpi::accounts::SwapSingleV2;
56
use raydium_clmm_cpi::cpi::swap_v2;
6-
use std::str::FromStr;
7-
8-
// LayerZero / OApp endpoint CPI helpers:
7+
use raydium_clmm_cpi::{
8+
program::RaydiumClmm,
9+
states::{AmmConfig, ObservationState, PoolState},
10+
};
911
use oapp::endpoint::{instructions::ClearComposeParams, ID as ENDPOINT_ID};
10-
use oapp::endpoint_cpi::{clear_compose};
12+
use oapp::endpoint_cpi::clear_compose;
1113
use oapp::LzComposeParams;
12-
13-
// Use our minimal AmmV3 type instead of importing from the raydium_amm_v3 crate.
14-
#[derive(Clone, Debug)]
15-
pub struct AmmV3;
16-
17-
impl anchor_lang::Id for AmmV3 {
18-
fn id() -> Pubkey {
19-
Pubkey::from_str("CAMMCzo5YL8w4VFF8KVHrK22GGUsp5VTaW7grrKgrWqK").unwrap()
20-
}
21-
}
14+
use spl_memo;
2215

2316
#[derive(Accounts)]
2417
pub struct LzCompose<'info> {
25-
#[account(seeds = [b"composer"], bump)]
26-
pub lz_program: AccountInfo<'info>,
18+
// Use the stored “oft” field as the unique seed.
19+
#[account(
20+
mut,
21+
seeds = [COMPOSER_SEED, &composer.oft.to_bytes()],
22+
bump = composer.bump
23+
)]
24+
pub composer: Account<'info, Composer>,
25+
26+
pub clmm_program: Program<'info, RaydiumClmm>,
27+
/// The user performing the swap.
2728
pub payer: Signer<'info>,
28-
#[account(seeds = [b"authority"], bump)]
29-
pub authority: AccountInfo<'info>,
30-
pub amm_config: AccountInfo<'info>,
29+
30+
/// The factory state to read protocol fees.
31+
#[account(address = pool_state.load()?.amm_config)]
32+
pub amm_config: Box<Account<'info, AmmConfig>>,
33+
34+
/// The program account of the pool in which the swap will be performed.
3135
#[account(mut)]
32-
pub pool_state: AccountInfo<'info>,
36+
pub pool_state: AccountLoader<'info, PoolState>,
37+
38+
/// The user token account for input token.
3339
#[account(mut)]
34-
pub source_token_account: Account<'info, TokenAccount>,
40+
pub input_token_account: Box<InterfaceAccount<'info, TokenAccount>>,
41+
42+
/// The user token account for output token.
3543
#[account(mut)]
36-
pub dest_token_account: Account<'info, TokenAccount>,
44+
pub output_token_account: Box<InterfaceAccount<'info, TokenAccount>>,
45+
46+
/// The vault token account for input token.
3747
#[account(mut)]
38-
pub input_vault: AccountInfo<'info>,
48+
pub input_vault: Box<InterfaceAccount<'info, TokenAccount>>,
49+
50+
/// The vault token account for output token.
3951
#[account(mut)]
40-
pub output_vault: AccountInfo<'info>,
52+
pub output_vault: Box<InterfaceAccount<'info, TokenAccount>>,
53+
54+
/// The program account for the most recent oracle observation.
55+
#[account(mut, address = pool_state.load()?.observation_key)]
56+
pub observation_state: AccountLoader<'info, ObservationState>,
57+
58+
/// SPL program for token transfers.
4159
pub token_program: Program<'info, Token>,
60+
61+
/// SPL program 2022 for token transfers.
4262
pub token_program_2022: Program<'info, Token2022>,
43-
#[account(mut)]
44-
pub input_token_mint: AccountInfo<'info>,
45-
#[account(mut)]
46-
pub output_token_mint: AccountInfo<'info>,
47-
#[account(mut)]
48-
pub observation_state: AccountInfo<'info>,
49-
/// CHECK: Required for memo instructions.
50-
pub memo_program: AccountInfo<'info>,
63+
64+
/// CHECK: Must match spl_memo::id().
65+
#[account(address = spl_memo::id())]
66+
pub memo_program: UncheckedAccount<'info>,
67+
68+
/// The mint of the input token vault.
69+
#[account(address = input_vault.mint)]
70+
pub input_vault_mint: Box<InterfaceAccount<'info, Mint>>,
71+
72+
/// The mint of the output token vault.
73+
#[account(address = output_vault.mint)]
74+
pub output_vault_mint: Box<InterfaceAccount<'info, Mint>>,
75+
76+
// Extra accounts required by the CPI.
77+
/// The authority account for the swap.
78+
pub authority: AccountInfo<'info>,
79+
80+
/// Tick arrays for the swap range.
5181
#[account(mut)]
5282
pub tick_array_lower: AccountInfo<'info>,
5383
#[account(mut)]
5484
pub tick_array_current: AccountInfo<'info>,
5585
#[account(mut)]
5686
pub tick_array_upper: AccountInfo<'info>,
57-
pub raydium_program: Program<'info, AmmV3>,
5887
}
5988

60-
/// Processes the lz_compose instruction.
6189
impl LzCompose<'_> {
6290
pub fn apply(ctx: &mut Context<LzCompose>, params: &LzComposeParams) -> Result<()> {
6391
let msg = &params.message;
@@ -66,38 +94,33 @@ impl LzCompose<'_> {
6694
let mut compose_from = [0u8; 32];
6795
compose_from.copy_from_slice(&msg[40..72]);
6896
let inner = &msg[72..];
69-
7097
let min_amount_out = u64::from_be_bytes(inner[0..8].try_into().unwrap());
7198

72-
// Build the CPI accounts struct for Raydium's SwapSingleV2.
99+
// Build CPI accounts struct.
73100
let cpi_accounts = SwapSingleV2 {
74101
payer: ctx.accounts.payer.to_account_info(),
75102
amm_config: ctx.accounts.amm_config.to_account_info(),
76103
pool_state: ctx.accounts.pool_state.to_account_info(),
77-
input_token_account: ctx.accounts.source_token_account.to_account_info(),
78-
output_token_account: ctx.accounts.dest_token_account.to_account_info(),
104+
input_token_account: ctx.accounts.input_token_account.to_account_info(),
105+
output_token_account: ctx.accounts.output_token_account.to_account_info(),
79106
input_vault: ctx.accounts.input_vault.to_account_info(),
80107
output_vault: ctx.accounts.output_vault.to_account_info(),
81108
observation_state: ctx.accounts.observation_state.to_account_info(),
82109
token_program: ctx.accounts.token_program.to_account_info(),
83110
token_program_2022: ctx.accounts.token_program_2022.to_account_info(),
84111
memo_program: ctx.accounts.memo_program.to_account_info(),
85-
input_vault_mint: ctx.accounts.input_token_mint.to_account_info(),
86-
output_vault_mint: ctx.accounts.output_token_mint.to_account_info(),
112+
input_vault_mint: ctx.accounts.input_vault_mint.to_account_info(),
113+
output_vault_mint: ctx.accounts.output_vault_mint.to_account_info(),
87114
};
88115

89-
// Build the CPI context with the Raydium CLMM program.
90-
let mut cpi_ctx =
91-
CpiContext::new(ctx.accounts.raydium_program.to_account_info(), cpi_accounts);
92-
93-
// Attach remaining accounts in the exact order required.
116+
let mut cpi_ctx = CpiContext::new(ctx.accounts.clmm_program.to_account_info(), cpi_accounts);
94117
cpi_ctx = cpi_ctx.with_remaining_accounts(vec![
95118
ctx.accounts.payer.to_account_info(),
96119
ctx.accounts.authority.to_account_info(),
97120
ctx.accounts.amm_config.to_account_info(),
98121
ctx.accounts.pool_state.to_account_info(),
99-
ctx.accounts.source_token_account.to_account_info(),
100-
ctx.accounts.dest_token_account.to_account_info(),
122+
ctx.accounts.input_token_account.to_account_info(),
123+
ctx.accounts.output_token_account.to_account_info(),
101124
ctx.accounts.input_vault.to_account_info(),
102125
ctx.accounts.output_vault.to_account_info(),
103126
ctx.accounts.observation_state.to_account_info(),
@@ -106,29 +129,28 @@ impl LzCompose<'_> {
106129
ctx.accounts.tick_array_upper.to_account_info(),
107130
]);
108131

109-
// Execute the CPI swap call.
110-
swap_v2(
111-
cpi_ctx,
112-
amount_ld,
113-
min_amount_out,
114-
0u128, // sqrt_price_limit_x64 (adjust as needed)
115-
true, // is_base_input
116-
)?;
132+
swap_v2(cpi_ctx, amount_ld, min_amount_out, 0u128, true)?;
133+
134+
// Use the stored "oft" field as the seed instead of a non-existent “id”.
135+
let seeds: &[&[u8]] = &[
136+
COMPOSER_SEED,
137+
&ctx.accounts.composer.oft.to_bytes(),
138+
&[ctx.accounts.composer.bump],
139+
];
117140

118-
// Clear the LayerZero compose message.
119141
let clear_params = ClearComposeParams {
120-
from: compose_from.into(),
142+
from: params.from,
121143
guid: params.guid,
122144
index: params.index,
123145
message: params.message.clone(),
124146
};
125147

126148
clear_compose(
127149
ENDPOINT_ID,
128-
ctx.accounts.lz_program.key(),
150+
ctx.accounts.composer.key(),
129151
&ctx.remaining_accounts,
130-
&[b"composer"],
152+
seeds,
131153
clear_params,
132154
)
133155
}
134-
}
156+
}

0 commit comments

Comments
 (0)