LP 交互
创建 LP 交易
添加流动性 / 铸造 sFLP
const addLiquidityAndStake = async () => {
const usdcInputAmount = new BN(1_000_000); // $1
// 这可以是池中可用的任何其他代币,例如 SOL、BTC 和 ETH
const usdcCustody = POOL_CONFIG.custodies.find(c => c.symbol === 'USDC')!;
const slippageBps: number = 800 // 0.8%
let instructions: TransactionInstruction[] = []
let additionalSigners: Signer[] = []
await flashClient.loadAddressLookupTable(POOL_CONFIG)
// flash-sdk 版本 >= 2.31.6
const { amount: minLpAmountOut, fee } = await flashClient.getAddLiquidityAmountAndFeeView(usdcInputAmount, POOL_CONFIG.poolAddress, usdcCustody.custodyAccount, POOL_CONFIG);
const minLpAmountOutAfterSlippage = minLpAmountOut
.mul(new BN(10 ** BPS_DECIMALS - slippageBps))
.div(new BN(10 ** BPS_DECIMALS))
const setCULimitIx = ComputeBudgetProgram.setComputeUnitLimit({ units: 400_000 }) // addLiquidity
const addLiquidityAndStakeData = await flashClient.addLiquidityAndStake('USDC', usdcInputAmount, minLpAmountOutAfterSlippage, POOL_CONFIG);
instructions.push(...addLiquidityAndStakeData.instructions)
additionalSigners.push(...addLiquidityAndStakeData.additionalSigners)
const flpStakeAccountPK = PublicKey.findProgramAddressSync(
[Buffer.from('stake'), flashClient.provider.publicKey.toBuffer(), POOL_CONFIG.poolAddress.toBuffer()],
POOL_CONFIG.programId
)[0]
const refreshStakeInstruction = await flashClient.refreshStake('USDC', POOL_CONFIG, [flpStakeAccountPK])
instructions.push(refreshStakeInstruction)
const trxId = await flashClient.sendTransaction([setCULimitIx, ...instructions])
console.log('addLiquidityAndStake trx :>> ', trxId);
}
添加复投流动性 / 铸造 FLP
const addCompoundingLiquidity = async () => {
// USDC 及其小数位数
const usdcInputAmount = new BN(1_000_000); // $1
// 这可以是池中可用的任何其他代币,例如 SOL、BTC 和 ETH
const usdcCustody = POOL_CONFIG.custodies.find(c => c.symbol === 'USDC')!;
const slippageBps: number = 800 // 0.8%
let instructions: TransactionInstruction[] = []
let additionalSigners: Signer[] = []
await flashClient.loadAddressLookupTable(POOL_CONFIG)
// flash-sdk 版本 >= 2.31.6
const { amount: minLpAmountOut, fee } = await flashClient.getAddCompoundingLiquidityAmountAndFeeView(usdcInputAmount, POOL_CONFIG.poolAddress, usdcCustody.custodyAccount, POOL_CONFIG);
const minLpAmountOutAfterSlippage = minLpAmountOut
.mul(new BN(10 ** BPS_DECIMALS - slippageBps))
.div(new BN(10 ** BPS_DECIMALS))
const setCULimitIx = ComputeBudgetProgram.setComputeUnitLimit({ units: 400_000 }) // addLiquidity
const addCompoundingLiquidityData = await flashClient.addCompoundingLiquidity(
usdcInputAmount,
minLpAmountOutAfterSlippage,
'USDC',
usdcCustody.mintKey,
POOL_CONFIG
)
instructions.push(...addCompoundingLiquidityData.instructions)
additionalSigners.push(...addCompoundingLiquidityData.additionalSigners)
const trxId = await flashClient.sendTransaction([setCULimitIx, ...instructions])
console.log('addCompoundingLiquidity trx :>> ', trxId);
}
移除流动性 / 销毁 sFLP
const removeSflpLiquidity = async () => {
const usdcCustody = POOL_CONFIG.custodies.find(c => c.symbol === 'USDC')!;
const slippageBps: number = 800 // 0.8%
let instructions: TransactionInstruction[] = []
let additionalSigners: Signer[] = []
await flashClient.loadAddressLookupTable(POOL_CONFIG)
const flpStakeAccountPK = PublicKey.findProgramAddressSync(
[Buffer.from('stake'), flashClient.provider.publicKey.toBuffer(), POOL_CONFIG.poolAddress.toBuffer()],
POOL_CONFIG.programId
)[0]
const flpStakeAccount = await flashClient.program.account.flpStake.fetch(flpStakeAccountPK);
const flpWithPendingAndActive =
flpStakeAccount?.stakeStats.activeAmount.add(flpStakeAccount?.stakeStats.pendingActivation) ??
BN_ZERO
// flash-sdk version >= 2.31.6
const { amount: minTokenAmountOut, fee } = await flashClient.getRemoveLiquidityAmountAndFeeView(flpWithPendingAndActive, POOL_CONFIG.poolAddress, usdcCustody.custodyAccount, POOL_CONFIG);
const { instructions: unstakeInstantInstructions, additionalSigners: unstakeInstantAdditionalSigners } =
await flashClient.unstakeInstant('USDC', flpWithPendingAndActive, POOL_CONFIG)
const { instructions: withdrawStakeInstructions, additionalSigners: withdrawStakeAdditionalSigners } =
await flashClient.withdrawStake(POOL_CONFIG, true, true)
instructions.push(...unstakeInstantInstructions)
additionalSigners.push(...unstakeInstantAdditionalSigners)
instructions.push(...withdrawStakeInstructions)
additionalSigners.push(...withdrawStakeAdditionalSigners)
const minTokenAmountOutAfterSlippage = minTokenAmountOut
.mul(new BN(10 ** BPS_DECIMALS - slippageBps))
.div(new BN(10 ** BPS_DECIMALS))
const removeLiquidityData = await flashClient.removeLiquidity(
'USDC',
flpWithPendingAndActive,
minTokenAmountOutAfterSlippage,
POOL_CONFIG
)
instructions.push(...removeLiquidityData.instructions)
additionalSigners.push(...removeLiquidityData.additionalSigners)
const setCULimitIx = ComputeBudgetProgram.setComputeUnitLimit({ units: 400_000 }) // addLiquidity
const trxId = await flashClient.sendTransaction([setCULimitIx, ...instructions])
console.log('trx :>> ', trxId);
}
移除复投流动性 / 销毁 FLP
const removeFlpLiquidity = async () => {
const usdcCustody = POOL_CONFIG.custodies.find(c => c.symbol === 'USDC')!;
const slippageBps: number = 800 // 0.8%
let instructions: TransactionInstruction[] = []
let additionalSigners: Signer[] = []
const usdcToken = POOL_CONFIG.tokens.find(t => t.symbol === 'USDC')!;
await flashClient.loadAddressLookupTable(POOL_CONFIG)
const account = getAssociatedTokenAddressSync(POOL_CONFIG.compoundingTokenMint, flashClient.provider.publicKey, true)
const walletBalance = await flashClient.provider.connection.getTokenAccountBalance(account, 'processed')
const compoundingTokenBalance = new BN(walletBalance.value.amount)
// flash-sdk version >= 2.31.6
const { amount: minTokenAmountOut, fee } = await flashClient.getRemoveCompoundingLiquidityAmountAndFeeView(compoundingTokenBalance, POOL_CONFIG.poolAddress, usdcCustody.custodyAccount, POOL_CONFIG);
const minTokenAmountOutAfterSlippage = minTokenAmountOut
.mul(new BN(10 ** BPS_DECIMALS - slippageBps))
.div(new BN(10 ** BPS_DECIMALS))
const removeCompoundingLiquidityData = await flashClient.removeCompoundingLiquidity(
compoundingTokenBalance,
minTokenAmountOutAfterSlippage,
'USDC',
usdcToken.mintKey,
POOL_CONFIG,
true
)
instructions.push(...removeCompoundingLiquidityData.instructions)
additionalSigners.push(...removeCompoundingLiquidityData.additionalSigners)
const setCULimitIx = ComputeBudgetProgram.setComputeUnitLimit({ units: 400_000 }) // addLiquidity
const trxId = await flashClient.sendTransaction([setCULimitIx, ...instructions])
console.log('trx :>> ', trxId);
}
获取 FLP/sFLP 代币价格
1.) 使用 SDK(高级集成)
const getLpTokenPrices = async () => {
await flashClient.loadAddressLookupTable(POOL_CONFIG)
const stakedLpPrice = await flashClient.getStakedLpTokenPrice(POOL_CONFIG.poolAddress, POOL_CONFIG); // sFLP 价格
const compoundingLPTokenPrice = await flashClient.getCompoundingLPTokenPrice(POOL_CONFIG.poolAddress, POOL_CONFIG); // FLP 价格
console.log('stakedLpPrice :>> ', stakedLpPrice);
console.log('compoundingLPTokenPrice :>> ', compoundingLPTokenPrice);
}
2.) 使用 API(快速简便)
查询以下端点以获取所有池的价格数据:
https://api.prod.flash.trade/earn-page/data
✅ 响应格式(示例)
响应是一个包含 pools
数组的 JSON 对象,每个代表一个独特的 FLP 池。以下是每个键的含义:
字段
描述
poolAddress
流动性池的唯一链上地址
aum
此池的管理资产(以美元计)
flpTokenSymbol
复投 FLP 代币的符号(例如,FLP.1
、FLP.2
)
sFlpTokenSymbol
质押 FLP 代币的符号(例如,sFLP.1
、sFLP.2
)
flpDailyApy
复投 FLP 代币的日 APY(自动再投资)
flpWeeklyApy
复投 FLP 代币的周 APY
flpWeeklyApr
复投 FLP 代币的周 APR(非复投)
sFlpDailyApr
质押 FLP 代币的日 APR(非复投)
sFlpPrice
质押 FLP 代币的当前价格
flpPrice
复投 FLP 代币的当前价格
sFlpPriceWithYield
如果收益包含在估值中,sFLP 代币的衍生价格
🔎 如何使用
获取代币价格:
匹配
flpTokenSymbol
(例如,"FLP.1"
)或poolAddress
来识别您想要的池。对于复投 FLP 代币使用
flpPrice
,对于质押版本使用sFlpPrice
。
这是需要实时价格和收益数据的前端和仪表板的最简单方法,无需设置 SDK 或查询区块链。
最后更新于
这有帮助吗?