SDK
API 客户端
Last updated February 19, 2026
Genesis API 客户端提供了用于创建和注册代币发行的高级函数。它通过基于 Umi 构建的简洁接口,处理交易构建、签名和链上注册。
我们建议使用 SDK 以编程方式创建发行,因为 metaplex.com 尚未支持 Genesis 程序的全部功能。通过 API 创建的主网发行在注册后将显示在 metaplex.com 上。
安装
npm install @metaplex-foundation/genesis @metaplex-foundation/umi \
@metaplex-foundation/umi-bundle-defaults
设置
import { createUmi } from '@metaplex-foundation/umi-bundle-defaults';
import { genesis } from '@metaplex-foundation/genesis';
import { keypairIdentity } from '@metaplex-foundation/umi';
const umi = createUmi('https://api.mainnet-beta.solana.com')
.use(genesis());
// For server-side or scripts, load a keypair
umi.use(keypairIdentity(myKeypair));
三种集成模式
SDK 提供三种创建发行的模式,从全自动到完全手动。
简易模式 — createAndRegisterLaunch
最简单的方式。一次函数调用即可处理所有事项:创建链上账户、通过 Umi 签名并发送交易,以及注册发行。
1import {
2 createAndRegisterLaunch,
3 CreateLaunchInput,
4 genesis,
5} from '@metaplex-foundation/genesis'
6import { createUmi } from '@metaplex-foundation/umi-bundle-defaults'
7import { keypairIdentity } from '@metaplex-foundation/umi'
8
9const umi = createUmi('https://api.mainnet-beta.solana.com')
10 .use(genesis())
11
12// Use keypairIdentity to set a wallet when running server-side:
13// umi.use(keypairIdentity(myKeypair))
14
15const input: CreateLaunchInput = {
16 wallet: umi.identity.publicKey,
17 token: {
18 name: 'My Token',
19 symbol: 'MTK',
20 image: 'https://gateway.irys.xyz/...',
21 },
22 launchType: 'project',
23 launch: {
24 launchpool: {
25 tokenAllocation: 500_000_000,
26 depositStartTime: new Date(Date.now() + 48 * 60 * 60 * 1000),
27 raiseGoal: 200,
28 raydiumLiquidityBps: 5000,
29 fundsRecipient: umi.identity.publicKey,
30 },
31 },
32}
33
34const result = await createAndRegisterLaunch(umi, {}, input)
35console.log(`Launch live at: ${result.launch.link}`)
返回 CreateAndRegisterLaunchResult:
| 字段 | 类型 | 描述 |
|---|---|---|
signatures | Uint8Array[] | 交易签名 |
mintAddress | string | 创建的代币铸造地址 |
genesisAccount | string | Genesis 账户 PDA 地址 |
launch.id | string | 发行 ID |
launch.link | string | 发行页面 URL |
token.id | string | 代币 ID |
token.mintAddress | string | 代币铸造地址 |
中级模式 — 自定义交易发送器
使用 createAndRegisterLaunch 配合自定义 txSender 回调,适用于多签钱包或自定义重试逻辑等场景。
1import {
2 createAndRegisterLaunch,
3 SignAndSendOptions,
4} from '@metaplex-foundation/genesis'
5
6// Assumes umi and input from the Easy Mode example.
7
8const options: SignAndSendOptions = {
9 txSender: async (transactions) => {
10 // Replace myCustomSign / myCustomSend with your own
11 // signing and sending implementation.
12 const signatures: Uint8Array[] = []
13 for (const tx of transactions) {
14 const signed = await myCustomSign(tx) // your signer
15 const sig = await myCustomSend(signed) // your sender
16 signatures.push(sig)
17 }
18 return signatures
19 },
20}
21
22const result = await createAndRegisterLaunch(umi, {}, input, options)
23console.log(`Launch live at: ${result.launch.link}`)
txSender 回调接收未签名交易数组,必须返回签名数组。回调完成后 SDK 会处理注册。
完全控制 — createLaunch + registerLaunch
完全控制交易生命周期。调用 createLaunch 获取未签名交易,自行处理签名和发送,然后调用 registerLaunch。
1import {
2 createLaunch,
3 registerLaunch,
4} from '@metaplex-foundation/genesis'
5
6// Assumes umi and input from the Easy Mode example.
7
8// Step 1: Get unsigned transactions from the API
9const createResult = await createLaunch(umi, {}, input)
10
11// Step 2: Sign and send each transaction
12for (const tx of createResult.transactions) {
13 const signedTx = await umi.identity.signTransaction(tx)
14 const signature = await umi.rpc.sendTransaction(signedTx, {
15 commitment: 'confirmed',
16 preflightCommitment: 'confirmed',
17 })
18 await umi.rpc.confirmTransaction(signature, {
19 commitment: 'confirmed',
20 strategy: {
21 type: 'blockhash',
22 ...createResult.blockhash,
23 },
24 })
25}
26
27// Step 3: Register the launch
28const registerResult = await registerLaunch(umi, {}, {
29 genesisAccount: createResult.genesisAccount,
30 createLaunchInput: input,
31})
32console.log(`Launch live at: ${registerResult.launch.link}`)
createLaunch 返回 CreateLaunchResponse:
| 字段 | 类型 | 描述 |
|---|---|---|
transactions | Transaction[] | 需要签名并发送的未签名 Umi 交易 |
blockhash | BlockhashWithExpiryBlockHeight | 用于确认交易的区块哈希 |
mintAddress | string | 创建的代币铸造地址 |
genesisAccount | string | Genesis 账户 PDA 地址 |
registerLaunch 返回 RegisterLaunchResponse:
| 字段 | 类型 | 描述 |
|---|---|---|
existing | boolean? | 如果发行已注册则为 true |
launch.id | string | 发行 ID |
launch.link | string | 发行页面 URL |
token.id | string | 代币 ID |
token.mintAddress | string | 代币铸造地址 |
在调用 registerLaunch 之前,交易必须在链上确认。注册端点会验证 Genesis 账户是否存在以及是否与预期配置匹配。
配置
CreateLaunchInput
| 字段 | 类型 | 必填 | 描述 |
|---|---|---|---|
wallet | PublicKey | string | 是 | 创建者钱包(签署交易) |
token | TokenMetadata | 是 | 代币元数据 |
network | SvmNetwork | 否 | 'solana-mainnet'(默认)或 'solana-devnet' |
quoteMint | QuoteMintInput | 否 | 'SOL'(默认)、'USDC' 或原始铸造地址 |
launchType | LaunchType | 是 | 'project' |
launch | ProjectLaunchInput | 是 | 发行配置 |
TokenMetadata
| 字段 | 类型 | 必填 | 描述 |
|---|---|---|---|
name | string | 是 | 代币名称,1–32 个字符 |
symbol | string | 是 | 代币符号,1–10 个字符 |
image | string | 是 | 图片 URL(有效的 HTTPS URL) |
description | string | 否 | 最多 250 个字符 |
externalLinks | ExternalLinks | 否 | 网站、Twitter、Telegram 链接 |
ExternalLinks
| 字段 | 类型 | 描述 |
|---|---|---|
website | string? | 网站 URL |
twitter | string? | Twitter/X 用户名(@mytoken)或完整 URL |
telegram | string? | Telegram 用户名或完整 URL |
LaunchpoolConfig
| 字段 | 类型 | 描述 |
|---|---|---|
tokenAllocation | number | 销售代币数量(总供应量 10 亿中的一部分) |
depositStartTime | Date | string | 存款期开始时间(持续 48 小时) |
raiseGoal | number | 最低募集报价代币数量,以整数单位表示(例如 200 SOL) |
raydiumLiquidityBps | number | 用于 Raydium LP 的募集资金百分比,以基点表示(2000–10000) |
fundsRecipient | PublicKey | string | 接收解锁部分募集资金的地址 |
LockedAllocation(Streamflow 锁仓)
可通过 launch.lockedAllocations 添加可选的锁仓代币计划:
| 字段 | 类型 | 描述 |
|---|---|---|
name | string | 流名称,最多 64 个字符(例如 "Team"、"Advisors") |
recipient | PublicKey | string | 锁仓接收方钱包 |
tokenAmount | number | 锁仓计划中的代币总量 |
vestingStartTime | Date | string | 解锁计划开始时间 |
vestingDuration | { value: number, unit: TimeUnit } | 完整锁仓周期 |
unlockSchedule | TimeUnit | 代币释放频率 |
cliff | object? | 可选悬崖期,包含 duration 和 unlockAmount |
vestingStartTime 必须在存款期结束之后(即 depositStartTime + 48 小时之后)。API 将拒绝在存款窗口关闭之前开始的锁仓计划。
TimeUnit 值: 'SECOND'、'MINUTE'、'HOUR'、'DAY'、'WEEK'、'TWO_WEEKS'、'MONTH'、'QUARTER'、'YEAR'
带锁仓分配的示例:
1import {
2 createAndRegisterLaunch,
3 CreateLaunchInput,
4 genesis,
5} from '@metaplex-foundation/genesis'
6import { createUmi } from '@metaplex-foundation/umi-bundle-defaults'
7import { keypairIdentity } from '@metaplex-foundation/umi'
8
9const umi = createUmi('https://api.mainnet-beta.solana.com')
10 .use(genesis())
11
12// Use keypairIdentity to set a wallet when running server-side:
13// umi.use(keypairIdentity(myKeypair))
14
15const input: CreateLaunchInput = {
16 wallet: umi.identity.publicKey,
17 token: {
18 name: 'My Token',
19 symbol: 'MTK',
20 image: 'https://gateway.irys.xyz/...',
21 description: 'A project token with locked allocations.',
22 externalLinks: {
23 website: 'https://example.com',
24 twitter: '@mytoken',
25 },
26 },
27 launchType: 'project',
28 launch: {
29 launchpool: {
30 tokenAllocation: 500_000_000,
31 depositStartTime: new Date('2026-04-01T00:00:00Z'),
32 raiseGoal: 200,
33 raydiumLiquidityBps: 5000,
34 fundsRecipient: 'FundsRecipientWallet...',
35 },
36 lockedAllocations: [
37 {
38 name: 'Team',
39 recipient: 'TeamWallet...',
40 tokenAmount: 100_000_000,
41 vestingStartTime: new Date('2026-04-05T00:00:00Z'),
42 vestingDuration: { value: 1, unit: 'YEAR' },
43 unlockSchedule: 'MONTH',
44 cliff: {
45 duration: { value: 3, unit: 'MONTH' },
46 unlockAmount: 10_000_000,
47 },
48 },
49 ],
50 },
51}
52
53const result = await createAndRegisterLaunch(umi, {}, input)
54console.log(`Launch live at: ${result.launch.link}`)
SignAndSendOptions
createAndRegisterLaunch 的选项(扩展自 RpcSendTransactionOptions):
| 字段 | 类型 | 默认值 | 描述 |
|---|---|---|---|
txSender | (txs: Transaction[]) => Promise<Uint8Array[]> | — | 自定义交易发送器回调 |
commitment | string | 'confirmed' | 确认的承诺级别 |
preflightCommitment | string | 'confirmed' | 预检承诺级别 |
skipPreflight | boolean | false | 跳过预检检查 |
错误处理
SDK 提供三种错误类型及对应的类型守卫函数。
GenesisApiError
当 API 返回非成功响应时抛出。
import { isGenesisApiError } from '@metaplex-foundation/genesis';
try {
await createLaunch(umi, input);
} catch (err) {
if (isGenesisApiError(err)) {
console.error('API error:', err.statusCode, err.responseBody);
}
}
| 属性 | 类型 | 描述 |
|---|---|---|
statusCode | number | HTTP 状态码 |
responseBody | unknown | API 返回的完整响应体 |
GenesisApiNetworkError
当 fetch 调用失败时抛出(网络问题、DNS 故障等)。
import { isGenesisApiNetworkError } from '@metaplex-foundation/genesis';
if (isGenesisApiNetworkError(err)) {
console.error('Network error:', err.cause.message);
}
| 属性 | 类型 | 描述 |
|---|---|---|
cause | Error | 底层 fetch 错误 |
GenesisValidationError
当输入验证在发起 API 调用之前失败时抛出。
import { isGenesisValidationError } from '@metaplex-foundation/genesis';
if (isGenesisValidationError(err)) {
console.error(`Validation failed on field "${err.field}":`, err.message);
}
| 属性 | 类型 | 描述 |
|---|---|---|
field | string | 验证失败的输入字段 |
综合错误处理
1import {
2 createAndRegisterLaunch,
3 isGenesisApiError,
4 isGenesisApiNetworkError,
5 isGenesisValidationError,
6} from '@metaplex-foundation/genesis'
7
8// Assumes umi and input from the Easy Mode example.
9
10try {
11 const result = await createAndRegisterLaunch(umi, {}, input)
12 console.log(`Launch live at: ${result.launch.link}`)
13} catch (err) {
14 if (isGenesisValidationError(err)) {
15 console.error(`Invalid input "${err.field}":`, err.message)
16 } else if (isGenesisApiError(err)) {
17 console.error('API error:', err.statusCode, err.responseBody)
18 } else if (isGenesisApiNetworkError(err)) {
19 console.error('Network error:', err.cause.message)
20 } else {
21 throw err
22 }
23}
验证规则
SDK 在将输入发送到 API 之前会进行验证:
| 规则 | 约束条件 |
|---|---|
| 代币名称 | 1–32 个字符 |
| 代币符号 | 1–10 个字符 |
| 代币图片 | 有效的 HTTPS URL |
| 代币描述 | 最多 250 个字符 |
| 代币分配量 | 大于 0 |
| 募集目标 | 大于 0 |
| Raydium 流动性 BPS | 2000–10000(20%–100%) |
| 总供应量 | 固定为 10 亿枚代币 |
| 锁仓分配名称 | 最多 64 个字符 |
总供应量始终为 10 亿枚代币。SDK 会自动计算创建者分配额,即总供应量减去 Launch Pool、Raydium LP 和所有锁仓分配后的剩余部分。
辅助函数
signAndSendLaunchTransactions
如果您希望将默认的签名并发送行为作为独立函数使用(适用于重试或部分流程):
import {
createLaunch,
signAndSendLaunchTransactions,
} from '@metaplex-foundation/genesis';
const createResult = await createLaunch(umi, input);
const signatures = await signAndSendLaunchTransactions(umi, createResult, {
commitment: 'confirmed',
});
交易按顺序签名并发送——每笔交易在下一笔发送之前完成确认。
buildCreateLaunchPayload
验证输入并构建原始 API 载荷。为高级用例导出:
import { buildCreateLaunchPayload } from '@metaplex-foundation/genesis';
const payload = buildCreateLaunchPayload(input);
// Use payload with your own HTTP client
