Create an NFT Listing
Create an NFT Listing
14 Oct 2022
Contributed by Flow Blockchain
List an NFT to be sold using the NFTStorefront contract.
Smart Contract Example
When creating an NFT listing, you need to provide several key parameters to ensure the listing is properly set up and functions as intended. First, you must pass a capability that allows the storefront to withdraw the NFT when it is sold. This capability should be securely linked to your private storage path to prevent unauthorized access to your account's NFTs. Additionally, you need to specify the type of NFT being listed and its unique NFT ID. The listing also requires a payment vault type, which specifies the cryptocurrency or fungible token that will be used for the purchase.
A crucial part of the setup is defining the SaleCut structure, which determines how the payment is divided among recipients. For example, you might include a marketplace fee as one sale cut and allocate the remaining amount to the seller. Multiple sale cuts can be configured to accommodate complex payment arrangements. You will also need to provide the storefront ID where the listing will reside, as each account has a single storefront managing all its listings.
Once these parameters are provided, the listing is created and becomes part of your storefront. To make it accessible for potential buyers, link the listing's public capability to the ListingPublic interface, allowing others to call the purchase function and complete the transaction.
Transaction Example
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
import "FungibleToken"
import "NonFungibleToken"
import "ExampleNFT"
import "NFTStorefrontV2"
transaction {
let storefront: auth(NFTStorefrontV2.CreateListing) &NFTStorefrontV2.Storefront
prepare(acct: auth(Storage, Capabilities, NFTStorefrontV2.CreateListing) &Account) {
// Create and save the storefront
let storefront <- NFTStorefrontV2.createStorefront()
acct.storage.save(<-storefront, to: NFTStorefrontV2.StorefrontStoragePath)
// Publish the storefront capability to the public path
let storefrontCap = acct.capabilities.storage.issue<&{NFTStorefrontV2.StorefrontPublic}>(
NFTStorefrontV2.StorefrontStoragePath
)
acct.capabilities.publish(storefrontCap, at: NFTStorefrontV2.StorefrontPublicPath)
// Borrow the storefront reference using the public capability path
let storefrontRef = acct.capabilities.borrow<&{NFTStorefrontV2.StorefrontPublic}>(
NFTStorefrontV2.StorefrontPublicPath
) ?? panic("Could not borrow Storefront from provided address")
// Borrow the storefront reference directly from storage
self.storefront = acct.storage.borrow<auth(NFTStorefrontV2.CreateListing) &NFTStorefrontV2.Storefront>(
from: NFTStorefrontV2.StorefrontStoragePath
) ?? panic("Could not borrow Storefront with CreateListing authorization from storage")
// Borrow the NFTMinter from the caller's storage
let minter = acct.storage.borrow<&ExampleNFT.NFTMinter>(
from: /storage/exampleNFTMinter
) ?? panic("Could not borrow the NFT minter reference.")
// Mint a new NFT with metadata
let nft <- minter.mintNFT(
name: "Example NFT",
description: "Minting a sample NFT",
thumbnail: "https://example.com/thumbnail.png",
royalties: [],
metadata: {
"Power": "100",
"Will": "Strong",
"Determination": "Unyielding"
},
)
let nftID = nft.id
// Borrow the collection from the caller's storage
let collection = acct.storage.borrow<&ExampleNFT.Collection>(
from: /storage/exampleNFTCollection
) ?? panic("Could not borrow the NFT collection reference.")
// Deposit the newly minted NFT into the caller's collection
collection.deposit(token: <-nft)
let nftProviderCapability = acct.capabilities.storage.issue<auth(NonFungibleToken.Withdraw) &{NonFungibleToken.Collection}>(
/storage/exampleNFTCollection
)
// List the NFT
self.storefront.createListing(
nftProviderCapability: nftProviderCapability,
nftType: Type<@ExampleNFT.NFT>(),
nftID: nftID,
salePaymentVaultType: Type<@{FungibleToken.Vault}>(),
saleCuts: [
NFTStorefrontV2.SaleCut(
receiver: acct.capabilities.get<&{FungibleToken.Receiver}>(
/public/flowTokenReceiver
)!,
amount: 1.0
)
],
marketplacesCapability: nil,
customID: nil,
commissionAmount: 0.0,
expiry: UInt64(getCurrentBlock().timestamp + UFix64(60 * 60 * 24))
)
log("Listing created successfully")
}
}
First, we define the types that are expected to be returned for each of the variables used in the transaction. The process starts by borrowing the storefront resource from the account that contains it. This step ensures that the storefront has the necessary permissions to manage NFT listings. Next, we retrieve the capability to withdraw NFTs from the account, which allows the storefront to withdraw the specific NFT of the correct type when it is sold.
Next, we acquire the Vault receiver capability, which is crucial for setting up the SaleCut structure. This ensures that the specified vault will receive its designated portion of the proceeds from the NFT sale.
Once all these preparations are complete, we use the self.storefront reference to call the createListing function, passing in all the required parameters, including the NFT provider capability, NFT type, NFT ID, payment vault type, and the list of sale cuts. This step creates the listing on the storefront. Finally, the transaction is executed, and a log message confirms that the storefront listing was successfully created with its corresponding ID.
Up Next: Purchase NFT on Marketplace
67%