The Mission Impossible NFT

sukalpo mitra
6 min readOct 1, 2022

--

At the outset, let me apologize for the clickbait title. I could not think of any other.

Our company will take us to an annual retreat in Danang, Vietnam, in a few weeks. The team organizing the trip has given it a spy theme and has named the trip Mission Impossible.

One of the main reasons for this trip is that employees can mingle and foster a family feeling. This made even more sense after this Covid period when people were not allowed to meet.

To encourage this mingling, our Product Manager (oh yes! we build products in-house) came up with an idea! His idea is to create an app that will generate random names of five other employees. You find these persons as spies and scan a QR code in their respective apps to form connections. If you finish connecting with all five of them, then an NFT is minted and assigned to the employee. This NFT will be like an entry permit to the actual trip activities and can also have other traits like drink coupons. You can show the coupon to get free drinks etc. We liked the idea and decided to implement it.

We were a team of three. One person handled the UI coding, the other backend. I nominated myself to R&D on the ERC1155 specifications for minting an NFT.

The idea was we would pre-mint this NFT and will host them in OpenSea. After the event, we will pass the NFT to each employee who completed the mission!

It was now time to get serious.

My initial R&D told me I must host the asset and its metadata, which will become the NFT in IPFS. I chose Pinata as the IPFS provider. Once I signed up in Pinata, I uploaded the file, generating a CID (Content Identifier). The metadata is nothing but JSON. The structure of the JSON is documented in OpenSea documents.

It should be something like this:-

{
“description”: “Friendly OpenSea Creature”,
“external_url”: “https://openseacreatures.io/3",
“image”: “ipfs://someurl",
“name”: “Dave Starbelly”,
“attributes”: […]
}

So next, I uploaded the JSON file containing the metadata to IPFS.

Next, I needed to write the smart contract in solidity.

pragma solidity ^0.8.0; // This line specifies to the compiler what version of solidity to use// Importing OpenZeppelin pre-made contracts. OpenZeppelin Contracts helps you minimize risk.
// by using battle-tested libraries of smart contracts for Ethereum and other blockchains.
// It includes the most used implementations of ERC standards.
import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/token/ERC1155/ERC1155.sol";import "https://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/access/Ownable.sol";//This is the starting point of writing the contract, and it extends the Ownable and ERC1155 contracts that we imported from OpenZeppelincontract MINFT is ERC1155, Ownable {string public name;
string public symbol;
mapping(uint => string) public tokenURI;
constructor() ERC1155("") {
name = "MI NFT";
symbol = "MINFT";
}
//OnlyOwner is a guard to say that only the owner of the NFT can mint it.
//This is the mint function that takes the address to whom the NFT will be minted, token Id, and the amount of NFT we want to mint
function mint(address _to, uint _id, uint _amount) external onlyOwner {
_mint(_to, _id, _amount, "");
}
//This function helps to set the URI that hosts the metadata of the NFT.
function setURI(uint _id, string memory _uri) external onlyOwner {
tokenURI[_id] = _uri;
emit URI(_uri, _id);
}
}

And that’s it! That’s the bare minimum we need to mint the NFT.

I will now be using Remix IDE for deploying my smart contract. I created a new workspace and, under contracts, created a new solidity file and copied and pasted our code.

Once the code was there, I went to the solidity compiler tab in the Remix IDE and checked Auto compile, which triggered the compilation of our solidity code. I could see all the dependencies started to appear in the IDE.

The next thing that I wanted to do was to flatten our code. This helps in getting all the dependencies in one file. To do that, I went to the plugin manager of the IDE and searched for “flattener.” Once I found the plugin, I clicked on “Activate.”

Once I clicked on “Activate”, the IDE showed another button called “Flattener”, like below.

After I clicked on the “Flattener” button, the following two buttons came up -

I clicked on both buttons. “Flattener” now wanted permission to write the flattened contract to the file system.

Once I accepted the permission, I could see the flattened contract now in the file explorer section of the Remix IDE. The flattened file name comes as <original_file_name>_flat.sol.

Now we are all set for testing! For testing, I had to navigate to “Deploy & Run Transactions” in the Remix IDE. I chose the environment as “Injected Provider — Metamask” till I completed my testing. On my Metamask, I decided the network as Rinkeby Test Network. I also got some RinkebyETH from Rinkeby Faucet — https://rinkebyfaucet.com/.

Note:- By the time you read this blog, Rinkeby Test Network might be deprecated already due to the Ethereum merge. Your best bet, then, is to use Goerli Test Network.

After choosing my environment, I decided on my flattened contract from the contract dropdown. I ensured that the contract name was the one I gave in my contract code.

I clicked on deploy next and waited for the transaction to be successful.

Once the transaction was successful, I went to Etherscan. And then navigate to the contract address.

Once on the “contract” page, I went to the contract tab and clicked on “Verify and Publish.” This is an essential step as, without this, I wouldn’t have been able to interact with my contract directly at Etherscan. Once I clicked on the above link, I had to select the compiler type. I chose it as Solidity(single file) as I had flattened my solidity contract. As the compiler version, I decided on “0.8.7+commit.e28d00a7” as this was the version selected in the Remix IDE for compiling the contract.

On the next page, I kept the optimization to “No” as I had not selected the optimization in the compiler tab in Remix IDE. The “Enable Optimisation” checkbox is under Advanced Configurations. I copied the whole flattened code from Remix, then. Since I had not used any arguments in the constructor, I left the Constructor Arguments section empty.

Once I published, I could see the Write Contract tab when I returned to our Contract Address. Navigating to the “Write Contract” tab, I could see all the public methods I could execute on the contract.

Note:- If you have not chosen the correct contract to deploy in Remix, you will see the following when navigating to the “Write Contract” tab — Sorry, no public Write functions were found for this contract.

Almost there! Now we begin the mint. I clicked the “Connect to Web3” button to connect to my metamask and executed the mint function. The “to address” I gave was mine, token id, and the amount I set to 1. I then clicked on Write, which executed the mint operation.

Once I minted the NFT, it was time for me to set its metadata. This was done by executing the “setUri” function by passing “1” as the token id and the URI as “ipfs://<CID>/<metadata JSON filename>.json” from the pinata.cloud.

And now, when I go to “https://testnets.opensea.io/” and connect my account, I can see the NFT under my profile!

Sign up to discover human stories that deepen your understanding of the world.

Free

Distraction-free reading. No ads.

Organize your knowledge with lists and highlights.

Tell your story. Find your audience.

Membership

Read member-only stories

Support writers you read most

Earn money for your writing

Listen to audio narrations

Read offline with the Medium app

--

--

No responses yet

Write a response