오프체인 IP(예: 책, 캐릭터, 그림 등)가 있다고 가정해 봅시다. Story에서 해당 IP를 등록하려면 먼저 NFT를 발행해야 합니다. 이 NFT는 IP에 대한 소유권 입니다. 그런 다음 등록 하여 Story에서 IP 자산 으로 만듭니다. 아래 튜토리얼에서 이 과정을 안내해 드리겠습니다.
사전 준비사항
튜토리얼을 시작하기 전에 완료해야 할 몇 가지 단계가 있습니다.
TypeScript SDK 설정TypeScript SDK 설정
[선택사항] Pinata 로 이동하여 새 API 키를 생성하세요. JWT를 .env
file:
PINATA_JWT=<YOUR_PINATA_JWT>
[선택사항] pinata-web3
dependency:
1. [선택사항] IP 메타데이터 설정
NFT와 IP에 메타데이터를 설정할 수 있지만, 필수는 아닙니다 . 이를 위해 IPA 메타데이터 표준 을 확인하고 NFT와 IP 모두에 대한 메타데이터를 구성하세요.
// you should already have a client set up (prerequisite)
import { client } from "./utils" ;
async function main () {
const ipMetadata = {
title: "Ippy" ,
description: "Official mascot of Story." ,
image:
"https://ipfs.io/ipfs/QmSamy4zqP91X42k6wS7kLJQVzuYJuW2EN94couPaq82A8" ,
imageHash:
"0x21937ba9d821cb0306c7f1a1a2cc5a257509f228ea6abccc9af1a67dd754af6e" ,
mediaUrl:
"https://ipfs.io/ipfs/QmSamy4zqP91X42k6wS7kLJQVzuYJuW2EN94couPaq82A8" ,
mediaHash:
"0x21937ba9d821cb0306c7f1a1a2cc5a257509f228ea6abccc9af1a67dd754af6e" ,
mediaType: "image/png" ,
creators: [
{
name: "Story Foundation" ,
address: "0x67ee74EE04A0E6d14Ca6C27428B27F3EFd5CD084" ,
description: "The World's IP Blockchain" ,
contributionPercent: 100 ,
socialMedia: [
{
platform: "Twitter" ,
url: "https://twitter.com/storyprotocol" ,
},
{
platform: "Website" ,
url: "https://story.foundation" ,
},
],
},
],
};
}
main ();
2. [선택사항] NFT 메타데이터 설정
NFT 메타데이터는 ERC-721 메타데이터 표준 을 따릅니다.
import { IpMetadata } from "@story-protocol/core-sdk" ;
import { client } from "./utils" ;
async function main () {
// previous code here ...
const nftMetadata = {
name: "Ownership NFT" ,
description: "This is an NFT representing owernship of our IP Asset." ,
image: "https://picsum.photos/200" ,
};
}
main ();
3. [선택사항] IP 및 NFT 메타데이터를 IPFS에 업로드
별도의 uploadToIpfs
파일에서 IP 및 NFT 메타데이터 객체를 IPFS에 업로드하는 함수를 만드세요:
import { PinataSDK } from "pinata-web3" ;
const pinata = new PinataSDK ({
pinataJwt: process . env . PINATA_JWT ,
});
export async function uploadJSONToIPFS ( jsonMetadata : any ): Promise < string > {
const { IpfsHash } = await pinata . upload . json ( jsonMetadata );
return IpfsHash ;
}
그런 다음 아래와 같이 해당 함수를 사용하여 메타데이터를 업로드할 수 있습니다:
import { IpMetadata } from "@story-protocol/core-sdk" ;
import { client } from "./utils" ;
import { uploadJSONToIPFS } from "./uploadToIpfs" ;
import { createHash } from "crypto" ;
async function main () {
// previous code here ...
const ipIpfsHash = await uploadJSONToIPFS ( ipMetadata );
const ipHash = createHash ( "sha256" )
. update ( JSON . stringify ( ipMetadata ))
. digest ( "hex" );
const nftIpfsHash = await uploadJSONToIPFS ( nftMetadata );
const nftHash = createHash ( "sha256" )
. update ( JSON . stringify ( nftMetadata ))
. digest ( "hex" );
}
main ();
4. NFT를 IP 자산으로 등록
새로운 IP를 등록하려면 먼저 IP의 기본 소유권을 나타내는 NFT를 발행해야 한다는 점을 기억하세요. 이 NFT는 그 후 “등록”되어 IP 자산 이 됩니다.
다행히도 mintAndRegisterIp
함수를 사용하여 NFT를 발행하고 동일한 트랜잭션에서 IP 자산으로 등록할 수 있습니다.
이 함수는 발행할 SPG NFT 계약이 필요합니다.
4a. 어떤 SPG NFT 계약 주소를 사용해야 하나요?
간단히 말해, Aeneid 테스트넷에서 여러분을 위해 만든 공개 컬렉션을 사용할 수 있습니다: 0xc32A8a0FF3beDDDa58393d022aF433e78739FAbc
. 메인넷에서, 또는 Aeneid에서 실제 시나리오를 테스트할 때도 자체 계약을 생성 해야 합니다. 이는 아래 “사용자 정의 ERC-721 계약 사용” 섹션에서 설명합니다.
우리가 제공하는 공개 컬렉션을 사용하는 것도 괜찮지만, 실제로 이를 수행할 때는 IP를 위한 자체 NFT 컬렉션을 만들어야 합니다. 이를 위한 두 가지 방법이 있습니다:
ISPGNFTISPGNFT 인터페이스를 구현하는 계약을 배포하거나 SDK의 createNFTCollection 함수(아래 참조)를 사용하여 이를 대신 수행할 수 있습니다. 이렇게 하면 오직 여러분만이 발행할 수 있는 자체 SPG NFT 컬렉션을 얻게 됩니다.
createSpgNftCollection.ts
import { zeroAddress } from "viem" ;
import { client } from "./utils" ;
async function createSpgNftCollection () {
const newCollection = await client . nftClient . createNFTCollection ({
name: "Test NFTs" ,
symbol: "TEST" ,
isPublicMinting: false ,
mintOpen: true ,
mintFeeRecipient: zeroAddress ,
contractURI: "" ,
txOptions: { waitForTransaction: true },
});
console . log ( "New collection created:" , {
"SPG NFT Contract Address" : newCollection . spgNftContract ,
"Transaction Hash" : newCollection . txHash ,
});
}
createSpgNftCollection ();
자체적으로 사용자 정의 ERC-721 NFT 컬렉션을 만들고 register 함수를 사용하세요 - nftContract
와 tokenId
를 제공하세요 - 대신 mintAndRegisterIp
함수를 사용하는 것입니다. 작동하는 코드 예제는 여기 에서 확인할 수 있습니다. 이는 이미 자체 로직이 있는 사용자 정의 NFT 계약이 있거나 IP 자체가 NFT인 경우에 유용합니다.
다음은 IP를 등록하는 코드입니다:
import { IpMetadata } from "@story-protocol/core-sdk" ;
import { client } from "./utils" ;
import { uploadJSONToIPFS } from "./uploadToIpfs" ;
import { createHash } from "crypto" ;
import { Address } from "viem" ;
async function main () {
// previous code here ...
const response = await client . ipAsset . mintAndRegisterIp ({
spgNftContract: "0xc32A8a0FF3beDDDa58393d022aF433e78739FAbc" ,
ipMetadata: {
ipMetadataURI: `https://ipfs.io/ipfs/ ${ ipIpfsHash } ` ,
ipMetadataHash: `0x ${ ipHash } ` ,
nftMetadataURI: `https://ipfs.io/ipfs/ ${ nftIpfsHash } ` ,
nftMetadataHash: `0x ${ nftHash } ` ,
},
txOptions: { waitForTransaction: true },
});
console . log (
`Root IPA created at transaction hash ${ response . txHash } , IPA ID: ${ response . ipId } `
);
console . log (
`View on the explorer: https://aeneid.explorer.story.foundation/ipa/ ${ response . ipId } `
);
}
main ();
5. 완성된 코드 보기
축하합니다, IP를 등록하셨습니다!
6. IP에 라이선스 조건 추가
이제 IP가 등록되었으니 라이선스 조건 을 생성하고 첨부할 수 있습니다. 이를 통해 다른 사람들이 라이선스를 발행하고 조건에 따라 제한된 방식으로 여러분의 IP를 사용할 수 있게 됩니다.
다음 섹션에서 이에 대해 다루겠지만, mintAndRegisterIp
function, you can register IP + create terms + attach terms all in the same step with the following functions: