初始化项目
mkdir new-nft && cd new-nft
pnpm init
pnpm add @metaplex-foundation/mpl-token-metadata @metaplex-foundation/umi-bundle-defaults @solana-developers/helpers @metaplex-foundation/umi @solana/web3.js esrun
npx esrun xx.ts
collection-nft.ts
import {
createNft,
fetchDigitalAsset,
mplTokenMetadata,
} from "@metaplex-foundation/mpl-token-metadata";
import {
airdropIfRequired,
getExplorerLink,
getKeypairFromFile,
} from "@solana-developers/helpers";
import { createUmi } from "@metaplex-foundation/umi-bundle-defaults";
import {
Connection,
LAMPORTS_PER_SOL,
clusterApiUrl,
} from "@solana/web3.js";
import {
generateSigner,
keypairIdentity,
percentAmount,
} from "@metaplex-foundation/umi";
const connection = new Connection(clusterApiUrl("devnet"));
const user = await getKeypairFromFile();
await airdropIfRequired(
connection,
user.publicKey,
1 * LAMPORTS_PER_SOL,
0.5 * LAMPORTS_PER_SOL
);
console.log("Loading user", user.publicKey.toBase58());
const umi = createUmi(connection.rpcEndpoint);
umi.use(mplTokenMetadata());
const umiUser = umi.eddsa.createKeypairFromSecretKey(user.secretKey);
umi.use(keypairIdentity(umiUser));
console.log("Set up Umi instance for user");
const collectionMint = generateSigner(umi);
const transaction = await createNft(umi, {
mint: collectionMint,
name: "NOAH NFT",
symbol: "NN",
uri: "https://raw.githubusercontent.com/NoahChen1994/picgo/refs/heads/main/nft-metadata.json",
sellerFeeBasisPoints: percentAmount(0),
isCollection: true,
});
await transaction.sendAndConfirm(umi);
const createdCollectionNft = await fetchDigitalAsset(
umi,
collectionMint.publicKey
);
console.log(
`✅ Created Collection 📦! Address: ${getExplorerLink(
"address",
createdCollectionNft.mint.publicKey,
"devnet"
)}`
);
创建集合类型的 NFT(Collection)
- 该脚本中的
createNft
方法用于创建一个 集合类型的 NFT。
isCollection: true
表示该 NFT 是一个 集合(collection),通常集合用于分组相关的 NFT。集合类型的 NFT 用于标识一个 NFT 项目的集合。
- 该脚本指定了
uri
(指向 metadata 文件)和 name
(集合的名称)。它会创建一个集合类型的 NFT,该 NFT 可以用于标识一组相关的 NFT 项目,通常作为 NFT 的根集合。
const transaction = await createNft(umi, {
mint: collectionMint,
name: "NOAH NFT",
symbol: "NN",
uri: "https://raw.githubusercontent.com/NoahChen1994/picgo/refs/heads/main/nft-metadata.json",
sellerFeeBasisPoints: percentAmount(0),
isCollection: true,
});
- 该脚本会生成一个新的 mint,用于创建集合类型的 NFT。
ordinary-nft.ts
import {
createNft,
fetchDigitalAsset,
mplTokenMetadata,
} from "@metaplex-foundation/mpl-token-metadata";
import {
airdropIfRequired,
getExplorerLink,
getKeypairFromFile,
} from "@solana-developers/helpers";
import { createUmi } from "@metaplex-foundation/umi-bundle-defaults";
import {
Connection,
LAMPORTS_PER_SOL,
clusterApiUrl,
} from "@solana/web3.js";
import {
generateSigner,
keypairIdentity,
percentAmount,
publicKey,
} from "@metaplex-foundation/umi";
const connection = new Connection(clusterApiUrl("devnet"));
const user = await getKeypairFromFile();
await airdropIfRequired(
connection,
user.publicKey,
1 * LAMPORTS_PER_SOL,
0.5 * LAMPORTS_PER_SOL
);
console.log("Loaded user ", user.publicKey);
const umi = createUmi(connection.rpcEndpoint);
umi.use(mplTokenMetadata());
const umiUser = umi.eddsa.createKeypairFromSecretKey(user.secretKey);
umi.use(keypairIdentity(umiUser));
console.log("Set Up umi user");
const noahAddress = publicKey("FrN56USkTMeHrfw2qjUWDCNri46Zq9aAjNSxG1t7V3C");
console.log("Nft creating! ");
const mint = generateSigner(umi);
const transaction = await createNft(umi, {
mint,
name: "MyNft",
uri: "https://raw.githubusercontent.com/NoahChen1994/picgo/refs/heads/main/nft-metadata.json",
sellerFeeBasisPoints: percentAmount(0),
collection: {
key: noahAddress,
verified: false,
},
});
const tx = await transaction.sendAndConfirm(umi);
console.log("Transaction successful:", tx);
console.log("Mint Address:", mint.publicKey);
const createdNft = await fetchDigitalAsset(umi, mint.publicKey);
console.log(
`🖼️ Created NFT! Address is ${getExplorerLink(
"address",
createdNft.mint.publicKey,
"devnet"
)}`
);
创建普通类型的 NFT
- 该脚本创建的 NFT 是普通的、非集合类型的。
collection
只是指向一个已存在的 collection 地址(noahAddress
),表示这枚 NFT 将属于一个已经存在的集合。
isCollection
没有被设置为 true
,表示这并不是一个集合,而是集合中的一枚普通 NFT。
const transaction = await createNft(umi, {
mint,
name: "MyNft",
uri: "https://raw.githubusercontent.com/NoahChen1994/picgo/refs/heads/main/nft-metadata.json",
sellerFeeBasisPoints: percentAmount(0),
collection: {
key: noahAddress,
verified: false,
},
});
- 该脚本创建的 NFT 属于已经存在的 noahAddress 集合,
collection.key
指定了 NFT 所属的集合地址。
- 这是一枚 普通的 NFT,它只是与一个集合关联,而不是创建一个新的集合。
verify.ts
import {
findMetadataPda,
mplTokenMetadata,
verifyCollectionV1,
} from "@metaplex-foundation/mpl-token-metadata";
import {
airdropIfRequired,
getExplorerLink,
getKeypairFromFile,
} from "@solana-developers/helpers";
import { createUmi } from "@metaplex-foundation/umi-bundle-defaults";
import { Connection, LAMPORTS_PER_SOL, clusterApiUrl } from "@solana/web3.js";
import { keypairIdentity, publicKey } from "@metaplex-foundation/umi";
const connection = new Connection(clusterApiUrl("devnet"));
const user = await getKeypairFromFile();
await airdropIfRequired(
connection,
user.publicKey,
1 * LAMPORTS_PER_SOL,
0.5 * LAMPORTS_PER_SOL
);
console.log("Loaded user", user.publicKey.toBase58());
const umi = createUmi(connection.rpcEndpoint);
umi.use(mplTokenMetadata());
const umiUser = umi.eddsa.createKeypairFromSecretKey(user.secretKey);
umi.use(keypairIdentity(umiUser));
console.log("Set up Umi instance for user");
const collectionAddress = publicKey(
"FrN56USkTMeHrfw2qjUWDCNri46Zq9aAjNSxG1t7V3C"
);
const nftAddress = publicKey("7mcqfSdkSDoTpJWQdsQ3nGBof92nvR9c5FsBy4fh1Ucb");
const transaction = await verifyCollectionV1(umi, {
metadata: findMetadataPda(umi, { mint: nftAddress }),
collectionMint: collectionAddress,
authority: umi.identity,
});
transaction.sendAndConfirm(umi);
console.log(
`✅ NFT ${nftAddress} verified as member of collection ${collectionAddress}! See Explorer at ${getExplorerLink(
"address",
nftAddress,
"devnet"
)}`
);
root@DESKTOP-OF7POL3:new-nft$ npx esrun verifiy.ts
bigint: Failed to load bindings, pure JS will be used (try npm run rebuild?)
Loaded user DPAGUq1r8pkVhHC2sEFAccPMvYqYcMHXMiLe2cJrRjGn
Set up Umi instance for user
✅ NFT 7mcqfSdkSDoTpJWQdsQ3nGBof92nvR9c5FsBy4fh1Ucb verified as member of collection FrN56USkTMeHrfw2qjUWDCNri46Zq9aAjNSxG1t7V3C! See Explorer at https://explorer.solana.com/address/7mcqfSdkSDoTpJWQdsQ3nGBof92nvR9c5FsBy4fh1Ucb?cluster=devnet
验证集合所属nft
const nftAddress = publicKey("7mcqfSdkSDoTpJWQdsQ3nGBof92nvR9c5FsBy4fh1Ucb");
const transaction = await verifyCollectionV1(umi, {
metadata: findMetadataPda(umi, { mint: nftAddress }),
collectionMint: collectionAddress,
authority: umi.identity,
});
- 根据
nftAddress
生成它的元数据地址(PDA)
- 指定目标集合地址
collectionMint
- 使用你自己的身份去执行验证(需要权限)