Secret Network: Create an NFT on Secret Network with Data Stored on IPFS

Learn how to create a Secret Network NFT with assets stored on IPFS.

What is Secret Network?

Secret Network is a decentralized network built on top of the Cosmos SDK that enables private computation and confidential smart contracts. Secret Network allows developers to create applications with privacy-preserving features such as encrypted data storage, private transactions, and private smart contract execution. This opens up a range of use cases, including financial services, supply chain management, healthcare, and more, where privacy and security are paramount.

Read below to learn how to create a Secret Network NFT with assets stored on IPFS.


1. We’ll start by uploading an image to Filebase for us to use as an NFT.

To do this, navigate to If you don’t have an account already, sign up, then log in.

2. Select ‘Buckets’ from the left side bar menu, or navigate to

Select ‘Create Bucket’ in the top right corner to create a new bucket for your NFTs.

3. Enter a bucket name and choose the IPFS storage network to create the bucket.

Bucket names must be unique across all Filebase users, be between 3 and 63 characters long, and can contain only lowercase characters, numbers, and dashes.

4. Next, select the bucket from your list of buckets, then select ‘Upload’ in the top right corner to upload your image file.

5. Select your image to be uploaded.

Once uploaded, it will be listed in the bucket.

6. You can view the object’s IPFS CID in the CID column, or you can click on your uploaded object to display the metadata for the object, which includes the IPFS CID.

Choose the method you prefer, and take note of the IPFS CID for your image. We will reference this later.

7. For this tutorial, we’ll be using a private metadata.json file and a public metadata.json file. An example of each can be found below:

Private Metadata:

"description" : "Filebase NFT.",
"image" : "",
"name" : "Filebase Robot"

Public Metadata:

"attributes" : [ {
"trait_type" : "Type",
"value" : "Robot"
}, {
"trait_type" : "Eye color",
"value" : "Blue"
} ],
"description" : "Filebase NFT.",
"image" : "",
"name" : "Filebase Robot"

Replace FILEBASE_IPFS_CID with the Filebase IPFS CID you took note of previously. Then save both of these as private-metadata.json and public-metadata.json respectively. Upload these files to Filebase in the same manner you used to upload the image file, then take note of each of their unique CID values.

8. Next, clone the following Github repository:

git clone

9. Then, start a Docker container to run a local testnet network:

cd secret-contracts-guide

docker run -it --rm \\

-p 26657:26657 -p 26656:26656 -p 1317:1317 \\

--name secretdev enigmampc/secret-network-sw-dev:v1.0.2

10. Next, open a new terminal and navigate into the running Docker container to obtain the secret key pair for using the Secret Network node running in that Docker container:

docker exec -it secretdev /bin/bash

secretcli keys list --keyring-backend test

11. Next, download and install Rust, then set up the wasm32 Rust package:

curl --proto '=https' --tlsv1.2 -sSf | sh

source $HOME/.cargo/env

rustup default stable

rustup target list --installed

rustup target add wasm32-unknown-unknown

rustup install nightly

rustup target add wasm32-unknown-unknown --toolchain nightly

12. Then, generate a smart contract project with the command:

cargo generate --git --name nft-ipfs

13. Next, open the src folder, then open the file. Replace the existing contents with the following src folder:

git clone

mv snip721-reference-imp/src nft-ipfs/src

14. Then compile the smart contract with the command:

cd nft-ipfs

cargo wasm

15. To mint an NFT, open the schema folder, then replace the execute_msg.json file’s existing content with the following:

	"mint_nft": {
		"token_id": "optional_ID_of_new_token",
		"owner": "optional_address_the_new_token_will_be_minted_to",
		"public_metadata": {
			"token_uri": "",
			"extension": {
				"...": "..."
		"private_metadata": {
			"token_uri": "",
			"extension": {
				"...": "..."
		"serial_number": {
			"mint_run": 3,
			"serial_number": 67,
			"quantity_minted_this_run": 1000,
		"royalty_info": {
			"decimal_places_in_rates": 4,
			"royalties": [
					"recipient": "address_that_should_be_paid_this_royalty",
					"rate": 100,
					"...": "..."
		"transferable": true | false,
		"memo": "optional_memo_for_the_mint_tx",
		"padding": "optional_ignored_string_that_can_be_used_to_maintain_constant_message_length"

Replace the following values to match your configuration:

  • Token_id: Optional unique ID for the token.

  • Owner: Your wallet address.

  • Public Metadata -> token_URI: Your Filebase IPFS link to the public metadata file.

  • Private Metadata -> token_URI: Your Filebase IPFS link to the private metadata file.

  • Royalties -> Recipient: Wallet address that will receive crypto royalties from this token.

This smart contract uses the SNIP-721 standard, which mints a single token and can only be used by an authorized minting address.

16. Then, deploy the smart contract to the testnet with the command:

docker run --rm -v "$(pwd)":/contract \\

--mount type=volume,source="$(basename "$(pwd)")_cache",target=/code/target \\

--mount type=volume,source=registry_cache,target=/usr/local/cargo/registry \\


If you have any questions, please join our Discord server, or send us an email at

Last updated