@fogo/sessions-sdk 0.0.29 → 0.0.30

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,6 +1,6 @@
1
- import type { Transaction, Instruction, TransactionWithLifetime, Rpc, GetLatestBlockhashApi } from "@solana/kit";
1
+ import type { GetLatestBlockhashApi, Instruction, Rpc, Transaction, TransactionWithLifetime } from "@solana/kit";
2
2
  import type { TransactionError } from "@solana/web3.js";
3
- import { Keypair, Connection as Web3Connection, TransactionInstruction, VersionedTransaction, PublicKey } from "@solana/web3.js";
3
+ import { Keypair, PublicKey, TransactionInstruction, VersionedTransaction, Connection as Web3Connection } from "@solana/web3.js";
4
4
  export declare enum Network {
5
5
  Testnet = 0,
6
6
  Mainnet = 1
package/cjs/index.d.ts CHANGED
@@ -1,12 +1,12 @@
1
- import type { TransactionError, VersionedTransaction } from "@solana/web3.js";
1
+ import type { TransactionError, TransactionInstruction, VersionedTransaction } from "@solana/web3.js";
2
2
  import { Connection, PublicKey } from "@solana/web3.js";
3
3
  import type { Chain } from "@wormhole-foundation/sdk";
4
4
  import BN from "bn.js";
5
5
  import { z } from "zod";
6
6
  import type { TransactionOrInstructions, TransactionResult } from "./connection.js";
7
7
  import type { SendTransactionOptions, SessionContext } from "./context.js";
8
- export { type SessionContext, type SendTransactionOptions, createSessionContext, } from "./context.js";
9
- export { type TransactionResult, type Connection, type TransactionOrInstructions, Network, TransactionResultType, createSessionConnection, } from "./connection.js";
8
+ export { type Connection, createSessionConnection, Network, type TransactionOrInstructions, type TransactionResult, TransactionResultType, } from "./connection.js";
9
+ export { createSessionContext, type SendTransactionOptions, type SessionContext, } from "./context.js";
10
10
  type EstablishSessionOptions = {
11
11
  context: SessionContext;
12
12
  walletPublicKey: PublicKey;
@@ -2228,6 +2228,9 @@ export type Session = {
2228
2228
  sessionKey: CryptoKeyPair;
2229
2229
  walletPublicKey: PublicKey;
2230
2230
  payer: PublicKey;
2231
+ getSystemProgramSessionWrapInstruction: (amount: bigint) => TransactionInstruction;
2232
+ getSessionWrapInstructions: (amount: bigint) => TransactionInstruction[];
2233
+ getSessionUnwrapInstructions: () => TransactionInstruction[];
2231
2234
  sendTransaction: (instructions: TransactionOrInstructions, extraConfig?: SendTransactionOptions) => Promise<TransactionResult>;
2232
2235
  sessionInfo: NonNullable<z.infer<typeof sessionInfoSchema>>;
2233
2236
  };
@@ -2258,6 +2261,18 @@ type SendTransferOptions = {
2258
2261
  feeConfig: Awaited<ReturnType<typeof getTransferFee>>;
2259
2262
  };
2260
2263
  export declare const sendTransfer: (options: SendTransferOptions) => Promise<TransactionResult>;
2264
+ type SendNativeTransferOptions = {
2265
+ context: SessionContext;
2266
+ walletPublicKey: PublicKey;
2267
+ signMessage: (message: Uint8Array) => Promise<{
2268
+ signedMessage: Uint8Array;
2269
+ signature: Uint8Array;
2270
+ }>;
2271
+ amount: bigint;
2272
+ recipient: PublicKey;
2273
+ feeConfig: Awaited<ReturnType<typeof getTransferFee>>;
2274
+ };
2275
+ export declare const sendNativeTransfer: (options: SendNativeTransferOptions) => Promise<TransactionResult>;
2261
2276
  type SendBridgeOutOptions = {
2262
2277
  context: SessionContext;
2263
2278
  sessionKey: CryptoKeyPair;
package/cjs/index.js CHANGED
@@ -3,7 +3,7 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.verifyLogInToken = exports.createLogInToken = exports.bridgeIn = exports.bridgeOut = exports.sendTransfer = exports.getBridgeOutFee = exports.getTransferFee = exports.SessionResultType = exports.getDomainRecordAddress = exports.AuthorizedTokens = exports.AuthorizedProgramsType = exports.getSessionAccount = exports.reestablishSession = exports.revokeSession = exports.replaceSession = exports.establishSession = exports.createSessionConnection = exports.TransactionResultType = exports.Network = exports.createSessionContext = void 0;
6
+ exports.verifyLogInToken = exports.createLogInToken = exports.bridgeIn = exports.bridgeOut = exports.sendNativeTransfer = exports.sendTransfer = exports.getBridgeOutFee = exports.getTransferFee = exports.SessionResultType = exports.getDomainRecordAddress = exports.AuthorizedTokens = exports.AuthorizedProgramsType = exports.getSessionAccount = exports.reestablishSession = exports.revokeSession = exports.replaceSession = exports.establishSession = exports.createSessionContext = exports.TransactionResultType = exports.Network = exports.createSessionConnection = void 0;
7
7
  const anchor_1 = require("@coral-xyz/anchor");
8
8
  const sessions_idls_1 = require("@fogo/sessions-idls");
9
9
  const mpl_token_metadata_1 = require("@metaplex-foundation/mpl-token-metadata");
@@ -26,12 +26,13 @@ const zod_1 = require("zod");
26
26
  const connection_js_1 = require("./connection.js");
27
27
  const context_js_1 = require("./context.js");
28
28
  const crypto_js_1 = require("./crypto.js");
29
- var context_js_2 = require("./context.js");
30
- Object.defineProperty(exports, "createSessionContext", { enumerable: true, get: function () { return context_js_2.createSessionContext; } });
29
+ const instructions_js_1 = require("./instructions.js");
31
30
  var connection_js_2 = require("./connection.js");
31
+ Object.defineProperty(exports, "createSessionConnection", { enumerable: true, get: function () { return connection_js_2.createSessionConnection; } });
32
32
  Object.defineProperty(exports, "Network", { enumerable: true, get: function () { return connection_js_2.Network; } });
33
33
  Object.defineProperty(exports, "TransactionResultType", { enumerable: true, get: function () { return connection_js_2.TransactionResultType; } });
34
- Object.defineProperty(exports, "createSessionConnection", { enumerable: true, get: function () { return connection_js_2.createSessionConnection; } });
34
+ var context_js_2 = require("./context.js");
35
+ Object.defineProperty(exports, "createSessionContext", { enumerable: true, get: function () { return context_js_2.createSessionContext; } });
35
36
  const MESSAGE_HEADER = `Fogo Sessions:
36
37
  Signing this intent will allow this app to interact with your on-chain balances. Please make sure you trust this app and the domain in the message matches the domain of the current web application.
37
38
  `;
@@ -130,6 +131,11 @@ const createSession = async (context, walletPublicKey, sessionKey) => {
130
131
  walletPublicKey,
131
132
  sessionKey,
132
133
  payer: context.payer,
134
+ getSystemProgramSessionWrapInstruction: (amount) => (0, instructions_js_1.createSystemProgramSessionWrapInstruction)(sessionPublicKey, walletPublicKey, amount),
135
+ getSessionWrapInstructions: (amount) => (0, instructions_js_1.createSessionWrapInstructions)(sessionPublicKey, walletPublicKey, amount),
136
+ getSessionUnwrapInstructions: () => [
137
+ (0, instructions_js_1.createSessionUnwrapInstruction)(sessionPublicKey, walletPublicKey),
138
+ ],
133
139
  sendTransaction: (instructions, extraConfig) => context.sendTransaction(sessionKey, instructions, extraConfig),
134
140
  sessionInfo,
135
141
  };
@@ -354,7 +360,7 @@ const SymbolOrMint = {
354
360
  mint,
355
361
  }),
356
362
  };
357
- const getTokenInfo = async (context, limits) => {
363
+ const getTokenInfo = (context, limits) => {
358
364
  const umi = (0, umi_bundle_defaults_1.createUmi)(context.connection.rpcEndpoint);
359
365
  return Promise.all(limits.entries().map(async ([mint, amount]) => {
360
366
  const metaplexMint = (0, umi_1.publicKey)(mint.toBase58());
@@ -588,6 +594,41 @@ const buildTransferIntentInstruction = async (program, options, symbol, feeToken
588
594
  nonce: nonce === null ? "1" : nonce.nonce.add(new bn_js_1.default(1)).toString(),
589
595
  });
590
596
  };
597
+ const sendNativeTransfer = async (options) => {
598
+ const program = new sessions_idls_1.IntentTransferProgram(new anchor_1.AnchorProvider(options.context.connection, {}, {}));
599
+ return options.context.sendTransaction(undefined, [
600
+ await buildNativeTransferIntentInstruction(program, options, options.feeConfig.symbolOrMint, amountToString(options.feeConfig.fee, options.feeConfig.decimals)),
601
+ await program.methods
602
+ .sendNative()
603
+ .accounts({
604
+ feeMetadata: options.feeConfig.metadata,
605
+ feeMint: options.feeConfig.mint,
606
+ feeSource: (0, spl_token_1.getAssociatedTokenAddressSync)(options.feeConfig.mint, options.walletPublicKey),
607
+ source: options.walletPublicKey,
608
+ destination: options.recipient,
609
+ sponsor: options.context.internalPayer,
610
+ })
611
+ .instruction(),
612
+ ], {
613
+ variation: "Intent Transfer",
614
+ paymasterDomain: context_js_1.SESSIONS_INTERNAL_PAYMASTER_DOMAIN,
615
+ });
616
+ };
617
+ exports.sendNativeTransfer = sendNativeTransfer;
618
+ const FOGO_DECIMALS = 9;
619
+ const buildNativeTransferIntentInstruction = async (program, options, feeToken, feeAmount) => {
620
+ const nonce = await getNonce(program, options.walletPublicKey, NonceType.Transfer);
621
+ return buildIntentInstruction(options, TRANSFER_MESSAGE_HEADER, {
622
+ version: `${CURRENT_INTENT_TRANSFER_MAJOR}.${CURRENT_INTENT_TRANSFER_MINOR}`,
623
+ chain_id: options.context.chainId,
624
+ token: "FOGO",
625
+ amount: amountToString(options.amount, FOGO_DECIMALS),
626
+ recipient: options.recipient.toBase58(),
627
+ fee_token: feeToken,
628
+ fee_amount: feeAmount,
629
+ nonce: nonce === null ? "1" : nonce.nonce.add(new bn_js_1.default(1)).toString(),
630
+ });
631
+ };
591
632
  const BRIDGE_OUT_MESSAGE_HEADER = `Fogo Bridge Transfer:
592
633
  Signing this intent will bridge out the tokens as described below.
593
634
  `;
@@ -0,0 +1,18 @@
1
+ import { type PublicKey, TransactionInstruction } from "@solana/web3.js";
2
+ /**
3
+ * Creates the system program instruction `SessionWrap`, only available on Fogo, which allows a session key to transfer native token from its user's wallet to its user's wrapped token associated token account.
4
+ * This instruction may be combined with the `CreateAssociatedTokenAccountIdempotent` and `SyncNative` instructions for a session to wrap tokens on behalf of its user.
5
+ */
6
+ export declare function createSystemProgramSessionWrapInstruction(sessionKey: PublicKey, walletPublicKey: PublicKey, amount: bigint): TransactionInstruction;
7
+ /**
8
+ * Creates the sequence of instructions required to wrap native tokens within a session.
9
+ *
10
+ * Note: This function sets the session key as the payer for the `CreateAssociatedTokenAccountIdempotent` instruction, which is unconventional since the session key can't spend funds.
11
+ * It works because at the time `CreateAssociatedTokenAccountIdempotent` is called, the `userTokenAccount` has already been funded by the `SessionWrap` instruction.
12
+ * The paymaster will reject the transaction if the payer of the `CreateAssociatedTokenAccountIdempotent` is set to the paymaster payer to avoid the paymaster's funds getting drained.
13
+ */
14
+ export declare function createSessionWrapInstructions(sessionKey: PublicKey, walletPublicKey: PublicKey, amount: bigint): TransactionInstruction[];
15
+ /**
16
+ * Creates the instruction required to unwrap native tokens within a session.
17
+ */
18
+ export declare function createSessionUnwrapInstruction(sessionKey: PublicKey, walletPublicKey: PublicKey): TransactionInstruction;
@@ -0,0 +1,56 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createSystemProgramSessionWrapInstruction = createSystemProgramSessionWrapInstruction;
4
+ exports.createSessionWrapInstructions = createSessionWrapInstructions;
5
+ exports.createSessionUnwrapInstruction = createSessionUnwrapInstruction;
6
+ const spl_token_1 = require("@solana/spl-token");
7
+ const web3_js_1 = require("@solana/web3.js");
8
+ const SESSION_WRAP_DISCRIMINATOR = 4_000_000;
9
+ function getNativeMintAssociatedTokenAddressSync(walletPublicKey) {
10
+ return (0, spl_token_1.getAssociatedTokenAddressSync)(spl_token_1.NATIVE_MINT, walletPublicKey);
11
+ }
12
+ /**
13
+ * Creates the system program instruction `SessionWrap`, only available on Fogo, which allows a session key to transfer native token from its user's wallet to its user's wrapped token associated token account.
14
+ * This instruction may be combined with the `CreateAssociatedTokenAccountIdempotent` and `SyncNative` instructions for a session to wrap tokens on behalf of its user.
15
+ */
16
+ function createSystemProgramSessionWrapInstruction(sessionKey, walletPublicKey, amount) {
17
+ const data = new Uint8Array(12);
18
+ const view = new DataView(data.buffer);
19
+ view.setUint32(0, SESSION_WRAP_DISCRIMINATOR, true);
20
+ view.setBigUint64(4, amount, true);
21
+ return new web3_js_1.TransactionInstruction({
22
+ programId: web3_js_1.SystemProgram.programId,
23
+ keys: [
24
+ { pubkey: walletPublicKey, isSigner: false, isWritable: true },
25
+ {
26
+ pubkey: getNativeMintAssociatedTokenAddressSync(walletPublicKey),
27
+ isSigner: false,
28
+ isWritable: true,
29
+ },
30
+ { pubkey: sessionKey, isSigner: true, isWritable: false },
31
+ ],
32
+ data: Buffer.from(data),
33
+ });
34
+ }
35
+ /**
36
+ * Creates the sequence of instructions required to wrap native tokens within a session.
37
+ *
38
+ * Note: This function sets the session key as the payer for the `CreateAssociatedTokenAccountIdempotent` instruction, which is unconventional since the session key can't spend funds.
39
+ * It works because at the time `CreateAssociatedTokenAccountIdempotent` is called, the `userTokenAccount` has already been funded by the `SessionWrap` instruction.
40
+ * The paymaster will reject the transaction if the payer of the `CreateAssociatedTokenAccountIdempotent` is set to the paymaster payer to avoid the paymaster's funds getting drained.
41
+ */
42
+ function createSessionWrapInstructions(sessionKey, walletPublicKey, amount) {
43
+ const userTokenAccount = (0, spl_token_1.getAssociatedTokenAddressSync)(spl_token_1.NATIVE_MINT, walletPublicKey);
44
+ return [
45
+ createSystemProgramSessionWrapInstruction(sessionKey, walletPublicKey, amount),
46
+ (0, spl_token_1.createAssociatedTokenAccountIdempotentInstruction)(sessionKey, // This is unconventional! Read the note in the function's docs.
47
+ userTokenAccount, walletPublicKey, spl_token_1.NATIVE_MINT),
48
+ (0, spl_token_1.createSyncNativeInstruction)(userTokenAccount),
49
+ ];
50
+ }
51
+ /**
52
+ * Creates the instruction required to unwrap native tokens within a session.
53
+ */
54
+ function createSessionUnwrapInstruction(sessionKey, walletPublicKey) {
55
+ return (0, spl_token_1.createCloseAccountInstruction)(getNativeMintAssociatedTokenAddressSync(walletPublicKey), walletPublicKey, sessionKey);
56
+ }
@@ -1,6 +1,6 @@
1
- import type { Transaction, Instruction, TransactionWithLifetime, Rpc, GetLatestBlockhashApi } from "@solana/kit";
1
+ import type { GetLatestBlockhashApi, Instruction, Rpc, Transaction, TransactionWithLifetime } from "@solana/kit";
2
2
  import type { TransactionError } from "@solana/web3.js";
3
- import { Keypair, Connection as Web3Connection, TransactionInstruction, VersionedTransaction, PublicKey } from "@solana/web3.js";
3
+ import { Keypair, PublicKey, TransactionInstruction, VersionedTransaction, Connection as Web3Connection } from "@solana/web3.js";
4
4
  export declare enum Network {
5
5
  Testnet = 0,
6
6
  Mainnet = 1
package/esm/connection.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import { fromLegacyKeypair, fromLegacyPublicKey, fromLegacyTransactionInstruction, fromVersionedTransaction, } from "@solana/compat";
2
- import { createSolanaRpc, getBase64EncodedWireTransaction, createTransactionMessage, setTransactionMessageFeePayer, setTransactionMessageLifetimeUsingBlockhash, appendTransactionMessageInstructions, partiallySignTransactionMessageWithSigners, pipe, addSignersToTransactionMessage, compressTransactionMessageUsingAddressLookupTables, createSignerFromKeyPair, partiallySignTransaction, } from "@solana/kit";
3
- import { Keypair, Connection as Web3Connection, TransactionInstruction, VersionedTransaction, PublicKey, } from "@solana/web3.js";
2
+ import { addSignersToTransactionMessage, appendTransactionMessageInstructions, compressTransactionMessageUsingAddressLookupTables, createSignerFromKeyPair, createSolanaRpc, createTransactionMessage, getBase64EncodedWireTransaction, partiallySignTransaction, partiallySignTransactionMessageWithSigners, pipe, setTransactionMessageFeePayer, setTransactionMessageLifetimeUsingBlockhash, } from "@solana/kit";
3
+ import { Keypair, PublicKey, TransactionInstruction, VersionedTransaction, Connection as Web3Connection, } from "@solana/web3.js";
4
4
  import { z } from "zod";
5
5
  export var Network;
6
6
  (function (Network) {
package/esm/context.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import { AnchorProvider } from "@coral-xyz/anchor";
2
2
  import { ChainIdProgram } from "@fogo/sessions-idls";
3
- import { Connection as Web3Connection, Keypair } from "@solana/web3.js";
3
+ import { Keypair, Connection as Web3Connection } from "@solana/web3.js";
4
4
  // eslint-disable-next-line unicorn/no-typeof-undefined
5
5
  const IS_BROWSER = typeof globalThis.window !== "undefined";
6
6
  export const SESSIONS_INTERNAL_PAYMASTER_DOMAIN = "sessions";
package/esm/index.d.ts CHANGED
@@ -1,12 +1,12 @@
1
- import type { TransactionError, VersionedTransaction } from "@solana/web3.js";
1
+ import type { TransactionError, TransactionInstruction, VersionedTransaction } from "@solana/web3.js";
2
2
  import { Connection, PublicKey } from "@solana/web3.js";
3
3
  import type { Chain } from "@wormhole-foundation/sdk";
4
4
  import BN from "bn.js";
5
5
  import { z } from "zod";
6
6
  import type { TransactionOrInstructions, TransactionResult } from "./connection.js";
7
7
  import type { SendTransactionOptions, SessionContext } from "./context.js";
8
- export { type SessionContext, type SendTransactionOptions, createSessionContext, } from "./context.js";
9
- export { type TransactionResult, type Connection, type TransactionOrInstructions, Network, TransactionResultType, createSessionConnection, } from "./connection.js";
8
+ export { type Connection, createSessionConnection, Network, type TransactionOrInstructions, type TransactionResult, TransactionResultType, } from "./connection.js";
9
+ export { createSessionContext, type SendTransactionOptions, type SessionContext, } from "./context.js";
10
10
  type EstablishSessionOptions = {
11
11
  context: SessionContext;
12
12
  walletPublicKey: PublicKey;
@@ -2228,6 +2228,9 @@ export type Session = {
2228
2228
  sessionKey: CryptoKeyPair;
2229
2229
  walletPublicKey: PublicKey;
2230
2230
  payer: PublicKey;
2231
+ getSystemProgramSessionWrapInstruction: (amount: bigint) => TransactionInstruction;
2232
+ getSessionWrapInstructions: (amount: bigint) => TransactionInstruction[];
2233
+ getSessionUnwrapInstructions: () => TransactionInstruction[];
2231
2234
  sendTransaction: (instructions: TransactionOrInstructions, extraConfig?: SendTransactionOptions) => Promise<TransactionResult>;
2232
2235
  sessionInfo: NonNullable<z.infer<typeof sessionInfoSchema>>;
2233
2236
  };
@@ -2258,6 +2261,18 @@ type SendTransferOptions = {
2258
2261
  feeConfig: Awaited<ReturnType<typeof getTransferFee>>;
2259
2262
  };
2260
2263
  export declare const sendTransfer: (options: SendTransferOptions) => Promise<TransactionResult>;
2264
+ type SendNativeTransferOptions = {
2265
+ context: SessionContext;
2266
+ walletPublicKey: PublicKey;
2267
+ signMessage: (message: Uint8Array) => Promise<{
2268
+ signedMessage: Uint8Array;
2269
+ signature: Uint8Array;
2270
+ }>;
2271
+ amount: bigint;
2272
+ recipient: PublicKey;
2273
+ feeConfig: Awaited<ReturnType<typeof getTransferFee>>;
2274
+ };
2275
+ export declare const sendNativeTransfer: (options: SendNativeTransferOptions) => Promise<TransactionResult>;
2261
2276
  type SendBridgeOutOptions = {
2262
2277
  context: SessionContext;
2263
2278
  sessionKey: CryptoKeyPair;
package/esm/index.js CHANGED
@@ -8,7 +8,7 @@ import { fromLegacyPublicKey } from "@solana/compat";
8
8
  import { generateKeyPair, getAddressFromPublicKey, getProgramDerivedAddress, } from "@solana/kit";
9
9
  import { getAssociatedTokenAddressSync, getMint } from "@solana/spl-token";
10
10
  import { ComputeBudgetProgram, Connection, Ed25519Program, Keypair, PublicKey, } from "@solana/web3.js";
11
- import { Wormhole, wormhole, routes } from "@wormhole-foundation/sdk";
11
+ import { routes, Wormhole, wormhole } from "@wormhole-foundation/sdk";
12
12
  import solanaSdk from "@wormhole-foundation/sdk/solana";
13
13
  import { contracts } from "@wormhole-foundation/sdk-base";
14
14
  import { nttExecutorRoute } from "@wormhole-foundation/sdk-route-ntt";
@@ -20,8 +20,9 @@ import { z } from "zod";
20
20
  import { Network, TransactionResultType } from "./connection.js";
21
21
  import { SESSIONS_INTERNAL_PAYMASTER_DOMAIN } from "./context.js";
22
22
  import { importKey, signMessageWithKey, verifyMessageWithKey, } from "./crypto.js";
23
+ import { createSessionUnwrapInstruction, createSessionWrapInstructions, createSystemProgramSessionWrapInstruction, } from "./instructions.js";
24
+ export { createSessionConnection, Network, TransactionResultType, } from "./connection.js";
23
25
  export { createSessionContext, } from "./context.js";
24
- export { Network, TransactionResultType, createSessionConnection, } from "./connection.js";
25
26
  const MESSAGE_HEADER = `Fogo Sessions:
26
27
  Signing this intent will allow this app to interact with your on-chain balances. Please make sure you trust this app and the domain in the message matches the domain of the current web application.
27
28
  `;
@@ -115,6 +116,11 @@ const createSession = async (context, walletPublicKey, sessionKey) => {
115
116
  walletPublicKey,
116
117
  sessionKey,
117
118
  payer: context.payer,
119
+ getSystemProgramSessionWrapInstruction: (amount) => createSystemProgramSessionWrapInstruction(sessionPublicKey, walletPublicKey, amount),
120
+ getSessionWrapInstructions: (amount) => createSessionWrapInstructions(sessionPublicKey, walletPublicKey, amount),
121
+ getSessionUnwrapInstructions: () => [
122
+ createSessionUnwrapInstruction(sessionPublicKey, walletPublicKey),
123
+ ],
118
124
  sendTransaction: (instructions, extraConfig) => context.sendTransaction(sessionKey, instructions, extraConfig),
119
125
  sessionInfo,
120
126
  };
@@ -339,7 +345,7 @@ const SymbolOrMint = {
339
345
  mint,
340
346
  }),
341
347
  };
342
- const getTokenInfo = async (context, limits) => {
348
+ const getTokenInfo = (context, limits) => {
343
349
  const umi = createUmi(context.connection.rpcEndpoint);
344
350
  return Promise.all(limits.entries().map(async ([mint, amount]) => {
345
351
  const metaplexMint = metaplexPublicKey(mint.toBase58());
@@ -569,6 +575,40 @@ const buildTransferIntentInstruction = async (program, options, symbol, feeToken
569
575
  nonce: nonce === null ? "1" : nonce.nonce.add(new BN(1)).toString(),
570
576
  });
571
577
  };
578
+ export const sendNativeTransfer = async (options) => {
579
+ const program = new IntentTransferProgram(new AnchorProvider(options.context.connection, {}, {}));
580
+ return options.context.sendTransaction(undefined, [
581
+ await buildNativeTransferIntentInstruction(program, options, options.feeConfig.symbolOrMint, amountToString(options.feeConfig.fee, options.feeConfig.decimals)),
582
+ await program.methods
583
+ .sendNative()
584
+ .accounts({
585
+ feeMetadata: options.feeConfig.metadata,
586
+ feeMint: options.feeConfig.mint,
587
+ feeSource: getAssociatedTokenAddressSync(options.feeConfig.mint, options.walletPublicKey),
588
+ source: options.walletPublicKey,
589
+ destination: options.recipient,
590
+ sponsor: options.context.internalPayer,
591
+ })
592
+ .instruction(),
593
+ ], {
594
+ variation: "Intent Transfer",
595
+ paymasterDomain: SESSIONS_INTERNAL_PAYMASTER_DOMAIN,
596
+ });
597
+ };
598
+ const FOGO_DECIMALS = 9;
599
+ const buildNativeTransferIntentInstruction = async (program, options, feeToken, feeAmount) => {
600
+ const nonce = await getNonce(program, options.walletPublicKey, NonceType.Transfer);
601
+ return buildIntentInstruction(options, TRANSFER_MESSAGE_HEADER, {
602
+ version: `${CURRENT_INTENT_TRANSFER_MAJOR}.${CURRENT_INTENT_TRANSFER_MINOR}`,
603
+ chain_id: options.context.chainId,
604
+ token: "FOGO",
605
+ amount: amountToString(options.amount, FOGO_DECIMALS),
606
+ recipient: options.recipient.toBase58(),
607
+ fee_token: feeToken,
608
+ fee_amount: feeAmount,
609
+ nonce: nonce === null ? "1" : nonce.nonce.add(new BN(1)).toString(),
610
+ });
611
+ };
572
612
  const BRIDGE_OUT_MESSAGE_HEADER = `Fogo Bridge Transfer:
573
613
  Signing this intent will bridge out the tokens as described below.
574
614
  `;
@@ -0,0 +1,18 @@
1
+ import { type PublicKey, TransactionInstruction } from "@solana/web3.js";
2
+ /**
3
+ * Creates the system program instruction `SessionWrap`, only available on Fogo, which allows a session key to transfer native token from its user's wallet to its user's wrapped token associated token account.
4
+ * This instruction may be combined with the `CreateAssociatedTokenAccountIdempotent` and `SyncNative` instructions for a session to wrap tokens on behalf of its user.
5
+ */
6
+ export declare function createSystemProgramSessionWrapInstruction(sessionKey: PublicKey, walletPublicKey: PublicKey, amount: bigint): TransactionInstruction;
7
+ /**
8
+ * Creates the sequence of instructions required to wrap native tokens within a session.
9
+ *
10
+ * Note: This function sets the session key as the payer for the `CreateAssociatedTokenAccountIdempotent` instruction, which is unconventional since the session key can't spend funds.
11
+ * It works because at the time `CreateAssociatedTokenAccountIdempotent` is called, the `userTokenAccount` has already been funded by the `SessionWrap` instruction.
12
+ * The paymaster will reject the transaction if the payer of the `CreateAssociatedTokenAccountIdempotent` is set to the paymaster payer to avoid the paymaster's funds getting drained.
13
+ */
14
+ export declare function createSessionWrapInstructions(sessionKey: PublicKey, walletPublicKey: PublicKey, amount: bigint): TransactionInstruction[];
15
+ /**
16
+ * Creates the instruction required to unwrap native tokens within a session.
17
+ */
18
+ export declare function createSessionUnwrapInstruction(sessionKey: PublicKey, walletPublicKey: PublicKey): TransactionInstruction;
@@ -0,0 +1,51 @@
1
+ import { createAssociatedTokenAccountIdempotentInstruction, createCloseAccountInstruction, createSyncNativeInstruction, getAssociatedTokenAddressSync, NATIVE_MINT, } from "@solana/spl-token";
2
+ import { SystemProgram, TransactionInstruction, } from "@solana/web3.js";
3
+ const SESSION_WRAP_DISCRIMINATOR = 4_000_000;
4
+ function getNativeMintAssociatedTokenAddressSync(walletPublicKey) {
5
+ return getAssociatedTokenAddressSync(NATIVE_MINT, walletPublicKey);
6
+ }
7
+ /**
8
+ * Creates the system program instruction `SessionWrap`, only available on Fogo, which allows a session key to transfer native token from its user's wallet to its user's wrapped token associated token account.
9
+ * This instruction may be combined with the `CreateAssociatedTokenAccountIdempotent` and `SyncNative` instructions for a session to wrap tokens on behalf of its user.
10
+ */
11
+ export function createSystemProgramSessionWrapInstruction(sessionKey, walletPublicKey, amount) {
12
+ const data = new Uint8Array(12);
13
+ const view = new DataView(data.buffer);
14
+ view.setUint32(0, SESSION_WRAP_DISCRIMINATOR, true);
15
+ view.setBigUint64(4, amount, true);
16
+ return new TransactionInstruction({
17
+ programId: SystemProgram.programId,
18
+ keys: [
19
+ { pubkey: walletPublicKey, isSigner: false, isWritable: true },
20
+ {
21
+ pubkey: getNativeMintAssociatedTokenAddressSync(walletPublicKey),
22
+ isSigner: false,
23
+ isWritable: true,
24
+ },
25
+ { pubkey: sessionKey, isSigner: true, isWritable: false },
26
+ ],
27
+ data: Buffer.from(data),
28
+ });
29
+ }
30
+ /**
31
+ * Creates the sequence of instructions required to wrap native tokens within a session.
32
+ *
33
+ * Note: This function sets the session key as the payer for the `CreateAssociatedTokenAccountIdempotent` instruction, which is unconventional since the session key can't spend funds.
34
+ * It works because at the time `CreateAssociatedTokenAccountIdempotent` is called, the `userTokenAccount` has already been funded by the `SessionWrap` instruction.
35
+ * The paymaster will reject the transaction if the payer of the `CreateAssociatedTokenAccountIdempotent` is set to the paymaster payer to avoid the paymaster's funds getting drained.
36
+ */
37
+ export function createSessionWrapInstructions(sessionKey, walletPublicKey, amount) {
38
+ const userTokenAccount = getAssociatedTokenAddressSync(NATIVE_MINT, walletPublicKey);
39
+ return [
40
+ createSystemProgramSessionWrapInstruction(sessionKey, walletPublicKey, amount),
41
+ createAssociatedTokenAccountIdempotentInstruction(sessionKey, // This is unconventional! Read the note in the function's docs.
42
+ userTokenAccount, walletPublicKey, NATIVE_MINT),
43
+ createSyncNativeInstruction(userTokenAccount),
44
+ ];
45
+ }
46
+ /**
47
+ * Creates the instruction required to unwrap native tokens within a session.
48
+ */
49
+ export function createSessionUnwrapInstruction(sessionKey, walletPublicKey) {
50
+ return createCloseAccountInstruction(getNativeMintAssociatedTokenAddressSync(walletPublicKey), walletPublicKey, sessionKey);
51
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@fogo/sessions-sdk",
3
- "version": "0.0.29",
3
+ "version": "0.0.30",
4
4
  "description": "A set of utilities for integrating with Fogo sessions",
5
5
  "repository": {
6
6
  "type": "git",
@@ -17,7 +17,7 @@
17
17
  "main": "./cjs/index.js",
18
18
  "types": "./cjs/index.d.ts",
19
19
  "engines": {
20
- "node": ">=18"
20
+ "node": ">=22"
21
21
  },
22
22
  "exports": {
23
23
  ".": {
@@ -49,6 +49,6 @@
49
49
  "bn.js": "^5.1.2",
50
50
  "bs58": "^6.0.0",
51
51
  "zod": "3.25.67",
52
- "@fogo/sessions-idls": "^0.0.12"
52
+ "@fogo/sessions-idls": "^0.0.13"
53
53
  }
54
54
  }