proof-of-take-sdk 5.0.10 → 5.0.12

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.
@@ -1,10 +1,12 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.joinSeason = joinSeason;
4
- exports.joinSeasonClassic = joinSeasonClassic;
3
+ exports.createMoonpool = createMoonpool;
4
+ exports.joinMoonpoolSeason = joinMoonpoolSeason;
5
+ exports.joinSunpool = joinSunpool;
5
6
  exports.joinSeasonLaunchpad = joinSeasonLaunchpad;
6
- exports.joinSeasonAndInitialize = joinSeasonAndInitialize;
7
- exports.joinSeasonLaunchpadAndInitialize = joinSeasonLaunchpadAndInitialize;
7
+ exports.joinSeasonLaunchpadAndInitialize = joinSeasonLaunchpad;
8
+ exports.joinSeasonClassic = joinSeasonClassic;
9
+ exports.joinSeasonAndInitialize = joinSeasonClassic;
8
10
  const anchor_1 = require("@coral-xyz/anchor");
9
11
  const web3_js_1 = require("@solana/web3.js");
10
12
  const spl_token_1 = require("@solana/spl-token");
@@ -13,262 +15,319 @@ const pdas_1 = require("../utils/pdas");
13
15
  const constants_1 = require("../utils/constants");
14
16
  const programHelpers_1 = require("../utils/programHelpers");
15
17
  const signerHelpers_1 = require("../utils/signerHelpers");
16
- const optimistic_1 = require("../optimistic");
17
- const remainingAccounts_1 = require("../utils/remainingAccounts");
18
18
  /**
19
- * Join a season
20
- *
21
- * Signers: user + root admin (root admin pays for signup-rewards vault ATA creation when a referrer is present)
22
- * User pays for season (if needed) and membership accounts
23
- * Transfers active deposit into the season vault; the late-join escrow portion is converted into non-withdrawable join credit
19
+ * Create a new Moonpool and perform the first launchpad join.
24
20
  *
25
- * IMPORTANT: If providing a referrer, you MUST also provide referrerTier.
26
- * The referrerTier must match the tier the referrer actually joined the season with.
27
- * The referrer must have already joined the season before being used as a referrer.
21
+ * This instruction:
22
+ * - Creates a new launchpad_token_mint (SPL Token-2022)
23
+ * - Initializes the Moonpool
24
+ * - Initializes the Season (scoped to launchpad_token_mint)
25
+ * - Creates the first SeasonMembership
28
26
  *
29
- * @param options - Join season options
30
- * @returns Instructions, signers, PDAs, and optimistically created/updated accounts
27
+ * @param options - CreateMoonpool options
28
+ * @returns Instructions, signers, PDAs, and metadata with the generated keypair
31
29
  */
