@exponent-labs/exponent-sdk 0.0.3
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.
- package/CHANGELOG.md +16 -0
- package/build/addressLookupTableUtil.d.ts +12 -0
- package/build/addressLookupTableUtil.js +32 -0
- package/build/addressLookupTableUtil.js.map +1 -0
- package/build/environment.d.ts +10 -0
- package/build/environment.js +13 -0
- package/build/environment.js.map +1 -0
- package/build/events.d.ts +339 -0
- package/build/events.js +231 -0
- package/build/events.js.map +1 -0
- package/build/flavors.d.ts +24 -0
- package/build/flavors.js +713 -0
- package/build/flavors.js.map +1 -0
- package/build/index.d.ts +11 -0
- package/build/index.js +45 -0
- package/build/index.js.map +1 -0
- package/build/lpPosition.d.ts +35 -0
- package/build/lpPosition.js +103 -0
- package/build/lpPosition.js.map +1 -0
- package/build/market.d.ts +567 -0
- package/build/market.js +1445 -0
- package/build/market.js.map +1 -0
- package/build/syPosition.d.ts +6 -0
- package/build/syPosition.js +115 -0
- package/build/syPosition.js.map +1 -0
- package/build/tokenUtil.d.ts +3 -0
- package/build/tokenUtil.js +23 -0
- package/build/tokenUtil.js.map +1 -0
- package/build/utils/altUtil.d.ts +8 -0
- package/build/utils/altUtil.js +35 -0
- package/build/utils/altUtil.js.map +1 -0
- package/build/utils/binSolver.d.ts +1 -0
- package/build/utils/binSolver.js +45 -0
- package/build/utils/binSolver.js.map +1 -0
- package/build/utils/binSolver.test.d.ts +1 -0
- package/build/utils/binSolver.test.js +15 -0
- package/build/utils/binSolver.test.js.map +1 -0
- package/build/utils/index.d.ts +6 -0
- package/build/utils/index.js +31 -0
- package/build/utils/index.js.map +1 -0
- package/build/utils/ix.d.ts +6 -0
- package/build/utils/ix.js +3 -0
- package/build/utils/ix.js.map +1 -0
- package/build/vault.d.ts +289 -0
- package/build/vault.js +615 -0
- package/build/vault.js.map +1 -0
- package/build/ytPosition.d.ts +86 -0
- package/build/ytPosition.js +231 -0
- package/build/ytPosition.js.map +1 -0
- package/jest.config.js +5 -0
- package/package.json +42 -0
- package/src/addressLookupTableUtil.ts +34 -0
- package/src/environment.ts +19 -0
- package/src/events.ts +595 -0
- package/src/flavors.ts +773 -0
- package/src/index.ts +11 -0
- package/src/lpPosition.ts +129 -0
- package/src/market.ts +2338 -0
- package/src/syPosition.ts +151 -0
- package/src/tokenUtil.ts +20 -0
- package/src/utils/altUtil.ts +47 -0
- package/src/utils/binSolver.test.ts +15 -0
- package/src/utils/binSolver.ts +44 -0
- package/src/utils/index.ts +32 -0
- package/src/utils/ix.ts +7 -0
- package/src/vault.ts +999 -0
- package/src/ytPosition.ts +313 -0
- package/tsconfig.json +38 -0
package/build/market.js
ADDED
|
@@ -0,0 +1,1445 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.Market = exports.MyWallet = void 0;
|
|
4
|
+
const anchor_1 = require("@coral-xyz/anchor");
|
|
5
|
+
const exponent_fetcher_1 = require("@exponent-labs/exponent-fetcher");
|
|
6
|
+
const exponent_ix_1 = require("@exponent-labs/exponent-ix");
|
|
7
|
+
const spl_token_1 = require("@solana/spl-token");
|
|
8
|
+
const addressLookupTableUtil_1 = require("./addressLookupTableUtil");
|
|
9
|
+
const tokenUtil_1 = require("./tokenUtil");
|
|
10
|
+
const flavors_1 = require("./flavors");
|
|
11
|
+
const exponent_idl_1 = require("@exponent-labs/exponent-idl");
|
|
12
|
+
const anchor_2 = require("@coral-xyz/anchor");
|
|
13
|
+
const exponent_pda_1 = require("@exponent-labs/exponent-pda");
|
|
14
|
+
const vault_1 = require("./vault");
|
|
15
|
+
const market_math_1 = require("@exponent-labs/market-math");
|
|
16
|
+
const utils_1 = require("./utils");
|
|
17
|
+
const precise_number_1 = require("@exponent-labs/precise-number");
|
|
18
|
+
const altUtil_1 = require("./utils/altUtil");
|
|
19
|
+
const syPosition_1 = require("./syPosition");
|
|
20
|
+
const exponent_ix_2 = require("@exponent-labs/exponent-ix");
|
|
21
|
+
const SECONDS_PER_YEAR = 365 * 24 * 60 * 60;
|
|
22
|
+
class MyWallet {
|
|
23
|
+
payer;
|
|
24
|
+
constructor(payer) {
|
|
25
|
+
this.payer = payer;
|
|
26
|
+
this.payer = payer;
|
|
27
|
+
}
|
|
28
|
+
async signTransaction(tx) {
|
|
29
|
+
if (tx instanceof anchor_1.web3.Transaction) {
|
|
30
|
+
tx.partialSign(this.payer);
|
|
31
|
+
}
|
|
32
|
+
else {
|
|
33
|
+
tx.sign([this.payer]);
|
|
34
|
+
}
|
|
35
|
+
return tx;
|
|
36
|
+
}
|
|
37
|
+
async signAllTransactions(txs) {
|
|
38
|
+
return txs.map((t) => {
|
|
39
|
+
if (t instanceof anchor_1.web3.Transaction) {
|
|
40
|
+
t.partialSign(this.payer);
|
|
41
|
+
}
|
|
42
|
+
else if (t instanceof anchor_1.web3.VersionedTransaction) {
|
|
43
|
+
t.sign([this.payer]);
|
|
44
|
+
}
|
|
45
|
+
return t;
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
get publicKey() {
|
|
49
|
+
return this.payer.publicKey;
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
exports.MyWallet = MyWallet;
|
|
53
|
+
class Market {
|
|
54
|
+
state;
|
|
55
|
+
selfAddress;
|
|
56
|
+
env;
|
|
57
|
+
connection;
|
|
58
|
+
coreProgram;
|
|
59
|
+
xponIx;
|
|
60
|
+
xponPda;
|
|
61
|
+
constructor(state, selfAddress, env, connection) {
|
|
62
|
+
this.state = state;
|
|
63
|
+
this.selfAddress = selfAddress;
|
|
64
|
+
this.env = env;
|
|
65
|
+
this.connection = connection;
|
|
66
|
+
this.xponPda = new exponent_pda_1.ExponentPDA(env.coreProgramId);
|
|
67
|
+
this.xponIx = new exponent_ix_1.ExponentIx(env.coreProgramId);
|
|
68
|
+
const mockWallet = new MyWallet(anchor_1.web3.Keypair.generate());
|
|
69
|
+
this.coreProgram = new anchor_1.Program(exponent_idl_1.IDL, new anchor_1.AnchorProvider(connection, mockWallet));
|
|
70
|
+
}
|
|
71
|
+
static async load(env, connection, address, vault) {
|
|
72
|
+
const fetcher = new exponent_fetcher_1.ExponentFetcher({ connection });
|
|
73
|
+
const m = await fetcher.fetchMarket(address);
|
|
74
|
+
const [[lpSupply, sySupply], alt, loadedVault] = await Promise.all([
|
|
75
|
+
(0, tokenUtil_1.getMultipleMintSupply)(connection, [m.mintLp, m.mintSy]),
|
|
76
|
+
(0, addressLookupTableUtil_1.fetchAddressLookupTable)(connection, m.addressLookupTable),
|
|
77
|
+
vault || vault_1.Vault.load(env, connection, m.vault),
|
|
78
|
+
]);
|
|
79
|
+
const cpiAccounts = (0, addressLookupTableUtil_1.makeCpiAccountMetaLists)(alt, m.cpiAccounts);
|
|
80
|
+
const flavor = (() => {
|
|
81
|
+
switch (loadedVault.flavor.flavor) {
|
|
82
|
+
case "marginfi":
|
|
83
|
+
return (0, flavors_1.makeFlavorMarginfiSync)(loadedVault.flavor);
|
|
84
|
+
case "kamino":
|
|
85
|
+
return (0, flavors_1.makeFlavorKaminoSync)(loadedVault.flavor);
|
|
86
|
+
case "jitoRestaking":
|
|
87
|
+
return (0, flavors_1.makeFlavorJitoRestakingSync)(loadedVault.flavor);
|
|
88
|
+
case "perena":
|
|
89
|
+
return (0, flavors_1.makeFlavorPerenaSync)(loadedVault.flavor);
|
|
90
|
+
case "generic":
|
|
91
|
+
return (0, flavors_1.makeFlavorGenericSync)(loadedVault.flavor);
|
|
92
|
+
default:
|
|
93
|
+
throw new Error(`Unknown flavor: ${loadedVault.flavor}`);
|
|
94
|
+
}
|
|
95
|
+
})();
|
|
96
|
+
const syPosition = await (0, syPosition_1.makeSyPosition)(fetcher, flavor, m.syProgram, address);
|
|
97
|
+
const state = {
|
|
98
|
+
...m,
|
|
99
|
+
vault: loadedVault,
|
|
100
|
+
cpiAccounts,
|
|
101
|
+
lpSupply,
|
|
102
|
+
sySupply,
|
|
103
|
+
flavor,
|
|
104
|
+
syPosition,
|
|
105
|
+
};
|
|
106
|
+
return new Market(state, address, env, connection);
|
|
107
|
+
}
|
|
108
|
+
async reload(conn = this.connection) {
|
|
109
|
+
const m = await Market.load(this.env, conn, this.selfAddress);
|
|
110
|
+
this.state = m.state;
|
|
111
|
+
return m;
|
|
112
|
+
}
|
|
113
|
+
/** Convert to a JSON representation */
|
|
114
|
+
toJson() {
|
|
115
|
+
return toJson(this);
|
|
116
|
+
}
|
|
117
|
+
get vault() {
|
|
118
|
+
return this.state.vault;
|
|
119
|
+
}
|
|
120
|
+
get flavor() {
|
|
121
|
+
return this.state.flavor;
|
|
122
|
+
}
|
|
123
|
+
get lpSupply() {
|
|
124
|
+
return this.state.lpSupply;
|
|
125
|
+
}
|
|
126
|
+
get syBalance() {
|
|
127
|
+
return this.state.syBalance;
|
|
128
|
+
}
|
|
129
|
+
get ptBalance() {
|
|
130
|
+
return this.state.ptBalance;
|
|
131
|
+
}
|
|
132
|
+
get mintSy() {
|
|
133
|
+
return this.state.mintSy;
|
|
134
|
+
}
|
|
135
|
+
get mintPt() {
|
|
136
|
+
return this.state.mintPt;
|
|
137
|
+
}
|
|
138
|
+
get statusFlags() {
|
|
139
|
+
return this.state.statusFlags;
|
|
140
|
+
}
|
|
141
|
+
get mintYt() {
|
|
142
|
+
return this.vault.mintYt;
|
|
143
|
+
}
|
|
144
|
+
get mintLp() {
|
|
145
|
+
return this.state.mintLp;
|
|
146
|
+
}
|
|
147
|
+
get addressLookupTable() {
|
|
148
|
+
return this.state.addressLookupTable;
|
|
149
|
+
}
|
|
150
|
+
get syProgram() {
|
|
151
|
+
return this.state.syProgram;
|
|
152
|
+
}
|
|
153
|
+
get cpiAccounts() {
|
|
154
|
+
return this.state.cpiAccounts;
|
|
155
|
+
}
|
|
156
|
+
get marketEmissions() {
|
|
157
|
+
return this.state.emissions;
|
|
158
|
+
}
|
|
159
|
+
get emissions() {
|
|
160
|
+
if (this.flavor.flavor === "marginfi") {
|
|
161
|
+
return this.flavor.mfiSyState.account.emissions.map((e) => ({
|
|
162
|
+
escrowAccountAddress: e.escrowAccount,
|
|
163
|
+
mint: e.mint,
|
|
164
|
+
tokenProgramAddress: e.tokenProgram,
|
|
165
|
+
totalClaimed: BigInt(e.totalClaimedEmissions.toString()),
|
|
166
|
+
lastSeenTotalAccruedEmissions: BigInt(e.lastSeenTotalAccruedEmissions.toString()),
|
|
167
|
+
index: e.index,
|
|
168
|
+
}));
|
|
169
|
+
}
|
|
170
|
+
if (this.flavor.flavor === "kamino") {
|
|
171
|
+
return this.flavor.kaminoSyState.account.emissions.map((e) => ({
|
|
172
|
+
escrowAccountAddress: e.escrowAccount,
|
|
173
|
+
mint: e.mint,
|
|
174
|
+
tokenProgramAddress: e.tokenProgram,
|
|
175
|
+
totalClaimed: BigInt(e.totalClaimedEmissions.toString()),
|
|
176
|
+
lastSeenTotalAccruedEmissions: BigInt(e.lastSeenTotalAccruedEmissions.toString()),
|
|
177
|
+
index: e.index,
|
|
178
|
+
}));
|
|
179
|
+
}
|
|
180
|
+
if (this.flavor.flavor === "jitoRestaking") {
|
|
181
|
+
return this.flavor.jitoSyState.account.emissions.map((e) => ({
|
|
182
|
+
escrowAccountAddress: e.escrowAccount,
|
|
183
|
+
mint: e.mint,
|
|
184
|
+
tokenProgramAddress: e.tokenProgram,
|
|
185
|
+
totalClaimed: BigInt(e.totalClaimedEmissions.toString()),
|
|
186
|
+
lastSeenTotalAccruedEmissions: BigInt(e.lastSeenTotalAccruedEmissions.toString()),
|
|
187
|
+
index: e.index,
|
|
188
|
+
}));
|
|
189
|
+
}
|
|
190
|
+
if (this.flavor.flavor === "perena") {
|
|
191
|
+
return this.flavor.perenaSyState.account.emissions.map((e) => ({
|
|
192
|
+
escrowAccountAddress: e.escrowAccount,
|
|
193
|
+
mint: e.mint,
|
|
194
|
+
tokenProgramAddress: e.tokenProgram,
|
|
195
|
+
totalClaimed: BigInt(e.totalClaimedEmissions.toString()),
|
|
196
|
+
lastSeenTotalAccruedEmissions: BigInt(e.lastSeenTotalAccruedEmissions.toString()),
|
|
197
|
+
index: e.index,
|
|
198
|
+
}));
|
|
199
|
+
}
|
|
200
|
+
if (this.flavor.flavor === "generic") {
|
|
201
|
+
return this.flavor.genericSyState.account.emissions.map((e) => ({
|
|
202
|
+
escrowAccountAddress: e.escrowAccount,
|
|
203
|
+
mint: e.mint,
|
|
204
|
+
tokenProgramAddress: e.tokenProgram,
|
|
205
|
+
totalClaimed: BigInt(e.totalClaimedEmissions.toString()),
|
|
206
|
+
lastSeenTotalAccruedEmissions: BigInt(e.lastSeenTotalAccruedEmissions.toString()),
|
|
207
|
+
index: e.index,
|
|
208
|
+
}));
|
|
209
|
+
}
|
|
210
|
+
throw new Error("Unknown flavor");
|
|
211
|
+
}
|
|
212
|
+
/** Get the escrow token account addresses for the emissions, in order */
|
|
213
|
+
get emissionTokenAccounts() {
|
|
214
|
+
return this.emissions.map((e) => e.escrowAccountAddress);
|
|
215
|
+
}
|
|
216
|
+
/** Pass-through SY account owned by the market */
|
|
217
|
+
get tokenSyEscrow() {
|
|
218
|
+
return this.state.tokenSyEscrow;
|
|
219
|
+
}
|
|
220
|
+
/** SY account that holds treasury SY fees from PT trading */
|
|
221
|
+
get tokenFeeTreasurySy() {
|
|
222
|
+
return this.state.tokenFeeTreasurySy;
|
|
223
|
+
}
|
|
224
|
+
/** Market liquidity for PT */
|
|
225
|
+
get tokenPtEscrow() {
|
|
226
|
+
return this.state.tokenPtEscrow;
|
|
227
|
+
}
|
|
228
|
+
get tokenLpEscrow() {
|
|
229
|
+
return this.state.tokenLpEscrow;
|
|
230
|
+
}
|
|
231
|
+
get currentSyExchangeRate() {
|
|
232
|
+
return this.flavor.currentSyExchangeRate;
|
|
233
|
+
}
|
|
234
|
+
/** Special account for event emit self-cpi */
|
|
235
|
+
get eventAuthority() {
|
|
236
|
+
return (0, utils_1.emitEventAuthority)(this.env.coreProgramId);
|
|
237
|
+
}
|
|
238
|
+
get currentPtPriceInSy() {
|
|
239
|
+
return this.currentPtPriceInAsset / this.currentSyExchangeRate;
|
|
240
|
+
}
|
|
241
|
+
get currentPtPriceInAsset() {
|
|
242
|
+
const c = this.marketCalculator();
|
|
243
|
+
return c.exchangeRate;
|
|
244
|
+
}
|
|
245
|
+
get ptDiscount() {
|
|
246
|
+
return 1 / this.currentPtPriceInAsset;
|
|
247
|
+
}
|
|
248
|
+
get lpPriceInAsset() {
|
|
249
|
+
// Calculate total value of liquidity in asset units
|
|
250
|
+
const liquidityPoolTvl = Number(this.syBalance) * this.flavor.currentSyExchangeRate + Number(this.ptBalance) / this.currentPtPriceInAsset;
|
|
251
|
+
// Return LP price in asset units (0 if no supply to avoid division by zero)
|
|
252
|
+
return Number(this.lpSupply) === 0 ? 0 : liquidityPoolTvl / Number(this.lpSupply);
|
|
253
|
+
}
|
|
254
|
+
get secondsRemaining() {
|
|
255
|
+
const now = Date.now() / 1000;
|
|
256
|
+
return Math.max(0, Math.round(this.state.expirationTs - now));
|
|
257
|
+
}
|
|
258
|
+
get absolutePtYield() {
|
|
259
|
+
const ptAssetExchangeRate = this.ptDiscount;
|
|
260
|
+
return (1 - ptAssetExchangeRate) / ptAssetExchangeRate;
|
|
261
|
+
}
|
|
262
|
+
/** Annualize a rate given the number of seconds remaining until maturity */
|
|
263
|
+
static annualize(r, secondsRemaining) {
|
|
264
|
+
return (r * SECONDS_PER_YEAR) / secondsRemaining;
|
|
265
|
+
}
|
|
266
|
+
/** Annualized PT fixed rate */
|
|
267
|
+
get ptApr() {
|
|
268
|
+
return Market.annualize(this.absolutePtYield, this.secondsRemaining);
|
|
269
|
+
}
|
|
270
|
+
/** The fee rate taken off of trade fees (typically around 20%) expressed as a BPS number */
|
|
271
|
+
get feeTreasuryBps() {
|
|
272
|
+
return this.state.feeTreasurySyBps;
|
|
273
|
+
}
|
|
274
|
+
/** The fee rate on assets when trading PT
|
|
275
|
+
* Expressed as a rational number
|
|
276
|
+
* eg 0.01 = 1%
|
|
277
|
+
*/
|
|
278
|
+
get feeRatePtTrade() {
|
|
279
|
+
return 1 - this.marketCalculator().feeRate;
|
|
280
|
+
}
|
|
281
|
+
/** The fee rate taken off of trade fees (typically around 20%) expressed as a rational number */
|
|
282
|
+
get feeTreasuryRate() {
|
|
283
|
+
return this.feeTreasuryBps / 10_000;
|
|
284
|
+
}
|
|
285
|
+
/** Calculate amonut of LP tokens to expect for tokens in */
|
|
286
|
+
lpOutForTokensIn(syInIntent, ptInIntent) {
|
|
287
|
+
return (0, market_math_1.lpOutForTokensIn)({
|
|
288
|
+
syIntent: Number(syInIntent),
|
|
289
|
+
ptIntent: Number(ptInIntent),
|
|
290
|
+
lpSupply: Number(this.lpSupply),
|
|
291
|
+
syLiquidity: Number(this.syBalance),
|
|
292
|
+
ptLiquidity: Number(this.ptBalance),
|
|
293
|
+
});
|
|
294
|
+
}
|
|
295
|
+
marketCalculator() {
|
|
296
|
+
const secondsRemaining = Math.max(0, Math.round(this.state.expirationTs - Date.now() / 1000));
|
|
297
|
+
return new market_math_1.MarketCalculator({
|
|
298
|
+
liquiditySy: parseInt(this.syBalance.toString()),
|
|
299
|
+
liquidityPt: parseInt(this.ptBalance.toString()),
|
|
300
|
+
currentSyExchangeRate: this.currentSyExchangeRate,
|
|
301
|
+
lnFeeRateRoot: this.state.lnFeeRateRoot,
|
|
302
|
+
secondsRemaining,
|
|
303
|
+
lpTokenSupply: this.lpSupply,
|
|
304
|
+
rateScalarRoot: this.state.rateScalarRoot,
|
|
305
|
+
lastLnImpliedRate: this.state.lastLnImpliedRate,
|
|
306
|
+
maxNetBalanceChangeNegativePercentage: this.state.liquidityNetBalanceLimits.maxNetBalanceChangeNegativePercentage,
|
|
307
|
+
maxNetBalanceChangePositivePercentage: this.state.liquidityNetBalanceLimits.maxNetBalanceChangePositivePercentage,
|
|
308
|
+
windowStartTimestamp: this.state.liquidityNetBalanceLimits.windowStartTimestamp,
|
|
309
|
+
windowStartNetBalance: this.state.liquidityNetBalanceLimits.windowStartNetBalance.toNumber(),
|
|
310
|
+
windowDurationSeconds: this.state.liquidityNetBalanceLimits.windowDurationSeconds,
|
|
311
|
+
});
|
|
312
|
+
}
|
|
313
|
+
/** Deposit a pair of tokens as liquidity to the market
|
|
314
|
+
* Adds PT & SY from the `depositor` to the market
|
|
315
|
+
*
|
|
316
|
+
* Due to unforeseeable slippage, the PT & SY amounts intended are effectively the maximum amounts
|
|
317
|
+
* The minimum LP tokens to receive is specified by `minLpOut`
|
|
318
|
+
*
|
|
319
|
+
* The token accounts themselves are optional, and will be derived from the depositor's wallet if not provided
|
|
320
|
+
*/
|
|
321
|
+
async ixDepositLiquidity({ ptInIntent, syInIntent, minLpOut, depositor, ptSrc, sySrc, lpDst, }) {
|
|
322
|
+
const tokenProgram = spl_token_1.TOKEN_PROGRAM_ID;
|
|
323
|
+
sySrc = sySrc || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
324
|
+
ptSrc = ptSrc || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
325
|
+
lpDst = lpDst || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
326
|
+
const syRemAccounts = this.cpiAccounts.depositSy;
|
|
327
|
+
return this.coreProgram.methods
|
|
328
|
+
.marketTwoDepositLiquidity(new anchor_2.BN(ptInIntent.toString()), new anchor_2.BN(syInIntent.toString()), new anchor_2.BN(minLpOut.toString()))
|
|
329
|
+
.accountsStrict({
|
|
330
|
+
depositor,
|
|
331
|
+
market: this.selfAddress,
|
|
332
|
+
mintLp: this.mintLp,
|
|
333
|
+
tokenPtSrc: ptSrc,
|
|
334
|
+
tokenSySrc: sySrc,
|
|
335
|
+
tokenLpDst: lpDst,
|
|
336
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
337
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
338
|
+
addressLookupTable: this.addressLookupTable,
|
|
339
|
+
syProgram: this.syProgram,
|
|
340
|
+
tokenProgram,
|
|
341
|
+
eventAuthority: this.vault.eventAuthority,
|
|
342
|
+
program: this.coreProgram.programId,
|
|
343
|
+
})
|
|
344
|
+
.remainingAccounts(syRemAccounts)
|
|
345
|
+
.instruction();
|
|
346
|
+
}
|
|
347
|
+
async ixModifyMarketSetting({ signer, adminAction }) {
|
|
348
|
+
return this.coreProgram.methods
|
|
349
|
+
.modifyMarketSetting(adminAction)
|
|
350
|
+
.accountsStrict({
|
|
351
|
+
market: this.selfAddress,
|
|
352
|
+
adminState: (0, utils_1.getExponentAdminStatePda)(),
|
|
353
|
+
signer,
|
|
354
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
355
|
+
})
|
|
356
|
+
.instruction();
|
|
357
|
+
}
|
|
358
|
+
async ixModifyFarm({ newRate, untilTimestamp, signer, farmMint, farmTokenProgram, farmTokenSrc, }) {
|
|
359
|
+
farmTokenSrc = farmTokenSrc || (0, spl_token_1.getAssociatedTokenAddressSync)(farmMint, signer, true, farmTokenProgram);
|
|
360
|
+
const tokenFarm = (0, spl_token_1.getAssociatedTokenAddressSync)(farmMint, this.selfAddress, true, farmTokenProgram);
|
|
361
|
+
return this.coreProgram.methods
|
|
362
|
+
.modifyFarm(untilTimestamp, new anchor_2.BN(newRate.toString()))
|
|
363
|
+
.accountsStrict({
|
|
364
|
+
adminState: (0, utils_1.getExponentAdminStatePda)(),
|
|
365
|
+
market: this.selfAddress,
|
|
366
|
+
mint: farmMint,
|
|
367
|
+
tokenFarm: tokenFarm,
|
|
368
|
+
signer,
|
|
369
|
+
tokenProgram: farmTokenProgram,
|
|
370
|
+
tokenSource: farmTokenSrc,
|
|
371
|
+
})
|
|
372
|
+
.instruction();
|
|
373
|
+
}
|
|
374
|
+
/**
|
|
375
|
+
* Redeem LP tokens for PT & SY (liquidity removal)
|
|
376
|
+
*
|
|
377
|
+
* The lpIn is exactly the amount of LP tokens to burn
|
|
378
|
+
* The minimum PT & SY out are specified by minPtOut & minSyOut
|
|
379
|
+
* The transaction may fail due to unforeseeable slippage on the redemption rate
|
|
380
|
+
*
|
|
381
|
+
* The token accounts themselves are optional, and will be derived from the withdrawer's wallet if not provided
|
|
382
|
+
*/
|
|
383
|
+
async ixWithdrawLiquidity({ lpIn, withdrawer, minPtOut, minSyOut, ptDst, syDst, lpSrc, }) {
|
|
384
|
+
ptDst = ptDst || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, withdrawer, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
385
|
+
syDst = syDst || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, withdrawer, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
386
|
+
lpSrc = lpSrc || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, withdrawer, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
387
|
+
const ptDstAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(withdrawer, ptDst, withdrawer, this.mintPt);
|
|
388
|
+
const syDstAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(withdrawer, syDst, withdrawer, this.mintSy);
|
|
389
|
+
const lpSrcAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(withdrawer, lpSrc, withdrawer, this.mintLp);
|
|
390
|
+
const syRemAccounts = this.cpiAccounts.withdrawSy;
|
|
391
|
+
const ixs = await this.coreProgram.methods
|
|
392
|
+
.marketTwoWithdrawLiquidity(new anchor_2.BN(lpIn.toString()), new anchor_2.BN(minPtOut.toString()), new anchor_2.BN(minSyOut.toString()))
|
|
393
|
+
.accountsStrict({
|
|
394
|
+
withdrawer,
|
|
395
|
+
market: this.selfAddress,
|
|
396
|
+
mintLp: this.mintLp,
|
|
397
|
+
tokenPtDst: ptDst,
|
|
398
|
+
tokenSyDst: syDst,
|
|
399
|
+
tokenLpSrc: lpSrc,
|
|
400
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
401
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
402
|
+
addressLookupTable: this.addressLookupTable,
|
|
403
|
+
syProgram: this.syProgram,
|
|
404
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
405
|
+
eventAuthority: this.vault.eventAuthority,
|
|
406
|
+
program: this.coreProgram.programId,
|
|
407
|
+
})
|
|
408
|
+
.remainingAccounts(syRemAccounts)
|
|
409
|
+
.instruction();
|
|
410
|
+
return { ixs: [ixs], setupIxs: [ptDstAtaIx, syDstAtaIx, lpSrcAtaIx] };
|
|
411
|
+
}
|
|
412
|
+
/** Buy PT with SY
|
|
413
|
+
*
|
|
414
|
+
* The trader is the account that sends the SY
|
|
415
|
+
* The amountPt is the exact amount of PT the trader intends to buy
|
|
416
|
+
* The syConstraint is the maximum amount of SY the trader is willing to spend
|
|
417
|
+
*
|
|
418
|
+
* The token accounts themselves are optional, and will be derived from the trader's wallet if not provided
|
|
419
|
+
*/
|
|
420
|
+
async ixBuyPt({ trader, amountPt, maxSySpend, tokenPt, tokenSy, }) {
|
|
421
|
+
return this.ixTradePt({
|
|
422
|
+
trader,
|
|
423
|
+
traderPt: amountPt,
|
|
424
|
+
syConstraint: maxSySpend,
|
|
425
|
+
isBuy: true,
|
|
426
|
+
tokenPt,
|
|
427
|
+
tokenSy,
|
|
428
|
+
});
|
|
429
|
+
}
|
|
430
|
+
/**
|
|
431
|
+
* Sell PT for SY
|
|
432
|
+
* The trader is the account that sends the PT
|
|
433
|
+
* The amountPt is the exact amount of PT the trader intends to sell
|
|
434
|
+
* The minSyReceive is the minimum amount of SY the trader is willing to receive
|
|
435
|
+
*
|
|
436
|
+
* The token accounts themselves are optional, and will be derived from the trader's wallet if not provided
|
|
437
|
+
*/
|
|
438
|
+
async ixSellPt({ trader, amountPt, minSyReceive, tokenPt, tokenSy, }) {
|
|
439
|
+
return this.ixTradePt({
|
|
440
|
+
trader,
|
|
441
|
+
traderPt: amountPt,
|
|
442
|
+
syConstraint: minSyReceive,
|
|
443
|
+
isBuy: false,
|
|
444
|
+
tokenPt,
|
|
445
|
+
tokenSy,
|
|
446
|
+
});
|
|
447
|
+
}
|
|
448
|
+
async ixTradePt({ trader, traderPt, syConstraint, isBuy, tokenPt, tokenSy, }) {
|
|
449
|
+
tokenPt = tokenPt || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, trader, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
450
|
+
tokenSy = tokenSy || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, trader, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
451
|
+
const tokenSyAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(trader, tokenSy, trader, this.mintSy);
|
|
452
|
+
const tokenPtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(trader, tokenPt, trader, this.mintPt);
|
|
453
|
+
const remainingAccounts = [
|
|
454
|
+
...this.cpiAccounts.getSyState,
|
|
455
|
+
...this.cpiAccounts.depositSy,
|
|
456
|
+
...this.cpiAccounts.withdrawSy,
|
|
457
|
+
];
|
|
458
|
+
const netTradePtBN = new anchor_2.BN(traderPt.toString()).mul(isBuy ? new anchor_2.BN(1) : new anchor_2.BN(-1));
|
|
459
|
+
const syConstraintBN = new anchor_2.BN(syConstraint.toString()).mul(isBuy ? new anchor_2.BN(-1) : new anchor_2.BN(1));
|
|
460
|
+
const ix = await this.coreProgram.methods
|
|
461
|
+
.tradePt(netTradePtBN, syConstraintBN)
|
|
462
|
+
.accountsStrict({
|
|
463
|
+
trader,
|
|
464
|
+
market: this.selfAddress,
|
|
465
|
+
tokenPtTrader: tokenPt,
|
|
466
|
+
tokenSyTrader: tokenSy,
|
|
467
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
468
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
469
|
+
addressLookupTable: this.addressLookupTable,
|
|
470
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
471
|
+
syProgram: this.syProgram,
|
|
472
|
+
tokenFeeTreasurySy: this.vault.state.treasurySyTokenAccount,
|
|
473
|
+
eventAuthority: this.vault.eventAuthority,
|
|
474
|
+
program: this.coreProgram.programId,
|
|
475
|
+
})
|
|
476
|
+
.remainingAccounts(remainingAccounts)
|
|
477
|
+
.instruction();
|
|
478
|
+
return { ixs: [ix], setupIxs: [tokenPtAtaIx, tokenSyAtaIx] };
|
|
479
|
+
}
|
|
480
|
+
/** Sell YT for SY
|
|
481
|
+
*
|
|
482
|
+
* The trader is the account that sends the YT
|
|
483
|
+
*
|
|
484
|
+
* The amountYt is the exact amount of YT the trader intends to sell
|
|
485
|
+
*
|
|
486
|
+
* The minSyOut is the minimum amount of SY the trader is willing to receive
|
|
487
|
+
*
|
|
488
|
+
* The token accounts themselves are optional, and will be derived from the trader's wallet if not provided
|
|
489
|
+
*/
|
|
490
|
+
async ixSellYt({ trader, ytIn, minSyOut, ytSrc, ptSrc, syDst, }) {
|
|
491
|
+
syDst = syDst || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, trader, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
492
|
+
ptSrc = ptSrc || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, trader, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
493
|
+
ytSrc = ytSrc || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, trader, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
494
|
+
const syDstAtaIxs = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(trader, syDst, trader, this.mintSy);
|
|
495
|
+
const ptSrcAtaIxs = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(trader, ptSrc, trader, this.mintPt);
|
|
496
|
+
const ytSrcAtaIxs = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(trader, ytSrc, trader, this.mintYt);
|
|
497
|
+
const mergeAccounts = this.vault.mergeAccounts({ owner: trader, ytSrc, ptSrc, syDst });
|
|
498
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
499
|
+
...this.cpiAccounts.getSyState,
|
|
500
|
+
...this.cpiAccounts.depositSy,
|
|
501
|
+
...mergeAccounts.remainingAccounts,
|
|
502
|
+
]);
|
|
503
|
+
remainingAccounts.push({ pubkey: this.coreProgram.programId, isWritable: false, isSigner: false });
|
|
504
|
+
const ix = await this.coreProgram.methods
|
|
505
|
+
.sellYt(new anchor_2.BN(ytIn.toString()), new anchor_2.BN(minSyOut.toString()))
|
|
506
|
+
.accountsStrict({
|
|
507
|
+
trader,
|
|
508
|
+
market: this.selfAddress,
|
|
509
|
+
tokenYtTrader: ytSrc,
|
|
510
|
+
tokenPtTrader: ptSrc,
|
|
511
|
+
tokenSyTrader: syDst,
|
|
512
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
513
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
514
|
+
addressLookupTable: this.addressLookupTable,
|
|
515
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
516
|
+
vault: mergeAccounts.mainAccounts.vault,
|
|
517
|
+
authorityVault: mergeAccounts.mainAccounts.authority,
|
|
518
|
+
tokenSyEscrowVault: mergeAccounts.mainAccounts.escrowSy,
|
|
519
|
+
mintYt: this.mintYt,
|
|
520
|
+
mintPt: this.mintPt,
|
|
521
|
+
addressLookupTableVault: mergeAccounts.mainAccounts.addressLookupTable,
|
|
522
|
+
yieldPositionVault: mergeAccounts.mainAccounts.yieldPosition,
|
|
523
|
+
syProgram: this.syProgram,
|
|
524
|
+
tokenFeeTreasurySy: this.vault.state.treasurySyTokenAccount,
|
|
525
|
+
eventAuthority: this.vault.eventAuthority,
|
|
526
|
+
program: this.coreProgram.programId,
|
|
527
|
+
})
|
|
528
|
+
.remainingAccounts(remainingAccounts)
|
|
529
|
+
.instruction();
|
|
530
|
+
return { ixs: [ix], setupIxs: [syDstAtaIxs, ptSrcAtaIxs, ytSrcAtaIxs] };
|
|
531
|
+
}
|
|
532
|
+
/** Buy YT with SY
|
|
533
|
+
*
|
|
534
|
+
* The trader is the account that sends the SY
|
|
535
|
+
*
|
|
536
|
+
* The ytOut is the exact amount of YT the trader intends to buy
|
|
537
|
+
*
|
|
538
|
+
* The maxSyIn is the maximum amount of SY the trader is willing to spend
|
|
539
|
+
*
|
|
540
|
+
* The token accounts themselves are optional, and will be derived from the trader's wallet if not provided
|
|
541
|
+
*/
|
|
542
|
+
async ixBuyYt({ trader, ytOut, maxSyIn, ytTrader, ptTrader, syTrader, }) {
|
|
543
|
+
syTrader = syTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, trader, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
544
|
+
ptTrader = ptTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, trader, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
545
|
+
ytTrader = ytTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, trader, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
546
|
+
const syTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(trader, syTrader, trader, this.mintSy);
|
|
547
|
+
const ptTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(trader, ptTrader, trader, this.mintPt);
|
|
548
|
+
const ytTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(trader, ytTrader, trader, this.mintYt);
|
|
549
|
+
const stripAccounts = this.vault.stripAccounts({
|
|
550
|
+
depositor: trader,
|
|
551
|
+
ytDst: ytTrader,
|
|
552
|
+
ptDst: ptTrader,
|
|
553
|
+
sySrc: syTrader,
|
|
554
|
+
});
|
|
555
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
556
|
+
...this.cpiAccounts.getSyState,
|
|
557
|
+
...this.cpiAccounts.withdrawSy,
|
|
558
|
+
...this.cpiAccounts.depositSy,
|
|
559
|
+
...stripAccounts.remainingAccounts,
|
|
560
|
+
]);
|
|
561
|
+
remainingAccounts.push({ pubkey: this.coreProgram.programId, isWritable: false, isSigner: false });
|
|
562
|
+
const ix = await this.coreProgram.methods
|
|
563
|
+
.buyYt(new anchor_2.BN(maxSyIn.toString()), new anchor_2.BN(ytOut.toString()))
|
|
564
|
+
.accountsStrict({
|
|
565
|
+
trader,
|
|
566
|
+
market: this.selfAddress,
|
|
567
|
+
tokenYtTrader: ytTrader,
|
|
568
|
+
tokenPtTrader: ptTrader,
|
|
569
|
+
tokenSyTrader: syTrader,
|
|
570
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
571
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
572
|
+
addressLookupTable: this.addressLookupTable,
|
|
573
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
574
|
+
syProgram: this.syProgram,
|
|
575
|
+
vault: stripAccounts.mainAccounts.vault,
|
|
576
|
+
vaultAuthority: stripAccounts.mainAccounts.authority,
|
|
577
|
+
tokenSyEscrowVault: stripAccounts.mainAccounts.escrowSy,
|
|
578
|
+
mintYt: this.mintYt,
|
|
579
|
+
mintPt: this.mintPt,
|
|
580
|
+
addressLookupTableVault: stripAccounts.mainAccounts.addressLookupTable,
|
|
581
|
+
yieldPosition: stripAccounts.mainAccounts.yieldPosition,
|
|
582
|
+
tokenFeeTreasurySy: this.vault.state.treasurySyTokenAccount,
|
|
583
|
+
eventAuthority: this.vault.eventAuthority,
|
|
584
|
+
program: this.coreProgram.programId,
|
|
585
|
+
})
|
|
586
|
+
.remainingAccounts(remainingAccounts)
|
|
587
|
+
.instruction();
|
|
588
|
+
return { ixs: [ix], setupIxs: [syTraderAtaIx, ptTraderAtaIx, ytTraderAtaIx] };
|
|
589
|
+
}
|
|
590
|
+
async ixInitLpPosition({ owner, feePayer }) {
|
|
591
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner });
|
|
592
|
+
return this.coreProgram.methods
|
|
593
|
+
.initLpPosition()
|
|
594
|
+
.accountsStrict({
|
|
595
|
+
owner,
|
|
596
|
+
feePayer: feePayer || owner,
|
|
597
|
+
lpPosition,
|
|
598
|
+
market: this.selfAddress,
|
|
599
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
600
|
+
eventAuthority: this.vault.eventAuthority,
|
|
601
|
+
program: this.coreProgram.programId,
|
|
602
|
+
})
|
|
603
|
+
.instruction();
|
|
604
|
+
}
|
|
605
|
+
/** Deposit LP tokens into the farming module to earn rewards */
|
|
606
|
+
async ixDepositLp({ owner, amount, lpSrc }) {
|
|
607
|
+
lpSrc = lpSrc || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
608
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner });
|
|
609
|
+
return this.coreProgram.methods
|
|
610
|
+
.marketDepositLp(new anchor_2.BN(amount.toString()))
|
|
611
|
+
.accountsStrict({
|
|
612
|
+
owner,
|
|
613
|
+
lpPosition,
|
|
614
|
+
tokenLpSrc: lpSrc,
|
|
615
|
+
tokenLpEscrow: this.tokenLpEscrow,
|
|
616
|
+
market: this.selfAddress,
|
|
617
|
+
addressLookupTable: this.addressLookupTable,
|
|
618
|
+
syProgram: this.syProgram,
|
|
619
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
620
|
+
mintLp: this.mintLp,
|
|
621
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
622
|
+
eventAuthority: this.vault.eventAuthority,
|
|
623
|
+
program: this.coreProgram.programId,
|
|
624
|
+
})
|
|
625
|
+
.remainingAccounts(this.cpiAccounts.getPositionState)
|
|
626
|
+
.instruction();
|
|
627
|
+
}
|
|
628
|
+
/** Withdraw LP tokens from the farming module */
|
|
629
|
+
async ixWithdrawLp({ owner, amount, lpDst }) {
|
|
630
|
+
lpDst = lpDst || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
631
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner });
|
|
632
|
+
return this.coreProgram.methods
|
|
633
|
+
.marketWithdrawLp(new anchor_2.BN(amount.toString()))
|
|
634
|
+
.accountsStrict({
|
|
635
|
+
owner,
|
|
636
|
+
lpPosition,
|
|
637
|
+
tokenLpDst: lpDst,
|
|
638
|
+
tokenLpEscrow: this.tokenLpEscrow,
|
|
639
|
+
market: this.selfAddress,
|
|
640
|
+
addressLookupTable: this.addressLookupTable,
|
|
641
|
+
mintLp: this.mintLp,
|
|
642
|
+
syProgram: this.syProgram,
|
|
643
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
644
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
645
|
+
eventAuthority: this.vault.eventAuthority,
|
|
646
|
+
program: this.coreProgram.programId,
|
|
647
|
+
})
|
|
648
|
+
.remainingAccounts(this.cpiAccounts.getPositionState)
|
|
649
|
+
.instruction();
|
|
650
|
+
}
|
|
651
|
+
async ixWrapperCollectInterest({ claimer, tokenSyDst }) {
|
|
652
|
+
const yieldPosition = this.xponPda.yieldPosition({ owner: claimer, vault: this.vault.selfAddress });
|
|
653
|
+
tokenSyDst = tokenSyDst || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, claimer, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
654
|
+
const tokenBaseClaimer = (0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, claimer, true, this.flavor.baseTokenProgram);
|
|
655
|
+
const tokenBaseClaimerAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(claimer, tokenBaseClaimer, claimer, this.flavor.mintBase);
|
|
656
|
+
const tokenSyClaimer = (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, claimer, true);
|
|
657
|
+
const tokenSyClaimerAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(claimer, tokenSyClaimer, claimer, this.mintSy);
|
|
658
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
659
|
+
...this.vault.cpiAccounts.getSyState,
|
|
660
|
+
...this.vault.cpiAccounts.withdrawSy,
|
|
661
|
+
]);
|
|
662
|
+
const redeemSyIx = await this.flavor.ixRedeemSy({
|
|
663
|
+
amountSy: "0",
|
|
664
|
+
redeemer: claimer,
|
|
665
|
+
redeemerBaseTokenAccount: tokenBaseClaimer,
|
|
666
|
+
redeemerSyTokenAccount: tokenSyDst,
|
|
667
|
+
});
|
|
668
|
+
const ix = await this.coreProgram.methods
|
|
669
|
+
.wrapperCollectInterest(redeemSyIx.keys.length)
|
|
670
|
+
.accountsStrict({
|
|
671
|
+
addressLookupTable: this.vault.addressLookupTable,
|
|
672
|
+
authority: this.vault.state.authority,
|
|
673
|
+
claimer,
|
|
674
|
+
escrowSy: this.vault.escrowSy,
|
|
675
|
+
syProgram: this.syProgram,
|
|
676
|
+
vault: this.vault.selfAddress,
|
|
677
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
678
|
+
treasurySyTokenAccount: this.vault.state.treasurySyTokenAccount,
|
|
679
|
+
yieldPosition: yieldPosition,
|
|
680
|
+
tokenSyDst,
|
|
681
|
+
eventAuthority: this.vault.eventAuthority,
|
|
682
|
+
program: this.coreProgram.programId,
|
|
683
|
+
})
|
|
684
|
+
.remainingAccounts(redeemSyIx.keys.concat(remainingAccounts))
|
|
685
|
+
.instruction();
|
|
686
|
+
return {
|
|
687
|
+
ixs: [
|
|
688
|
+
...(await this.flavor.preIxs({ signer: claimer })),
|
|
689
|
+
ix,
|
|
690
|
+
...(await this.flavor.postIxs({ signer: claimer })),
|
|
691
|
+
],
|
|
692
|
+
setupIxs: [tokenBaseClaimerAtaIx, tokenSyClaimerAtaIx],
|
|
693
|
+
};
|
|
694
|
+
}
|
|
695
|
+
async ixWrapperBuyPt({ owner, ptOut, maxBaseIn, tokenSyTrader, tokenPtTrader, tokenBaseTrader, }) {
|
|
696
|
+
tokenSyTrader = tokenSyTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
697
|
+
tokenPtTrader = tokenPtTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
698
|
+
tokenBaseTrader =
|
|
699
|
+
tokenBaseTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, owner, true, this.flavor.baseTokenProgram);
|
|
700
|
+
const tokenSyTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenSyTrader, owner, this.mintSy);
|
|
701
|
+
const tokenPtTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenPtTrader, owner, this.mintPt);
|
|
702
|
+
const tokenBaseTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenBaseTrader, owner, this.flavor.mintBase);
|
|
703
|
+
const mintSyIx = await this.flavor.ixMintSy({
|
|
704
|
+
amountBase: "0",
|
|
705
|
+
depositor: owner,
|
|
706
|
+
depositorBaseTokenAccount: tokenBaseTrader,
|
|
707
|
+
depositorSyTokenAccount: tokenSyTrader,
|
|
708
|
+
});
|
|
709
|
+
const mintSyRemAccounts = mintSyIx.keys;
|
|
710
|
+
console.log("mintSyRemAccounts", mintSyRemAccounts);
|
|
711
|
+
mintSyRemAccounts.push({
|
|
712
|
+
pubkey: this.coreProgram.programId,
|
|
713
|
+
isWritable: false,
|
|
714
|
+
isSigner: false,
|
|
715
|
+
});
|
|
716
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
717
|
+
...this.cpiAccounts.getSyState,
|
|
718
|
+
...this.cpiAccounts.depositSy,
|
|
719
|
+
// ...this.cpiAccounts.withdrawSy,
|
|
720
|
+
]);
|
|
721
|
+
const ix = await this.coreProgram.methods
|
|
722
|
+
.wrapperBuyPt(new anchor_2.BN(ptOut.toString()), new anchor_2.BN(maxBaseIn.toString()), mintSyRemAccounts.length)
|
|
723
|
+
.accountsStrict({
|
|
724
|
+
addressLookupTable: this.addressLookupTable,
|
|
725
|
+
buyer: owner,
|
|
726
|
+
market: this.selfAddress,
|
|
727
|
+
tokenSyTrader,
|
|
728
|
+
tokenPtTrader,
|
|
729
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
730
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
731
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
732
|
+
syProgram: this.syProgram,
|
|
733
|
+
tokenFeeTreasurySy: this.state.tokenFeeTreasurySy,
|
|
734
|
+
eventAuthority: this.vault.eventAuthority,
|
|
735
|
+
program: this.coreProgram.programId,
|
|
736
|
+
})
|
|
737
|
+
.remainingAccounts(mintSyRemAccounts.concat(remainingAccounts))
|
|
738
|
+
.instruction();
|
|
739
|
+
return {
|
|
740
|
+
ixs: [...(await this.flavor.preIxs({ signer: owner })), ix, ...(await this.flavor.postIxs({ signer: owner }))],
|
|
741
|
+
setupIxs: [tokenSyTraderAtaIx, tokenPtTraderAtaIx, tokenBaseTraderAtaIx],
|
|
742
|
+
};
|
|
743
|
+
}
|
|
744
|
+
async ixWrapperSellPt({ owner, amount, minBaseOut, tokenSyTrader, tokenPtTrader, tokenBaseTrader, }) {
|
|
745
|
+
tokenSyTrader = tokenSyTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
746
|
+
tokenPtTrader = tokenPtTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
747
|
+
tokenBaseTrader =
|
|
748
|
+
tokenBaseTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, owner, true, this.flavor.baseTokenProgram);
|
|
749
|
+
const tokenSyTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenSyTrader, owner, this.mintSy);
|
|
750
|
+
const tokenPtTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenPtTrader, owner, this.mintPt);
|
|
751
|
+
const tokenBaseTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenBaseTrader, owner, this.flavor.mintBase);
|
|
752
|
+
const redeemSyIx = await this.flavor.ixRedeemSy({
|
|
753
|
+
amountSy: "0",
|
|
754
|
+
redeemer: owner,
|
|
755
|
+
redeemerBaseTokenAccount: tokenBaseTrader,
|
|
756
|
+
redeemerSyTokenAccount: tokenSyTrader,
|
|
757
|
+
});
|
|
758
|
+
const redeemSyRemAccounts = redeemSyIx.keys;
|
|
759
|
+
redeemSyRemAccounts.push({
|
|
760
|
+
pubkey: this.coreProgram.programId,
|
|
761
|
+
isWritable: false,
|
|
762
|
+
isSigner: false,
|
|
763
|
+
});
|
|
764
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([...this.cpiAccounts.getSyState, ...this.cpiAccounts.withdrawSy]);
|
|
765
|
+
const ix = await this.coreProgram.methods
|
|
766
|
+
.wrapperSellPt(new anchor_2.BN(amount.toString()), new anchor_2.BN(minBaseOut.toString()), redeemSyRemAccounts.length)
|
|
767
|
+
.accountsStrict({
|
|
768
|
+
seller: owner,
|
|
769
|
+
market: this.selfAddress,
|
|
770
|
+
tokenPtTrader,
|
|
771
|
+
addressLookupTable: this.addressLookupTable,
|
|
772
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
773
|
+
syProgram: this.syProgram,
|
|
774
|
+
tokenSyTrader,
|
|
775
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
776
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
777
|
+
tokenFeeTreasurySy: this.state.tokenFeeTreasurySy,
|
|
778
|
+
eventAuthority: this.vault.eventAuthority,
|
|
779
|
+
program: this.coreProgram.programId,
|
|
780
|
+
})
|
|
781
|
+
.remainingAccounts(redeemSyRemAccounts.concat(remainingAccounts))
|
|
782
|
+
.instruction();
|
|
783
|
+
return {
|
|
784
|
+
ixs: [...(await this.flavor.preIxs({ signer: owner })), ix, ...(await this.flavor.postIxs({ signer: owner }))],
|
|
785
|
+
setupIxs: [tokenSyTraderAtaIx, tokenPtTraderAtaIx, tokenBaseTraderAtaIx],
|
|
786
|
+
};
|
|
787
|
+
}
|
|
788
|
+
async ixWrapperBuyYt({ owner, ytOut, maxBaseIn, tokenSyTrader, tokenPtTrader, tokenYtTrader, tokenBaseTrader, }) {
|
|
789
|
+
tokenSyTrader = tokenSyTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
790
|
+
tokenPtTrader = tokenPtTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
791
|
+
tokenYtTrader = tokenYtTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
792
|
+
tokenBaseTrader =
|
|
793
|
+
tokenBaseTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, owner, true, this.flavor.baseTokenProgram);
|
|
794
|
+
const tokenSyTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenSyTrader, owner, this.mintSy);
|
|
795
|
+
const tokenPtTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenPtTrader, owner, this.mintPt);
|
|
796
|
+
const tokenYtTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenYtTrader, owner, this.mintYt);
|
|
797
|
+
const mintSyIx = await this.flavor.ixMintSy({
|
|
798
|
+
amountBase: "0",
|
|
799
|
+
depositor: owner,
|
|
800
|
+
depositorBaseTokenAccount: tokenBaseTrader,
|
|
801
|
+
depositorSyTokenAccount: tokenSyTrader,
|
|
802
|
+
});
|
|
803
|
+
const mintSyRemAccounts = mintSyIx.keys;
|
|
804
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
805
|
+
...this.cpiAccounts.getSyState,
|
|
806
|
+
...this.vault.cpiAccounts.depositSy,
|
|
807
|
+
...this.vault.cpiAccounts.getSyState,
|
|
808
|
+
...this.cpiAccounts.withdrawSy,
|
|
809
|
+
...this.cpiAccounts.getPositionState,
|
|
810
|
+
]);
|
|
811
|
+
const allRemainingAccounts = mintSyRemAccounts.concat(remainingAccounts);
|
|
812
|
+
const ix1 = await this.coreProgram.methods
|
|
813
|
+
.wrapperBuyYt(new anchor_2.BN(ytOut.toString()), new anchor_2.BN(maxBaseIn.toString()), mintSyRemAccounts.length)
|
|
814
|
+
.accountsStrict({
|
|
815
|
+
buyer: owner,
|
|
816
|
+
market: this.selfAddress,
|
|
817
|
+
tokenSyTrader,
|
|
818
|
+
tokenYtTrader,
|
|
819
|
+
tokenPtTrader,
|
|
820
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
821
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
822
|
+
marketAddressLookupTable: this.addressLookupTable,
|
|
823
|
+
vault: this.vault.selfAddress,
|
|
824
|
+
vaultAuthority: this.vault.authority,
|
|
825
|
+
tokenSyEscrowVault: this.vault.escrowSy,
|
|
826
|
+
vaultAddressLookupTable: this.vault.addressLookupTable,
|
|
827
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
828
|
+
syProgram: this.syProgram,
|
|
829
|
+
mintPt: this.vault.mintPt,
|
|
830
|
+
yieldPosition: this.vault.state.yieldPositonAddress,
|
|
831
|
+
mintYt: this.vault.mintYt,
|
|
832
|
+
escrowYt: this.vault.escrowYt,
|
|
833
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
834
|
+
userYieldPosition: this.xponPda.yieldPosition({ vault: this.vault.selfAddress, owner }),
|
|
835
|
+
tokenFeeTreasurySy: this.state.tokenFeeTreasurySy,
|
|
836
|
+
eventAuthority: this.vault.eventAuthority,
|
|
837
|
+
program: this.coreProgram.programId,
|
|
838
|
+
})
|
|
839
|
+
.remainingAccounts(allRemainingAccounts)
|
|
840
|
+
.instruction();
|
|
841
|
+
const ix2 = await this.coreProgram.methods
|
|
842
|
+
.depositYt(new anchor_2.BN(ytOut.toString()))
|
|
843
|
+
.accountsStrict({
|
|
844
|
+
depositor: owner,
|
|
845
|
+
vault: this.vault.selfAddress,
|
|
846
|
+
userYieldPosition: this.xponPda.yieldPosition({ vault: this.vault.selfAddress, owner }),
|
|
847
|
+
ytSrc: tokenYtTrader,
|
|
848
|
+
escrowYt: this.vault.escrowYt,
|
|
849
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
850
|
+
syProgram: this.syProgram,
|
|
851
|
+
addressLookupTable: this.vault.addressLookupTable,
|
|
852
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
853
|
+
eventAuthority: this.vault.eventAuthority,
|
|
854
|
+
program: this.coreProgram.programId,
|
|
855
|
+
yieldPosition: this.vault.state.yieldPositonAddress,
|
|
856
|
+
})
|
|
857
|
+
.remainingAccounts(remainingAccounts)
|
|
858
|
+
.instruction();
|
|
859
|
+
return {
|
|
860
|
+
ixs: [
|
|
861
|
+
...(await this.flavor.preIxs({ signer: owner })),
|
|
862
|
+
ix1,
|
|
863
|
+
...(await this.flavor.postIxs({ signer: owner })),
|
|
864
|
+
ix2,
|
|
865
|
+
],
|
|
866
|
+
setupIxs: [tokenSyTraderAtaIx, tokenPtTraderAtaIx, tokenYtTraderAtaIx],
|
|
867
|
+
};
|
|
868
|
+
}
|
|
869
|
+
async ixWrapperSellYt({ owner, amount, minBaseOut, tokenBaseTrader, tokenSyTrader, tokenYtTrader, tokenPtTrader, }) {
|
|
870
|
+
tokenBaseTrader =
|
|
871
|
+
tokenBaseTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, owner, true, this.flavor.baseTokenProgram);
|
|
872
|
+
tokenSyTrader = tokenSyTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
873
|
+
tokenYtTrader = tokenYtTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
874
|
+
tokenPtTrader = tokenPtTrader || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
875
|
+
const tokenSyTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenSyTrader, owner, this.mintSy);
|
|
876
|
+
const tokenPtTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenPtTrader, owner, this.mintPt);
|
|
877
|
+
const tokenYtTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenYtTrader, owner, this.mintYt);
|
|
878
|
+
const tokenBaseTraderAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenBaseTrader, owner, this.flavor.mintBase);
|
|
879
|
+
const redeemSyIx = await this.flavor.ixRedeemSy({
|
|
880
|
+
amountSy: "0",
|
|
881
|
+
redeemer: owner,
|
|
882
|
+
redeemerBaseTokenAccount: tokenBaseTrader,
|
|
883
|
+
redeemerSyTokenAccount: tokenSyTrader,
|
|
884
|
+
});
|
|
885
|
+
const redeemSyRemAccounts = redeemSyIx.keys;
|
|
886
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
887
|
+
...this.cpiAccounts.getSyState,
|
|
888
|
+
...this.cpiAccounts.withdrawSy,
|
|
889
|
+
...this.vault.cpiAccounts.depositSy,
|
|
890
|
+
]);
|
|
891
|
+
console.log(" remaining accounts length", remainingAccounts.length);
|
|
892
|
+
// remainingAccounts.push({
|
|
893
|
+
// pubkey: this.coreProgram.programId,
|
|
894
|
+
// isWritable: false,
|
|
895
|
+
// isSigner: false,
|
|
896
|
+
// })
|
|
897
|
+
const ix1 = await this.coreProgram.methods
|
|
898
|
+
.withdrawYt(new anchor_2.BN(amount.toString()))
|
|
899
|
+
.accountsStrict({
|
|
900
|
+
ytDst: tokenYtTrader,
|
|
901
|
+
escrowYt: this.vault.escrowYt,
|
|
902
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
903
|
+
syProgram: this.syProgram,
|
|
904
|
+
addressLookupTable: this.vault.addressLookupTable,
|
|
905
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
906
|
+
eventAuthority: this.vault.eventAuthority,
|
|
907
|
+
program: this.coreProgram.programId,
|
|
908
|
+
yieldPosition: this.vault.state.yieldPositonAddress,
|
|
909
|
+
userYieldPosition: this.xponPda.yieldPosition({ vault: this.vault.selfAddress, owner }),
|
|
910
|
+
authority: this.vault.authority,
|
|
911
|
+
owner,
|
|
912
|
+
vault: this.vault.selfAddress,
|
|
913
|
+
})
|
|
914
|
+
.remainingAccounts(remainingAccounts)
|
|
915
|
+
.instruction();
|
|
916
|
+
const ix2 = await this.coreProgram.methods
|
|
917
|
+
.wrapperSellYt(new anchor_2.BN(amount.toString()), new anchor_2.BN(minBaseOut.toString()), redeemSyRemAccounts.length)
|
|
918
|
+
.accountsStrict({
|
|
919
|
+
seller: owner,
|
|
920
|
+
market: this.selfAddress,
|
|
921
|
+
tokenYtTrader,
|
|
922
|
+
marketAddressLookupTable: this.addressLookupTable,
|
|
923
|
+
vault: this.vault.selfAddress,
|
|
924
|
+
vaultAuthority: this.vault.authority,
|
|
925
|
+
tokenPtTrader,
|
|
926
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
927
|
+
tokenSyEscrowVault: this.vault.escrowSy,
|
|
928
|
+
vaultAddressLookupTable: this.vault.addressLookupTable,
|
|
929
|
+
yieldPosition: this.vault.state.yieldPositonAddress,
|
|
930
|
+
mintPt: this.vault.mintPt,
|
|
931
|
+
mintYt: this.vault.mintYt,
|
|
932
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
933
|
+
syProgram: this.syProgram,
|
|
934
|
+
tokenSyTrader,
|
|
935
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
936
|
+
tokenFeeTreasurySy: this.state.tokenFeeTreasurySy,
|
|
937
|
+
eventAuthority: this.vault.eventAuthority,
|
|
938
|
+
program: this.coreProgram.programId,
|
|
939
|
+
})
|
|
940
|
+
.remainingAccounts(redeemSyRemAccounts.concat(remainingAccounts))
|
|
941
|
+
.instruction();
|
|
942
|
+
return {
|
|
943
|
+
ixs: [
|
|
944
|
+
ix1,
|
|
945
|
+
...(await this.flavor.preIxs({ signer: owner })),
|
|
946
|
+
ix2,
|
|
947
|
+
...(await this.flavor.postIxs({ signer: owner })),
|
|
948
|
+
],
|
|
949
|
+
setupIxs: [tokenSyTraderAtaIx, tokenPtTraderAtaIx, tokenYtTraderAtaIx, tokenBaseTraderAtaIx],
|
|
950
|
+
};
|
|
951
|
+
}
|
|
952
|
+
async ixCollectMarketEmission({ owner, emissionIndex, emissionDst, }) {
|
|
953
|
+
const emission = this.emissions[emissionIndex];
|
|
954
|
+
const tokenEmissionDst = emissionDst || (0, spl_token_1.getAssociatedTokenAddressSync)(emission.mint, owner, true, emission.tokenProgramAddress);
|
|
955
|
+
const tokenEmissionDstIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenEmissionDst, owner, emission.mint);
|
|
956
|
+
const ix = await this.coreProgram.methods
|
|
957
|
+
.marketCollectEmission(emissionIndex)
|
|
958
|
+
.accountsStrict({
|
|
959
|
+
addressLookupTable: this.addressLookupTable,
|
|
960
|
+
lpPosition: this.xponPda.marketLpPosition({ market: this.selfAddress, owner }),
|
|
961
|
+
market: this.selfAddress,
|
|
962
|
+
owner,
|
|
963
|
+
syProgram: this.syProgram,
|
|
964
|
+
tokenEmissionDst,
|
|
965
|
+
tokenEmissionEscrow: this.marketEmissions.trackers[emissionIndex].tokenEscrow,
|
|
966
|
+
tokenProgram: emission.tokenProgramAddress,
|
|
967
|
+
program: this.coreProgram.programId,
|
|
968
|
+
eventAuthority: this.eventAuthority,
|
|
969
|
+
})
|
|
970
|
+
.remainingAccounts(this.cpiAccounts.claimEmission[emissionIndex])
|
|
971
|
+
.instruction();
|
|
972
|
+
return {
|
|
973
|
+
ixs: [ix],
|
|
974
|
+
setupIxs: [tokenEmissionDstIx],
|
|
975
|
+
};
|
|
976
|
+
}
|
|
977
|
+
/** Provide liquidity from a base asset - and receive YT and LP tokens in return */
|
|
978
|
+
async ixProvideLiquidityNoPriceImpact({ depositor, amountBase, minLpOut, tokenSyDepositor, tokenYtDepositor, tokenPtDepositor, tokenBaseDepositor, tokenLpDepositor, }) {
|
|
979
|
+
tokenSyDepositor = tokenSyDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
980
|
+
tokenYtDepositor = tokenYtDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
981
|
+
tokenPtDepositor = tokenPtDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
982
|
+
tokenBaseDepositor =
|
|
983
|
+
tokenBaseDepositor ||
|
|
984
|
+
(0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, depositor, true, this.flavor.baseTokenProgram);
|
|
985
|
+
tokenLpDepositor = tokenLpDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
986
|
+
const tokenSyDepositorAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenSyDepositor, depositor, this.mintSy);
|
|
987
|
+
const tokenYtDepositorAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenYtDepositor, depositor, this.mintYt);
|
|
988
|
+
const tokenPtDepositorAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenPtDepositor, depositor, this.mintPt);
|
|
989
|
+
const tokenLpDepositorAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenLpDepositor, depositor, this.mintLp);
|
|
990
|
+
const amountBaseBn = new anchor_2.BN(amountBase.toString());
|
|
991
|
+
const minLpOutBn = new anchor_2.BN(minLpOut.toString());
|
|
992
|
+
// TODO - fix this
|
|
993
|
+
const mintSyIx = await this.flavor.ixMintSy({
|
|
994
|
+
// argument does not matter - since we are just getting the keys
|
|
995
|
+
amountBase: "0",
|
|
996
|
+
depositor,
|
|
997
|
+
depositorBaseTokenAccount: tokenBaseDepositor,
|
|
998
|
+
depositorSyTokenAccount: tokenSyDepositor,
|
|
999
|
+
});
|
|
1000
|
+
const mintSyRemAccounts = mintSyIx.keys;
|
|
1001
|
+
// Log vault accounts before filtering
|
|
1002
|
+
const beforeVaultAccounts = [...this.vault.cpiAccounts.getSyState, ...this.vault.cpiAccounts.depositSy];
|
|
1003
|
+
console.log("Before filtering vault accounts:", beforeVaultAccounts.length, "accounts");
|
|
1004
|
+
// Filter out TOKEN_PROGRAM_ID and SystemProgram.programId from vault remaining accounts
|
|
1005
|
+
const vaultCpiRemainingAccounts = beforeVaultAccounts.filter((account) => account.pubkey.toBase58() !== spl_token_1.TOKEN_PROGRAM_ID.toBase58());
|
|
1006
|
+
// Log vault accounts after filtering
|
|
1007
|
+
console.log("After filtering vault accounts:", vaultCpiRemainingAccounts.length, "accounts");
|
|
1008
|
+
// Log market accounts before filtering
|
|
1009
|
+
const beforeMarketAccounts = [...this.cpiAccounts.depositSy];
|
|
1010
|
+
console.log("Before filtering market accounts:", beforeMarketAccounts.length, "accounts");
|
|
1011
|
+
// Filter out TOKEN_PROGRAM_ID and SystemProgram.programId from market remaining accounts
|
|
1012
|
+
const marketCpiRemainingAccounts = beforeMarketAccounts.filter((account) => account.pubkey.toBase58() !== spl_token_1.TOKEN_PROGRAM_ID.toBase58() &&
|
|
1013
|
+
account.pubkey.toBase58() !== anchor_1.web3.SystemProgram.programId.toBase58() &&
|
|
1014
|
+
account.pubkey.toBase58() !== this.selfAddress.toBase58());
|
|
1015
|
+
// Log market accounts after filtering
|
|
1016
|
+
console.log("After filtering market accounts:", marketCpiRemainingAccounts.length, "accounts");
|
|
1017
|
+
// These remaining accounts can be in any order, and they can be unique-ified
|
|
1018
|
+
const unorderedRemainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
1019
|
+
...vaultCpiRemainingAccounts,
|
|
1020
|
+
...marketCpiRemainingAccounts,
|
|
1021
|
+
]);
|
|
1022
|
+
const allRemainingAccounts = [...mintSyRemAccounts, ...unorderedRemainingAccounts];
|
|
1023
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner: depositor });
|
|
1024
|
+
const ix = await this.coreProgram.methods
|
|
1025
|
+
.wrapperProvideLiquidity(amountBaseBn, minLpOutBn, mintSyRemAccounts.length)
|
|
1026
|
+
.accountsStrict({
|
|
1027
|
+
depositor,
|
|
1028
|
+
authority: this.vault.authority,
|
|
1029
|
+
vault: this.vault.selfAddress,
|
|
1030
|
+
market: this.selfAddress,
|
|
1031
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
1032
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
1033
|
+
tokenLpDst: tokenLpDepositor,
|
|
1034
|
+
mintLp: this.mintLp,
|
|
1035
|
+
escrowSy: this.vault.escrowSy,
|
|
1036
|
+
escrowYt: this.vault.escrowYt,
|
|
1037
|
+
tokenSyDepositor,
|
|
1038
|
+
tokenYtDepositor,
|
|
1039
|
+
tokenPtDepositor,
|
|
1040
|
+
mintYt: this.vault.mintYt,
|
|
1041
|
+
mintPt: this.vault.mintPt,
|
|
1042
|
+
userYieldPosition: this.xponPda.yieldPosition({ vault: this.vault.selfAddress, owner: depositor }),
|
|
1043
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
1044
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
1045
|
+
syProgram: this.syProgram,
|
|
1046
|
+
marketAddressLookupTable: this.addressLookupTable,
|
|
1047
|
+
vaultAddressLookupTable: this.vault.addressLookupTable,
|
|
1048
|
+
vaultRobotYieldPosition: this.vault.state.yieldPositonAddress,
|
|
1049
|
+
eventAuthority: this.vault.eventAuthority,
|
|
1050
|
+
program: this.coreProgram.programId,
|
|
1051
|
+
lpPosition,
|
|
1052
|
+
tokenLpEscrow: this.tokenLpEscrow,
|
|
1053
|
+
})
|
|
1054
|
+
.remainingAccounts(allRemainingAccounts)
|
|
1055
|
+
.instruction();
|
|
1056
|
+
console.log("ix accounts length", ix.keys.length);
|
|
1057
|
+
return {
|
|
1058
|
+
ixs: [
|
|
1059
|
+
...(await this.flavor.preIxs({ signer: depositor })),
|
|
1060
|
+
ix,
|
|
1061
|
+
...(await this.flavor.postIxs({ signer: depositor })),
|
|
1062
|
+
],
|
|
1063
|
+
setupIxs: [tokenSyDepositorAtaIx, tokenYtDepositorAtaIx, tokenPtDepositorAtaIx, tokenLpDepositorAtaIx],
|
|
1064
|
+
};
|
|
1065
|
+
}
|
|
1066
|
+
async ixProvideLiquidityBase({ depositor, amountBase, minLpOut, externalPtToBuy, externalSyConstraint, tokenSyDepositor, tokenYtDepositor, tokenPtDepositor, tokenBaseDepositor, tokenLpDepositor, }) {
|
|
1067
|
+
tokenSyDepositor = tokenSyDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1068
|
+
tokenYtDepositor = tokenYtDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1069
|
+
tokenPtDepositor = tokenPtDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1070
|
+
tokenBaseDepositor =
|
|
1071
|
+
tokenBaseDepositor ||
|
|
1072
|
+
(0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, depositor, true, this.flavor.baseTokenProgram);
|
|
1073
|
+
tokenLpDepositor = tokenLpDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1074
|
+
const tokenSyAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenSyDepositor, depositor, this.mintSy);
|
|
1075
|
+
const tokenYtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenYtDepositor, depositor, this.mintYt);
|
|
1076
|
+
const tokenPtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenPtDepositor, depositor, this.mintPt);
|
|
1077
|
+
const tokenBaseAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenBaseDepositor, depositor, this.flavor.mintBase, this.flavor.baseTokenProgram);
|
|
1078
|
+
const tokenLpAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenLpDepositor, depositor, this.mintLp);
|
|
1079
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner: depositor });
|
|
1080
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
1081
|
+
...this.cpiAccounts.depositSy,
|
|
1082
|
+
...this.cpiAccounts.getPositionState,
|
|
1083
|
+
]);
|
|
1084
|
+
const mintSyIx = await this.flavor.ixMintSy({
|
|
1085
|
+
amountBase: "0",
|
|
1086
|
+
depositor,
|
|
1087
|
+
depositorBaseTokenAccount: tokenBaseDepositor,
|
|
1088
|
+
depositorSyTokenAccount: tokenSyDepositor,
|
|
1089
|
+
});
|
|
1090
|
+
const mintSyRemAccounts = mintSyIx.keys;
|
|
1091
|
+
const ix = await this.coreProgram.methods
|
|
1092
|
+
.wrapperProvideLiquidityBase(new anchor_2.BN(amountBase.toString()), new anchor_2.BN(minLpOut.toString()), mintSyRemAccounts.length, new anchor_2.BN(externalPtToBuy.toString()), new anchor_2.BN(externalSyConstraint.toString()))
|
|
1093
|
+
.accountsStrict({
|
|
1094
|
+
depositor,
|
|
1095
|
+
lpPosition,
|
|
1096
|
+
market: this.selfAddress,
|
|
1097
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
1098
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
1099
|
+
tokenLpDst: tokenLpDepositor,
|
|
1100
|
+
mintLp: this.mintLp,
|
|
1101
|
+
syProgram: this.syProgram,
|
|
1102
|
+
tokenFeeTreasurySy: this.state.tokenFeeTreasurySy,
|
|
1103
|
+
tokenLpEscrow: this.tokenLpEscrow,
|
|
1104
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
1105
|
+
marketAddressLookupTable: this.addressLookupTable,
|
|
1106
|
+
tokenPtDepositor,
|
|
1107
|
+
tokenSyDepositor,
|
|
1108
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
1109
|
+
eventAuthority: this.vault.eventAuthority,
|
|
1110
|
+
program: this.coreProgram.programId,
|
|
1111
|
+
})
|
|
1112
|
+
.remainingAccounts(mintSyRemAccounts.concat(remainingAccounts))
|
|
1113
|
+
.instruction();
|
|
1114
|
+
return {
|
|
1115
|
+
ixs: [
|
|
1116
|
+
...(await this.flavor.preIxs({ signer: depositor })),
|
|
1117
|
+
ix,
|
|
1118
|
+
...(await this.flavor.postIxs({ signer: depositor })),
|
|
1119
|
+
],
|
|
1120
|
+
setupIxs: [tokenSyAtaIx, tokenYtAtaIx, tokenPtAtaIx, tokenBaseAtaIx, tokenLpAtaIx],
|
|
1121
|
+
};
|
|
1122
|
+
}
|
|
1123
|
+
async ixProvideLiquidityClassic({ depositor, amountBase, amountPt, minLpOut, tokenSyDepositor, tokenYtDepositor, tokenPtDepositor, tokenBaseDepositor, tokenLpDepositor, }) {
|
|
1124
|
+
tokenSyDepositor = tokenSyDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1125
|
+
tokenYtDepositor = tokenYtDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1126
|
+
tokenPtDepositor = tokenPtDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1127
|
+
tokenBaseDepositor =
|
|
1128
|
+
tokenBaseDepositor ||
|
|
1129
|
+
(0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, depositor, true, this.flavor.baseTokenProgram);
|
|
1130
|
+
tokenLpDepositor = tokenLpDepositor || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, depositor, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1131
|
+
const tokenSyAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenSyDepositor, depositor, this.mintSy);
|
|
1132
|
+
const tokenYtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenYtDepositor, depositor, this.mintYt);
|
|
1133
|
+
const tokenPtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenPtDepositor, depositor, this.mintPt);
|
|
1134
|
+
const tokenLpAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(depositor, tokenLpDepositor, depositor, this.mintLp);
|
|
1135
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner: depositor });
|
|
1136
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
1137
|
+
...this.cpiAccounts.depositSy,
|
|
1138
|
+
...this.cpiAccounts.getPositionState,
|
|
1139
|
+
]);
|
|
1140
|
+
const mintSyIx = await this.flavor.ixMintSy({
|
|
1141
|
+
amountBase: "0",
|
|
1142
|
+
depositor,
|
|
1143
|
+
depositorBaseTokenAccount: tokenBaseDepositor,
|
|
1144
|
+
depositorSyTokenAccount: tokenSyDepositor,
|
|
1145
|
+
});
|
|
1146
|
+
const mintSyRemAccounts = mintSyIx.keys;
|
|
1147
|
+
const ix = await this.coreProgram.methods
|
|
1148
|
+
.wrapperProvideLiquidityClassic(new anchor_2.BN(amountBase.toString()), new anchor_2.BN(amountPt.toString()), new anchor_2.BN(minLpOut.toString()), mintSyRemAccounts.length)
|
|
1149
|
+
.accountsStrict({
|
|
1150
|
+
depositor,
|
|
1151
|
+
lpPosition,
|
|
1152
|
+
market: this.selfAddress,
|
|
1153
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
1154
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
1155
|
+
tokenLpDst: tokenLpDepositor,
|
|
1156
|
+
mintLp: this.mintLp,
|
|
1157
|
+
syProgram: this.syProgram,
|
|
1158
|
+
tokenLpEscrow: this.tokenLpEscrow,
|
|
1159
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
1160
|
+
marketAddressLookupTable: this.addressLookupTable,
|
|
1161
|
+
tokenPtDepositor,
|
|
1162
|
+
tokenSyDepositor,
|
|
1163
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
1164
|
+
eventAuthority: this.vault.eventAuthority,
|
|
1165
|
+
program: this.coreProgram.programId,
|
|
1166
|
+
})
|
|
1167
|
+
.remainingAccounts(mintSyRemAccounts.concat(remainingAccounts))
|
|
1168
|
+
.instruction();
|
|
1169
|
+
return {
|
|
1170
|
+
ixs: [
|
|
1171
|
+
...(await this.flavor.preIxs({ signer: depositor })),
|
|
1172
|
+
ix,
|
|
1173
|
+
...(await this.flavor.postIxs({ signer: depositor })),
|
|
1174
|
+
],
|
|
1175
|
+
setupIxs: [tokenSyAtaIx, tokenYtAtaIx, tokenPtAtaIx, tokenLpAtaIx],
|
|
1176
|
+
};
|
|
1177
|
+
}
|
|
1178
|
+
async ixWithdrawLiquidityToBase({ owner, amountLp, minBaseOut, tokenSyWithdrawer, tokenYtWithdrawer, tokenPtWithdrawer, tokenBaseWithdrawer, tokenLpWithdrawer, }) {
|
|
1179
|
+
tokenSyWithdrawer = tokenSyWithdrawer || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1180
|
+
tokenYtWithdrawer = tokenYtWithdrawer || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1181
|
+
tokenPtWithdrawer = tokenPtWithdrawer || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1182
|
+
tokenBaseWithdrawer =
|
|
1183
|
+
tokenBaseWithdrawer ||
|
|
1184
|
+
(0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, owner, true, this.flavor.baseTokenProgram);
|
|
1185
|
+
tokenLpWithdrawer = tokenLpWithdrawer || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1186
|
+
const tokenSyAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenSyWithdrawer, owner, this.mintSy);
|
|
1187
|
+
const tokenYtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenYtWithdrawer, owner, this.mintYt);
|
|
1188
|
+
const tokenPtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenPtWithdrawer, owner, this.mintPt);
|
|
1189
|
+
const tokenBaseAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenBaseWithdrawer, owner, this.flavor.mintBase, this.flavor.baseTokenProgram);
|
|
1190
|
+
const tokenLpAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenLpWithdrawer, owner, this.mintLp);
|
|
1191
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner });
|
|
1192
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
1193
|
+
...this.cpiAccounts.withdrawSy,
|
|
1194
|
+
...this.cpiAccounts.getPositionState,
|
|
1195
|
+
]);
|
|
1196
|
+
const redeemSyIx = await this.flavor.ixRedeemSy({
|
|
1197
|
+
amountSy: "0",
|
|
1198
|
+
redeemer: owner,
|
|
1199
|
+
redeemerBaseTokenAccount: tokenBaseWithdrawer,
|
|
1200
|
+
redeemerSyTokenAccount: tokenSyWithdrawer,
|
|
1201
|
+
});
|
|
1202
|
+
const redeemSyRemAccounts = redeemSyIx.keys;
|
|
1203
|
+
const minSyOut = Number(minBaseOut) / this.currentSyExchangeRate;
|
|
1204
|
+
const ix = await this.coreProgram.methods
|
|
1205
|
+
.wrapperWithdrawLiquidity(new anchor_2.BN(amountLp.toString()), new anchor_2.BN(minSyOut.toFixed(0).toString()), redeemSyRemAccounts.length)
|
|
1206
|
+
.accountsStrict({
|
|
1207
|
+
market: this.selfAddress,
|
|
1208
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
1209
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
1210
|
+
tokenLpSrc: tokenLpWithdrawer,
|
|
1211
|
+
lpPosition,
|
|
1212
|
+
marketAddressLookupTable: this.addressLookupTable,
|
|
1213
|
+
eventAuthority: this.vault.eventAuthority,
|
|
1214
|
+
program: this.coreProgram.programId,
|
|
1215
|
+
syProgram: this.syProgram,
|
|
1216
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
1217
|
+
tokenFeeTreasurySy: this.state.tokenFeeTreasurySy,
|
|
1218
|
+
tokenLpEscrow: this.tokenLpEscrow,
|
|
1219
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
1220
|
+
tokenPtWithdrawer,
|
|
1221
|
+
tokenSyWithdrawer,
|
|
1222
|
+
mintLp: this.mintLp,
|
|
1223
|
+
withdrawer: owner,
|
|
1224
|
+
})
|
|
1225
|
+
.remainingAccounts(redeemSyRemAccounts.concat(remainingAccounts))
|
|
1226
|
+
.instruction();
|
|
1227
|
+
return {
|
|
1228
|
+
ixs: [...(await this.flavor.preIxs({ signer: owner })), ix, ...(await this.flavor.postIxs({ signer: owner }))],
|
|
1229
|
+
setupIxs: [tokenSyAtaIx, tokenYtAtaIx, tokenPtAtaIx, tokenBaseAtaIx, tokenLpAtaIx],
|
|
1230
|
+
};
|
|
1231
|
+
}
|
|
1232
|
+
async ixWithdrawLiquidityClassic({ owner, amountLp, minBaseOut, tokenSyWithdrawer, tokenYtWithdrawer, tokenPtWithdrawer, tokenBaseWithdrawer, tokenLpWithdrawer, }) {
|
|
1233
|
+
tokenSyWithdrawer = tokenSyWithdrawer || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintSy, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1234
|
+
tokenYtWithdrawer = tokenYtWithdrawer || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintYt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1235
|
+
tokenPtWithdrawer = tokenPtWithdrawer || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintPt, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1236
|
+
tokenBaseWithdrawer =
|
|
1237
|
+
tokenBaseWithdrawer ||
|
|
1238
|
+
(0, spl_token_1.getAssociatedTokenAddressSync)(this.flavor.mintBase, owner, true, this.flavor.baseTokenProgram);
|
|
1239
|
+
tokenLpWithdrawer = tokenLpWithdrawer || (0, spl_token_1.getAssociatedTokenAddressSync)(this.mintLp, owner, true, spl_token_1.TOKEN_PROGRAM_ID);
|
|
1240
|
+
const tokenSyAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenSyWithdrawer, owner, this.mintSy);
|
|
1241
|
+
const tokenYtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenYtWithdrawer, owner, this.mintYt);
|
|
1242
|
+
const tokenPtAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenPtWithdrawer, owner, this.mintPt);
|
|
1243
|
+
const tokenBaseAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenBaseWithdrawer, owner, this.flavor.mintBase, this.flavor.baseTokenProgram);
|
|
1244
|
+
const tokenLpAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenLpWithdrawer, owner, this.mintLp);
|
|
1245
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner });
|
|
1246
|
+
const remainingAccounts = (0, utils_1.uniqueRemainingAccounts)([
|
|
1247
|
+
...this.cpiAccounts.withdrawSy,
|
|
1248
|
+
...this.cpiAccounts.getPositionState,
|
|
1249
|
+
]);
|
|
1250
|
+
const redeemSyIx = await this.flavor.ixRedeemSy({
|
|
1251
|
+
amountSy: "0",
|
|
1252
|
+
redeemer: owner,
|
|
1253
|
+
redeemerBaseTokenAccount: tokenBaseWithdrawer,
|
|
1254
|
+
redeemerSyTokenAccount: tokenSyWithdrawer,
|
|
1255
|
+
});
|
|
1256
|
+
const redeemSyRemAccounts = redeemSyIx.keys;
|
|
1257
|
+
const ixn = await this.coreProgram.methods
|
|
1258
|
+
.wrapperWithdrawLiquidityClassic(new anchor_2.BN(amountLp.toString()), redeemSyRemAccounts.length)
|
|
1259
|
+
.accountsStrict({
|
|
1260
|
+
market: this.selfAddress,
|
|
1261
|
+
tokenPtEscrow: this.tokenPtEscrow,
|
|
1262
|
+
tokenSyEscrow: this.tokenSyEscrow,
|
|
1263
|
+
tokenLpSrc: tokenLpWithdrawer,
|
|
1264
|
+
lpPosition,
|
|
1265
|
+
marketAddressLookupTable: this.addressLookupTable,
|
|
1266
|
+
eventAuthority: this.vault.eventAuthority,
|
|
1267
|
+
program: this.coreProgram.programId,
|
|
1268
|
+
syProgram: this.syProgram,
|
|
1269
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
1270
|
+
tokenLpEscrow: this.tokenLpEscrow,
|
|
1271
|
+
tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
|
|
1272
|
+
tokenPtWithdrawer,
|
|
1273
|
+
tokenSyWithdrawer,
|
|
1274
|
+
mintLp: this.mintLp,
|
|
1275
|
+
withdrawer: owner,
|
|
1276
|
+
})
|
|
1277
|
+
.remainingAccounts(redeemSyRemAccounts.concat(remainingAccounts))
|
|
1278
|
+
.instruction();
|
|
1279
|
+
return {
|
|
1280
|
+
ixs: [...(await this.flavor.preIxs({ signer: owner })), ixn, ...(await this.flavor.postIxs({ signer: owner }))],
|
|
1281
|
+
setupIxs: [tokenSyAtaIx, tokenYtAtaIx, tokenPtAtaIx, tokenBaseAtaIx, tokenLpAtaIx],
|
|
1282
|
+
};
|
|
1283
|
+
}
|
|
1284
|
+
async claimFarmEmissions({ owner, mint, tokenProgram, tokenDst, }) {
|
|
1285
|
+
tokenDst = tokenDst || (0, spl_token_1.getAssociatedTokenAddressSync)(mint, owner, true, tokenProgram);
|
|
1286
|
+
const lpPosition = this.xponPda.marketLpPosition({ market: this.selfAddress, owner });
|
|
1287
|
+
const tokenFarm = (0, spl_token_1.getAssociatedTokenAddressSync)(mint, this.selfAddress, true, tokenProgram);
|
|
1288
|
+
const tokenAtaIx = (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(owner, tokenDst, owner, mint);
|
|
1289
|
+
const ix = await this.coreProgram.methods
|
|
1290
|
+
.claimFarmEmissions({ all: {} })
|
|
1291
|
+
.accountsStrict({
|
|
1292
|
+
market: this.selfAddress,
|
|
1293
|
+
lpPosition,
|
|
1294
|
+
mint,
|
|
1295
|
+
tokenFarm,
|
|
1296
|
+
owner,
|
|
1297
|
+
tokenDst,
|
|
1298
|
+
tokenProgram,
|
|
1299
|
+
eventAuthority: this.eventAuthority,
|
|
1300
|
+
program: this.coreProgram.programId,
|
|
1301
|
+
})
|
|
1302
|
+
.instruction();
|
|
1303
|
+
return {
|
|
1304
|
+
ixs: [ix],
|
|
1305
|
+
setupIxs: [tokenAtaIx],
|
|
1306
|
+
};
|
|
1307
|
+
}
|
|
1308
|
+
async ixAddStandaloneEmission({ signer, emissionMint, emissionTokenProgram = spl_token_1.TOKEN_PROGRAM_ID, altAddresses, cpiAccounts, }) {
|
|
1309
|
+
const altUtil = (0, altUtil_1.extendAddressLookupTable)(altAddresses, cpiAccounts);
|
|
1310
|
+
const tokenEmission = (0, spl_token_1.getAssociatedTokenAddressSync)(emissionMint, this.selfAddress, true, emissionTokenProgram);
|
|
1311
|
+
const ix = await this.coreProgram.methods
|
|
1312
|
+
.addMarketEmission(altUtil.cpiAccountIndexes)
|
|
1313
|
+
.accountsStrict({
|
|
1314
|
+
market: this.selfAddress,
|
|
1315
|
+
adminState: (0, utils_1.getExponentAdminStatePda)(),
|
|
1316
|
+
feePayer: signer,
|
|
1317
|
+
mintNew: emissionMint,
|
|
1318
|
+
signer,
|
|
1319
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
1320
|
+
tokenEmission,
|
|
1321
|
+
tokenProgram: emissionTokenProgram,
|
|
1322
|
+
})
|
|
1323
|
+
.instruction();
|
|
1324
|
+
return {
|
|
1325
|
+
extendAddressLookupTableExtensionAccounts: altUtil.addressLookupTableExtension,
|
|
1326
|
+
addMarketEmissionIx: ix,
|
|
1327
|
+
};
|
|
1328
|
+
}
|
|
1329
|
+
async addFarm({ signer, farmMint, farmRewardTokenProgram, emissionsRate, untilTimestamp, farmRewardSrc, feePayer, }) {
|
|
1330
|
+
feePayer = feePayer || signer;
|
|
1331
|
+
const farmRewardEscrow = (0, spl_token_1.getAssociatedTokenAddressSync)(farmMint, this.selfAddress, true, farmRewardTokenProgram);
|
|
1332
|
+
farmRewardSrc = farmRewardSrc || (0, spl_token_1.getAssociatedTokenAddressSync)(farmMint, signer, true, farmRewardTokenProgram);
|
|
1333
|
+
const ix = await this.coreProgram.methods
|
|
1334
|
+
.addFarm(new anchor_2.BN(emissionsRate), untilTimestamp)
|
|
1335
|
+
.accountsStrict({
|
|
1336
|
+
adminState: (0, utils_1.getExponentAdminStatePda)(),
|
|
1337
|
+
market: this.selfAddress,
|
|
1338
|
+
feePayer,
|
|
1339
|
+
signer,
|
|
1340
|
+
mintNew: farmMint,
|
|
1341
|
+
tokenFarm: farmRewardEscrow,
|
|
1342
|
+
tokenProgram: farmRewardTokenProgram,
|
|
1343
|
+
systemProgram: anchor_1.web3.SystemProgram.programId,
|
|
1344
|
+
tokenSource: farmRewardSrc,
|
|
1345
|
+
})
|
|
1346
|
+
.instruction();
|
|
1347
|
+
return {
|
|
1348
|
+
ixs: [ix],
|
|
1349
|
+
};
|
|
1350
|
+
}
|
|
1351
|
+
/** Calculate available liquidity for PT trades
|
|
1352
|
+
* @param is_buy - true if buying PT with SY, false if selling PT for SY
|
|
1353
|
+
* @param size_pt - amount of PT to trade (in PT decimals)
|
|
1354
|
+
* @returns amount of PT that can be traded given current liquidity
|
|
1355
|
+
*/
|
|
1356
|
+
liquidityAvailable(is_buy, size_pt) {
|
|
1357
|
+
const calc = this.marketCalculator();
|
|
1358
|
+
if (is_buy) {
|
|
1359
|
+
// When buying PT, we're limited by SY liquidity
|
|
1360
|
+
// Convert PT amount to SY using current price
|
|
1361
|
+
const syNeeded = Number(size_pt) * calc.exchangeRate;
|
|
1362
|
+
// Available SY in the market
|
|
1363
|
+
const syAvailable = Number(this.syBalance);
|
|
1364
|
+
if (syNeeded <= syAvailable) {
|
|
1365
|
+
return size_pt;
|
|
1366
|
+
}
|
|
1367
|
+
else {
|
|
1368
|
+
// Calculate max PT that can be bought with available SY
|
|
1369
|
+
return BigInt(Math.floor(syAvailable / calc.exchangeRate));
|
|
1370
|
+
}
|
|
1371
|
+
}
|
|
1372
|
+
else {
|
|
1373
|
+
// When selling PT, we're limited by PT liquidity in the market
|
|
1374
|
+
const ptAvailable = this.ptBalance;
|
|
1375
|
+
if (size_pt <= ptAvailable) {
|
|
1376
|
+
return size_pt;
|
|
1377
|
+
}
|
|
1378
|
+
else {
|
|
1379
|
+
return ptAvailable;
|
|
1380
|
+
}
|
|
1381
|
+
}
|
|
1382
|
+
}
|
|
1383
|
+
}
|
|
1384
|
+
exports.Market = Market;
|
|
1385
|
+
function toJson(m) {
|
|
1386
|
+
const c = m.marketCalculator();
|
|
1387
|
+
return {
|
|
1388
|
+
treasurySyTokenAccount: m.state.tokenFeeTreasurySy.toBase58(),
|
|
1389
|
+
address: m.selfAddress.toBase58(),
|
|
1390
|
+
addressLookupTable: m.addressLookupTable.toBase58(),
|
|
1391
|
+
tokenSyEscrow: m.tokenSyEscrow.toBase58(),
|
|
1392
|
+
tokenPtEscrow: m.tokenPtEscrow.toBase58(),
|
|
1393
|
+
tokenLpEscrow: m.tokenLpEscrow.toBase58(),
|
|
1394
|
+
lpSupply: m.state.lpSupply.toString(),
|
|
1395
|
+
syProgram: m.state.syProgram.toBase58(),
|
|
1396
|
+
mintPt: m.state.mintPt.toBase58(),
|
|
1397
|
+
mintSy: m.state.mintSy.toBase58(),
|
|
1398
|
+
mintLp: m.state.mintLp.toBase58(),
|
|
1399
|
+
feeTreasurySyBps: m.state.feeTreasurySyBps,
|
|
1400
|
+
ptBalance: m.state.ptBalance.toString(),
|
|
1401
|
+
syBalance: m.state.syBalance.toString(),
|
|
1402
|
+
currentSyRate: m.flavor.currentSyExchangeRate,
|
|
1403
|
+
expirationTs: m.state.expirationTs,
|
|
1404
|
+
expirationDate: new Date(m.state.expirationTs * 1000).toISOString(),
|
|
1405
|
+
lnFeeRateRoot: m.state.lnFeeRateRoot,
|
|
1406
|
+
rateScalarRoot: m.state.rateScalarRoot,
|
|
1407
|
+
lastLnImpliedRate: m.state.lastLnImpliedRate,
|
|
1408
|
+
currentPtPriceInSy: m.currentPtPriceInSy,
|
|
1409
|
+
currentPtPriceInAsset: m.currentPtPriceInAsset,
|
|
1410
|
+
secondsRemaining: m.secondsRemaining,
|
|
1411
|
+
proportionPtInAsset: c.proportionPtInAsset,
|
|
1412
|
+
proportionPtInSy: c.proportionPtInSy,
|
|
1413
|
+
currentFeeRate: c.feeRate,
|
|
1414
|
+
currentRateScalar: c.rateScalar,
|
|
1415
|
+
currentRateAnchor: c.findRateAnchor(),
|
|
1416
|
+
cpiAccounts: (0, exponent_ix_2.serializeCpiAccountsRaw)(m.cpiAccounts),
|
|
1417
|
+
emissions: {
|
|
1418
|
+
trackers: m.marketEmissions.trackers.map((e) => ({
|
|
1419
|
+
tokenEscrow: e.tokenEscrow.toBase58(),
|
|
1420
|
+
lpShareIndex: e.lpShareIndex,
|
|
1421
|
+
lastSeenStaged: e.lastSeenStaged,
|
|
1422
|
+
})),
|
|
1423
|
+
},
|
|
1424
|
+
ptApr: m.ptApr,
|
|
1425
|
+
lpEscrowAmount: m.state.lpEscrowAmount.toString(),
|
|
1426
|
+
maxLpSupply: m.state.maxLpSupply.toString(),
|
|
1427
|
+
liquidityNetBalanceLimits: {
|
|
1428
|
+
windowStartTimestamp: m.state.liquidityNetBalanceLimits.windowStartTimestamp,
|
|
1429
|
+
windowStartNetBalance: m.state.liquidityNetBalanceLimits.windowStartNetBalance.toString(),
|
|
1430
|
+
maxNetBalanceChangeNegativePercentage: m.state.liquidityNetBalanceLimits.maxNetBalanceChangeNegativePercentage,
|
|
1431
|
+
maxNetBalanceChangePositivePercentage: m.state.liquidityNetBalanceLimits.maxNetBalanceChangePositivePercentage,
|
|
1432
|
+
windowDurationSeconds: m.state.liquidityNetBalanceLimits.windowDurationSeconds,
|
|
1433
|
+
},
|
|
1434
|
+
lpFarm: {
|
|
1435
|
+
lastSeenTimestamp: m.state.lpFarm.lastSeenTimestamp,
|
|
1436
|
+
farmEmissions: m.state.lpFarm.farmEmissions.map((e) => ({
|
|
1437
|
+
mint: e.mint.toBase58(),
|
|
1438
|
+
tokenRate: e.tokenRate.toString(),
|
|
1439
|
+
expiryTimestamp: e.expiryTimestamp,
|
|
1440
|
+
index: precise_number_1.PreciseNumber.fromRaw(e.index[0]).valueString,
|
|
1441
|
+
})),
|
|
1442
|
+
},
|
|
1443
|
+
};
|
|
1444
|
+
}
|
|
1445
|
+
//# sourceMappingURL=market.js.map
|