32
- async function joinSeason(options) {
30
+ async function createMoonpool(options) {
33
31
  const program = (0, programHelpers_1.getProgram)(options.connection);
34
- const tokenMint = options.tokenMint ?? constants_1.MIZD_TOKEN_MINT;
35
- const launchpad = options.launchpad ?? false;
32
+ // Validate required fields
33
+ if (!options.starFlagPrompt || options.starFlagPrompt.length === 0) {
34
+ throw new Error("starFlagPrompt is required when creating a new Moonpool");
35
+ }
36
+ if (options.starFlagPrompt.length > 33) {
37
+ throw new Error("starFlagPrompt cannot exceed 33 characters");
38
+ }
39
+ if (!options.symbol || options.symbol.length === 0) {
40
+ throw new Error("symbol is required when creating a new Moonpool");
41
+ }
42
+ if (options.symbol.length > 4) {
43
+ throw new Error("symbol cannot exceed 4 characters");
44
+ }
45
+ // Generate a new keypair for the launchpad token mint
46
+ const launchpadTokenMintKeypair = web3_js_1.Keypair.generate();
47
+ const launchpadTokenMintPubkey = launchpadTokenMintKeypair.publicKey;
48
+ console.log("[createMoonpool] Generated new launchpad mint keypair:", launchpadTokenMintPubkey.toString());
49
+ // Derive PDAs with the new launchpadTokenMint
36
50
  const pdasBase = pdaManager_1.PDAManager.deriveJoinSeasonPdas({
37
51
  user: options.user,
38
52
  seasonNumber: options.seasonNumber,
39
53
  tier: options.tier,
40
- tokenMint,
54
+ tokenMint: constants_1.MIZD_TOKEN_MINT,
55
+ launchpadTokenMint: launchpadTokenMintPubkey,
41
56
  });
42
- // Auto-generate keypair for launchpad mode when moonpool is being initialized
43
- let launchpadTokenMintKeypair;
44
- let launchpadTokenMintPubkey;
45
- if (launchpad) {
46
- // If forceNewLaunchpadMint is set, skip on-chain checks and always generate a new keypair
47
- if (options.forceNewLaunchpadMint) {
48
- launchpadTokenMintKeypair = web3_js_1.Keypair.generate();
49
- launchpadTokenMintPubkey = launchpadTokenMintKeypair.publicKey;
50
- console.log("[joinSeason] forceNewLaunchpadMint=true - generated new launchpad mint keypair:", launchpadTokenMintPubkey.toString());
51
- }
52
- else {
53
- // For non-force mode, we need an existing launchpadTokenMint to find the moonpool
54
- // Check currentAccounts first (for LiteSVM or optimistic updates)
55
- let moonpoolData = options.currentAccounts?.moonpool ?? null;
56
- if (moonpoolData && !moonpoolData.launchpadTokenMint.equals(web3_js_1.PublicKey.default)) {
57
- // Use the launchpadTokenMint from the provided moonpool data
58
- launchpadTokenMintPubkey = moonpoolData.launchpadTokenMint;
59
- console.log("[joinSeason] Using launchpadTokenMint from currentAccounts:", launchpadTokenMintPubkey.toString());
60
- }
61
- else {
62
- // No moonpool data provided - this is a first join scenario
63
- // Generate a keypair for the mint (the mint will be created on-chain)
64
- launchpadTokenMintKeypair = web3_js_1.Keypair.generate();
65
- launchpadTokenMintPubkey = launchpadTokenMintKeypair.publicKey;
66
- console.log("[joinSeason] First join - generated launchpad mint keypair:", launchpadTokenMintPubkey.toString());
67
- }
68
- }
69
- }
70
- else {
71
- // Non-launchpad mode, use PDA
72
- launchpadTokenMintPubkey = pdasBase.launchpadTokenMint;
73
- }
74
- // Derive Moonpool and Treasury PDAs using the launchpadTokenMint
57
+ // Derive Moonpool and Treasury PDAs
75
58
  const [moonpoolPda] = (0, pdas_1.getMoonpoolPda)(launchpadTokenMintPubkey);
76
59
  const [moonpoolTreasuryPda] = (0, pdas_1.getMoonpoolTreasuryPda)(launchpadTokenMintPubkey);
77
- const rootAdminTokenAccount = launchpad
78
- ? null
79
- : (0, spl_token_1.getAssociatedTokenAddressSync)(constants_1.MIZD_TOKEN_MINT, constants_1.ADMIN_PUBLIC_KEY);
80
- const userMizdAta = launchpad
81
- ? null
82
- : (0, spl_token_1.getAssociatedTokenAddressSync)(constants_1.MIZD_TOKEN_MINT, options.user);
83
- // Join credit PDA + its vault ATA (owner is off-curve PDA, so allowOwnerOffCurve=true).
84
- const userJoinCreditVault = launchpad
85
- ? null
86
- : (0, spl_token_1.getAssociatedTokenAddressSync)(constants_1.MIZD_TOKEN_MINT, pdasBase.userJoinCredit, true);
87
60
  const pdas = {
88
- ...pdasBase,
61
+ seasonSettings: pdasBase.seasonSettings,
62
+ season: pdasBase.season,
63
+ seasonMembership: pdasBase.seasonMembership,
89
64
  moonpool: moonpoolPda,
90
65
  moonpoolTreasury: moonpoolTreasuryPda,
91
66
  launchpadTokenMint: launchpadTokenMintPubkey,
92
- userJoinCreditVault: userJoinCreditVault ?? web3_js_1.PublicKey.default,
93
67
  };
68
+ const referrer = options.referrer ?? web3_js_1.PublicKey.default;
94
69
  const accounts = {
95
70
  seasonSettings: pdas.seasonSettings,
96
71
  season: pdas.season,
97
72
  seasonMembership: pdas.seasonMembership,
98
- // SECURITY: Pool accounts are now MANDATORY (non-optional) to prevent bypassing
99
- // the mode check. The on-chain program validates pool state to ensure
100
- // subsequent seasons use the same mode (launchpad/classic) as the first season.
101
73
  moonpool: moonpoolPda,
102
74
  moonpoolTreasury: moonpoolTreasuryPda,
103
- launchpadTokenMint: pdas.launchpadTokenMint,
104
- sunpool: pdas.sunpool,
105
- seasonDepositVault: launchpad ? null : pdas.seasonDepositVault,
106
- userJoinCredit: launchpad ? null : pdas.userJoinCredit,
107
- userJoinCreditVault: launchpad ? null : userJoinCreditVault,
108
- mizdMint: constants_1.MIZD_TOKEN_MINT,
109
- tokenMint,
75
+ launchpadTokenMint: launchpadTokenMintPubkey,
110
76
  rootAdmin: constants_1.ADMIN_PUBLIC_KEY,
111
- rootAdminTokenAccount,
112
- // Always pass the canonical ATA; it may not exist yet (created on-chain with root admin as payer).
113
- userTokenAccount: userMizdAta,
114
77
  user: options.user,
115
- associatedTokenProgram: spl_token_1.ASSOCIATED_TOKEN_PROGRAM_ID,
116
- tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
117
78
  token2022Program: spl_token_1.TOKEN_2022_PROGRAM_ID,
118
79
  systemProgram: web3_js_1.SystemProgram.programId,
119
80
  };
120
- const referrer = options.referrer ?? web3_js_1.PublicKey.default;
121
- const hasReferrer = !referrer.equals(web3_js_1.PublicKey.default);
122
- // Validate: if referrer is provided, referrerTier must also be provided
123
- if (hasReferrer && options.referrerTier === undefined) {
124
- throw new Error("referrerTier is required when referrer is provided");
125
- }
126
- const remainingAccounts = hasReferrer
127
- ? (0, remainingAccounts_1.getJoinSeasonRemainingAccounts)({
128
- seasonNumber: options.seasonNumber,
129
- tier: options.tier,
130
- referrer,
131
- referrerTier: options.referrerTier,
132
- tokenMint,
133
- })
134
- : [];
135
- const methodBuilder = program.methods
136
- // Anchor expects BN for u64 args.
137
- // referrerTier defaults to 0 if no referrer (ignored on-chain)
138
- .joinSeason(options.seasonNumber, options.tier, referrer, options.referrerTier ?? 0, options.star ?? false, launchpad, options.maxSolInLamports ?? new anchor_1.BN(0), options.expectedSolInLamports ?? new anchor_1.BN(0), options.maxSlippageBps ?? 0, options.starFlagPrompt ?? "", options.symbol ?? "", options.forceNewLaunchpadMint ?? false)
139
- .accounts(accounts);
140
- if (remainingAccounts.length > 0) {
141
- methodBuilder.remainingAccounts(remainingAccounts);
142
- }
143
- const instruction = await methodBuilder.instruction();
144
- // For star joins, make the transaction fully sponsored: force the fee payer to be the root admin.
145
- // This prevents clients from accidentally using an unfunded/nonexistent fee payer account.
81
+ const instruction = await program.methods
82
+ .createMoonpool(options.seasonNumber, options.tier, referrer, options.star ?? false, options.maxSolInLamports ?? new anchor_1.BN(0), options.expectedSolInLamports ?? new anchor_1.BN(0), options.maxSlippageBps ?? 0, options.starFlagPrompt, options.symbol)
83
+ .accounts(accounts)
84
+ .instruction();
85
+ // For star joins, root admin pays
146
86
  const feePayer = options.star ? constants_1.ADMIN_PUBLIC_KEY : (0, signerHelpers_1.getDefaultFeePayer)(options.feePayer);
147
- // Build signers array
148
- const signersList = [(0, signerHelpers_1.asAdminSigner)(constants_1.ADMIN_PUBLIC_KEY), (0, signerHelpers_1.asUserSigner)(options.user)];
149
- // Add launchpad token mint keypair as signer if it exists (either provided or auto-generated)
150
- if (launchpad && launchpadTokenMintKeypair) {
151
- signersList.push({
152
- publicKey: launchpadTokenMintKeypair.publicKey,
153
- role: "payer", // Use 'payer' role for the mint keypair
154
- });
155
- }
87
+ // Build signers array - must include the launchpad mint keypair
88
+ const signersList = [
89
+ (0, signerHelpers_1.asAdminSigner)(constants_1.ADMIN_PUBLIC_KEY),
90
+ (0, signerHelpers_1.asUserSigner)(options.user),
91
+ { publicKey: launchpadTokenMintKeypair.publicKey, role: "payer" },
92
+ ];
156
93
  const signers = (0, signerHelpers_1.buildSigners)(signersList, feePayer);
157
- // OPTIMISTIC UPDATES
158
- const curr = options.currentAccounts || {};
159
- const now = (0, optimistic_1.getCurrentTimestamp)(options.now);
160
- let newSeasonMembership;
161
- let updatedSeason;
162
- if (curr.seasonSettings) {
163
- const optimistic = (0, optimistic_1.computeJoinSeasonOptimistic)({
164
- user: options.user,
165
- seasonNumber: options.seasonNumber,
166
- tier: options.tier,
167
- referrer: options.referrer ?? web3_js_1.PublicKey.default,
168
- tokenMint,
169
- now,
170
- star: options.star ?? false,
171
- seasonSettings: curr.seasonSettings,
172
- ...(curr.season ? { season: curr.season } : {}),
173
- });
174
- if (optimistic.kind === "skip") {
175
- return {
176
- instructions: [instruction],
177
- signers,
178
- pdas,
179
- };
180
- }
181
- newSeasonMembership = optimistic.newSeasonMembership;
182
- updatedSeason = optimistic.updatedSeason;
183
- }
184
94
  return {
185
95
  instructions: [instruction],
186
96
  signers,
187
97
  pdas,
188
- ...(curr.seasonSettings || updatedSeason || newSeasonMembership
189
- ? {
190
- updatedAccounts: {
191
- ...(curr.seasonSettings && { seasonSettings: curr.seasonSettings }),
192
- ...(updatedSeason && { season: updatedSeason }),
193
- ...(newSeasonMembership && {
194
- seasonMembership: newSeasonMembership,
195
- }),
196
- },
197
- }
198
- : {}),
199
- ...(launchpadTokenMintKeypair
200
- ? {
201
- meta: {
202
- launchpadTokenMintKeypair,
203
- },
204
- }
205
- : {}),
98
+ metadata: {
99
+ launchpadTokenMintKeypair,
100
+ },
206
101
  };
207
102
  }
208
103
  /**
209
- * Convenience wrapper: classic (non-launchpad) joinSeason.
210
- * - Keeps the existing MIZD-based join behavior.
211
- * - App code never passes nullable optional accounts.
104
+ * Join an existing Moonpool season.
105
+ *
106
+ * This instruction:
107
+ * - Requires Moonpool to already exist
108
+ * - Lazily initializes Season if needed (for new seasons with existing Moonpool)
109
+ * - Creates new SeasonMembership
110
+ *
111
+ * @param options - JoinMoonpoolSeason options
112
+ * @returns Instructions, signers, and PDAs
212
113
  */
213
- async function joinSeasonClassic(options) {
214
- // IMPORTANT: With `exactOptionalPropertyTypes`, we must OMIT optional props (not set them to `undefined`).
215
- return joinSeason({ ...options, launchpad: false });
114
+ async function joinMoonpoolSeason(options) {
115
+ const program = (0, programHelpers_1.getProgram)(options.connection);
116
+ const launchpadTokenMintPubkey = options.launchpadTokenMint;
117
+ console.log("[joinMoonpoolSeason] Using existing launchpadTokenMint:", launchpadTokenMintPubkey.toString());
118
+ // Derive PDAs with the existing launchpadTokenMint
119
+ const pdasBase = pdaManager_1.PDAManager.deriveJoinSeasonPdas({
120
+ user: options.user,
121
+ seasonNumber: options.seasonNumber,
122
+ tier: options.tier,
123
+ tokenMint: constants_1.MIZD_TOKEN_MINT,
124
+ launchpadTokenMint: launchpadTokenMintPubkey,
125
+ });
126
+ // Derive Moonpool and Treasury PDAs
127
+ const [moonpoolPda] = (0, pdas_1.getMoonpoolPda)(launchpadTokenMintPubkey);
128
+ const [moonpoolTreasuryPda] = (0, pdas_1.getMoonpoolTreasuryPda)(launchpadTokenMintPubkey);
129
+ const pdas = {
130
+ seasonSettings: pdasBase.seasonSettings,
131
+ season: pdasBase.season,
132
+ seasonMembership: pdasBase.seasonMembership,
133
+ moonpool: moonpoolPda,
134
+ moonpoolTreasury: moonpoolTreasuryPda,
135
+ launchpadTokenMint: launchpadTokenMintPubkey,
136
+ };
137
+ const referrer = options.referrer ?? web3_js_1.PublicKey.default;
138
+ const accounts = {
139
+ seasonSettings: pdas.seasonSettings,
140
+ season: pdas.season,
141
+ seasonMembership: pdas.seasonMembership,
142
+ moonpool: moonpoolPda,
143
+ moonpoolTreasury: moonpoolTreasuryPda,
144
+ launchpadTokenMint: launchpadTokenMintPubkey,
145
+ rootAdmin: constants_1.ADMIN_PUBLIC_KEY,
146
+ user: options.user,
147
+ token2022Program: spl_token_1.TOKEN_2022_PROGRAM_ID,
148
+ systemProgram: web3_js_1.SystemProgram.programId,
149
+ };
150
+ const instruction = await program.methods
151
+ .joinMoonpoolSeason(options.seasonNumber, options.tier, referrer, options.star ?? false, options.maxSolInLamports ?? new anchor_1.BN(0), options.expectedSolInLamports ?? new anchor_1.BN(0), options.maxSlippageBps ?? 0)
152
+ .accounts(accounts)
153
+ .instruction();
154
+ // For star joins, root admin pays
155
+ const feePayer = options.star ? constants_1.ADMIN_PUBLIC_KEY : (0, signerHelpers_1.getDefaultFeePayer)(options.feePayer);
156
+ // Build signers array
157
+ const signersList = [
158
+ (0, signerHelpers_1.asAdminSigner)(constants_1.ADMIN_PUBLIC_KEY),
159
+ (0, signerHelpers_1.asUserSigner)(options.user),
160
+ ];
161
+ const signers = (0, signerHelpers_1.buildSigners)(signersList, feePayer);
162
+ return {
163
+ instructions: [instruction],
164
+ signers,
165
+ pdas,
166
+ };
216
167
  }
217
168
  /**
218
- * Convenience wrapper: launchpad joinSeason.
219
- * - Uses SOL in + virtual token escrow.
220
- * - App code never passes nullable optional accounts.
169
+ * Join a Sunpool season (classic mode with MIZD).
170
+ *
171
+ * This instruction:
172
+ * - Lazily initializes Sunpool if needed
173
+ * - Lazily initializes Season if needed
174
+ * - Creates SeasonMembership
175
+ * - Handles MIZD token transfers and join credit
176
+ *
177
+ * @param options - JoinSunpool options
178
+ * @returns Instructions, signers, and PDAs
221
179
  */
222
- async function joinSeasonLaunchpad(options) {
223
- // IMPORTANT: With `exactOptionalPropertyTypes`, we must OMIT optional props (not set them to `undefined`).
224
- const { maxSolInLamports, expectedSolInLamports, maxSlippageBps, ...rest } = options;
225
- return joinSeason({
226
- ...rest,
227
- launchpad: true,
228
- ...(maxSolInLamports ? { maxSolInLamports } : {}),
229
- ...(expectedSolInLamports ? { expectedSolInLamports } : {}),
230
- ...(typeof maxSlippageBps === "number" ? { maxSlippageBps } : {}),
180
+ async function joinSunpool(options) {
181
+ const program = (0, programHelpers_1.getProgram)(options.connection);
182
+ const tokenMint = options.tokenMint ?? constants_1.MIZD_TOKEN_MINT;
183
+ console.log("[joinSunpool] Classic mode join with tokenMint:", tokenMint.toString());
184
+ // Derive PDAs - for Sunpool, use tokenMint for PDA derivation
185
+ const pdasBase = pdaManager_1.PDAManager.deriveJoinSeasonPdas({
186
+ user: options.user,
187
+ seasonNumber: options.seasonNumber,
188
+ tier: options.tier,
189
+ tokenMint,
190
+ launchpadTokenMint: tokenMint, // Sunpool uses tokenMint for Season/Membership PDAs
231
191
  });
192
+ // Derive Sunpool PDA
193
+ const [sunpoolPda] = (0, pdas_1.getSunpoolPda)(tokenMint);
194
+ // User join credit vault ATA
195
+ const userJoinCreditVault = (0, spl_token_1.getAssociatedTokenAddressSync)(constants_1.MIZD_TOKEN_MINT, pdasBase.userJoinCredit, true);
196
+ // Token accounts
197
+ const rootAdminTokenAccount = (0, spl_token_1.getAssociatedTokenAddressSync)(constants_1.MIZD_TOKEN_MINT, constants_1.ADMIN_PUBLIC_KEY);
198
+ const userMizdAta = (0, spl_token_1.getAssociatedTokenAddressSync)(constants_1.MIZD_TOKEN_MINT, options.user);
199
+ const pdas = {
200
+ seasonSettings: pdasBase.seasonSettings,
201
+ season: pdasBase.season,
202
+ seasonMembership: pdasBase.seasonMembership,
203
+ sunpool: sunpoolPda,
204
+ seasonDepositVault: pdasBase.seasonDepositVault,
205
+ userJoinCredit: pdasBase.userJoinCredit,
206
+ userJoinCreditVault,
207
+ };
208
+ const referrer = options.referrer ?? web3_js_1.PublicKey.default;
209
+ const hasReferrer = !referrer.equals(web3_js_1.PublicKey.default);
210
+ // Validate referrer tier
211
+ if (hasReferrer && options.referrerTier === undefined) {
212
+ throw new Error("referrerTier is required when referrer is provided");
213
+ }
214
+ const accounts = {
215
+ seasonSettings: pdas.seasonSettings,
216
+ season: pdas.season,
217
+ seasonMembership: pdas.seasonMembership,
218
+ sunpool: sunpoolPda,
219
+ seasonDepositVault: pdas.seasonDepositVault,
220
+ userJoinCredit: pdas.userJoinCredit,
221
+ userJoinCreditVault,
222
+ mizdMint: constants_1.MIZD_TOKEN_MINT,
223
+ tokenMint,
224
+ rootAdmin: constants_1.ADMIN_PUBLIC_KEY,
225
+ rootAdminTokenAccount,
226
+ userTokenAccount: userMizdAta,
227
+ user: options.user,
228
+ associatedTokenProgram: spl_token_1.ASSOCIATED_TOKEN_PROGRAM_ID,
229
+ tokenProgram: spl_token_1.TOKEN_PROGRAM_ID,
230
+ systemProgram: web3_js_1.SystemProgram.programId,
231
+ };
232
+ const instruction = await program.methods
233
+ .joinSunpool(options.seasonNumber, options.tier, referrer, options.referrerTier ?? 0, options.star ?? false, options.starFlagPrompt ?? "", options.symbol ?? "")
234
+ .accounts(accounts)
235
+ .instruction();
236
+ // For star joins, root admin pays
237
+ const feePayer = options.star ? constants_1.ADMIN_PUBLIC_KEY : (0, signerHelpers_1.getDefaultFeePayer)(options.feePayer);
238
+ // Build signers array
239
+ const signersList = [
240
+ (0, signerHelpers_1.asAdminSigner)(constants_1.ADMIN_PUBLIC_KEY),
241
+ (0, signerHelpers_1.asUserSigner)(options.user),
242
+ ];
243
+ const signers = (0, signerHelpers_1.buildSigners)(signersList, feePayer);
244
+ return {
245
+ instructions: [instruction],
246
+ signers,
247
+ pdas,
248
+ };
232
249
  }
233
250
  /**
234
- * Join season AND initialize it (first joiner).
235
- * Use this when you know the season doesn't exist yet.
251
+ * Convenience wrapper for launchpad mode joins.
252
+ *
253
+ * This function automatically determines whether to call:
254
+ * - createMoonpool (if forceNewLaunchpadMint=true or no existing moonpool)
255
+ * - joinMoonpoolSeason (if joining an existing moonpool)
236
256
  *
237
- * @param options - Options with REQUIRED starFlagPrompt
238
- * @throws Error if starFlagPrompt is empty or exceeds 33 characters
257
+ * @param options - Join options
258
+ * @returns Instructions, signers, PDAs, and metadata
239
259
  */
240
- async function joinSeasonAndInitialize(options) {
241
- // Validate starFlagPrompt
242
- if (!options.starFlagPrompt || options.starFlagPrompt.length === 0) {
243
- throw new Error("starFlagPrompt is required when initializing a new season");
260
+ async function joinSeasonLaunchpad(options) {
261
+ // Determine if we're creating a new Moonpool or joining an existing one
262
+ const shouldCreateNewMoonpool = options.forceNewLaunchpadMint ||
263
+ !options.currentAccounts?.moonpool ||
264
+ options.currentAccounts.moonpool.launchpadTokenMint?.equals(web3_js_1.PublicKey.default);
265
+ if (shouldCreateNewMoonpool) {
266
+ // Creating a new Moonpool - starFlagPrompt and symbol are required
267
+ if (!options.starFlagPrompt) {
268
+ throw new Error("starFlagPrompt is required when creating a new Moonpool");
269
+ }
270
+ if (!options.symbol) {
271
+ throw new Error("symbol is required when creating a new Moonpool");
272
+ }
273
+ return createMoonpool({
274
+ connection: options.connection,
275
+ user: options.user,
276
+ seasonNumber: options.seasonNumber,
277
+ tier: options.tier,
278
+ starFlagPrompt: options.starFlagPrompt,
279
+ symbol: options.symbol,
280
+ ...(options.referrer !== undefined && { referrer: options.referrer }),
281
+ ...(options.star !== undefined && { star: options.star }),
282
+ ...(options.maxSolInLamports !== undefined && { maxSolInLamports: options.maxSolInLamports }),
283
+ ...(options.expectedSolInLamports !== undefined && { expectedSolInLamports: options.expectedSolInLamports }),
284
+ ...(options.maxSlippageBps !== undefined && { maxSlippageBps: options.maxSlippageBps }),
285
+ ...(options.now !== undefined && { now: options.now }),
286
+ ...(options.feePayer !== undefined && { feePayer: options.feePayer }),
287
+ ...(options.currentAccounts !== undefined && { currentAccounts: options.currentAccounts }),
288
+ });
244
289
  }
245
- if (options.starFlagPrompt.length > 33) {
246
- throw new Error("starFlagPrompt cannot exceed 33 characters");
290
+ else {
291
+ // Joining an existing Moonpool
292
+ const launchpadTokenMint = options.currentAccounts.moonpool.launchpadTokenMint;
293
+ return joinMoonpoolSeason({
294
+ connection: options.connection,
295
+ user: options.user,
296
+ seasonNumber: options.seasonNumber,
297
+ launchpadTokenMint,
298
+ tier: options.tier,
299
+ ...(options.referrer !== undefined && { referrer: options.referrer }),
300
+ ...(options.star !== undefined && { star: options.star }),
301
+ ...(options.maxSolInLamports !== undefined && { maxSolInLamports: options.maxSolInLamports }),
302
+ ...(options.expectedSolInLamports !== undefined && { expectedSolInLamports: options.expectedSolInLamports }),
303
+ ...(options.maxSlippageBps !== undefined && { maxSlippageBps: options.maxSlippageBps }),
304
+ ...(options.now !== undefined && { now: options.now }),
305
+ ...(options.feePayer !== undefined && { feePayer: options.feePayer }),
306
+ ...(options.currentAccounts !== undefined && { currentAccounts: options.currentAccounts }),
307
+ });
247
308
  }
248
- return joinSeason(options);
249
309
  }
250
310
  /**
251
- * Join season AND initialize it in launchpad mode (first joiner).
252
- * Use this when you know the season doesn't exist yet and want launchpad mode.
311
+ * Convenience wrapper for classic (non-launchpad) mode joins.
312
+ * Routes to joinSunpool instruction.
253
313
  *
254
- * @param options - Options with REQUIRED starFlagPrompt
255
- * @throws Error if starFlagPrompt is empty or exceeds 33 characters
314
+ * @param options - Join options
315
+ * @returns Instructions, signers, and PDAs
256
316
  */
257
- async function joinSeasonLaunchpadAndInitialize(options) {
258
- // Validate starFlagPrompt
259
- if (!options.starFlagPrompt || options.starFlagPrompt.length === 0) {
260
- throw new Error("starFlagPrompt is required when initializing a new season");
261
- }
262
- if (options.starFlagPrompt.length > 33) {
263
- throw new Error("starFlagPrompt cannot exceed 33 characters");
264
- }
265
- const { maxSolInLamports, expectedSolInLamports, maxSlippageBps, ...rest } = options;
266
- return joinSeason({
267
- ...rest,
268
- launchpad: true,
269
- ...(maxSolInLamports ? { maxSolInLamports } : {}),
270
- ...(expectedSolInLamports ? { expectedSolInLamports } : {}),
271
- ...(typeof maxSlippageBps === "number" ? { maxSlippageBps } : {}),
317
+ async function joinSeasonClassic(options) {
318
+ return joinSunpool({
319
+ connection: options.connection,
320
+ user: options.user,
321
+ seasonNumber: options.seasonNumber,
322
+ tier: options.tier,
323
+ ...(options.tokenMint !== undefined && { tokenMint: options.tokenMint }),
324
+ ...(options.referrer !== undefined && { referrer: options.referrer }),
325
+ ...(options.referrerTier !== undefined && { referrerTier: options.referrerTier }),
326
+ ...(options.star !== undefined && { star: options.star }),
327
+ ...(options.starFlagPrompt !== undefined && { starFlagPrompt: options.starFlagPrompt }),
328
+ ...(options.symbol !== undefined && { symbol: options.symbol }),
329
+ ...(options.now !== undefined && { now: options.now }),
330
+ ...(options.feePayer !== undefined && { feePayer: options.feePayer }),
331
+ ...(options.currentAccounts !== undefined && { currentAccounts: options.currentAccounts }),
272
332
  });
273
333
  }
274
- // getTierPenaltyPerWindow imported from ../utils/tierPenalty