TL;DR
We present a gas effective batch reveal method for NFT projects, where you don’t need to reveal the whole collection at once.
Randomizing NFTs
Most PFP NFT collections are randomly generated from multiple traits, each of which has its own rarity. Because of this each NFT in the collection is unique, but some are more rare than others.
To assure that this process is fair and not manipulated, the project’s team needs to guarantee that every mint has the same chance to get a rare NFT.
Different techniques were evolved to solve this issue. We will briefly cover some of the most common methods.
Generating random traits on-chain
The traits for each NFT are randomly picked on-chain during the minting. Then a script listens for minting events and generates the metadata and the image.
Pros:
- Can not be manipulated by the creators
- Instant reveal possible
Cons:
- High gas costs
- Can be manipulated by the miners
Randomizing in tokenURI()
In this technique randomization occurs in the tokenURI function, which is a view function. This fixes the security issues and the high gas during minting, but because the logic is now in the tokenURI function, it becomes very expensive to be called from another contract.
Pros:
- Can not be manipulated by the creators
- Low minting gas costs
- Instant reveal possible (depending on the implementation)
Cons:
- Breaks composability (it will be very expensive to call tokenURI from another contract)
Using random offset number and provenance record
In this method the images and metadata are generated off-chain and hashed. Then all hashes are concatenated and hashed again. These records can be used by anyone to verify that the input data and the order were not tempered.
Since the initial sequence is known by the project team, a random offset number is generated on-chain using Chainlink VRF.
This makes sure that nobody knows the order of the artworks before the reveal.
Each artwork is assigned to an NFT token id with the following formula:
InitialSequenceIndex = (tokenId + offsetNumber) % maxAmount
Pros:
- Can not be manipulated by the creators
- Low minting gas costs
- Doesn’t break composability
Cons:
- Reveal after the mint is over, which leads to limited mint time
Lunar Colony Alpha approach
We excluded the first two options, because we don’t want to increase the gas costs and break the contract composability.
The main drawback of the approach using a provenance record is that you have a limited amount of time for minting, because the reveal needs to be done after the minting is over. Usually the period before the reveal is about 1 week. If the minting continues after the reveal, bad actors will be able to snipe and mint the most rare NFTs from the collection.
Batch reveals
If we could reveal in batches this would fix the issue, because we are revealing only the minted items.
Doing this is actually not so hard. We can extend the original approach using a very simple technique. We can treat every reveal as a different independent unit.
Divide and conquer
We roll a new random offset number for each batch and shift the order with it, but only in the range of the batch to prevent overlapping between the items.
To do this we need to modify the calculation to include information about each batch and return a correct InitialSequenceIndex.
So the original formula
InitialSequenceIndex = (tokenId + offsetNumber) % maxAmount
becomes
InitialSequenceIndex = (tokenId - batchStartIndex + batchOffsetNumber) % batchSize + batchStartIndex
Voila !
Now we need to provide the information needed to proof that the data and the sequence are not tempered.
In our case we need — Initial sequence index, token id, batch offset(with proof for randomness), artwork hash, provenance hash and the artwork(after reveal).
Now anybody can rerun the same algorithm used for generation of the provenance data and check if the output is correct.
Further thoughts
- Batch revealing gives the team more flexibility. Because there is no need to limit the amount of the collection or over hype the project with promoters, the community can be built more organically.
- Additional benefits can be provided to the early minters. In LCA we added a numeric trait called ”generation” that is incrementing with each batch reveal. This trait can be used later as a discord role, staking multiplier, p2e skills multiplier, etc.
- We are still early. All of these techniques are not standardized. There is no common tooling for the builders and the community.
Can devs do something? — Yes, we can :)
Additional Resources:
https://lca.m00n.city/provenance/
https://boredapeyachtclub.com/#/provenance
https://astrofrens.com/provenance
https://github.com/tubby-cats/batch-nft-reveal/blob/master/randomness.md
I would like to pay my special regards to the people who contributed indirectly by sharing their code and spreading knowledge, especially
0xngmi, nftchance, squeebo_nft, 0xInuarashi, woof, Tim Clancy
Lunar Colony Alpha is a generative artwork collection of 10,000 hand drawn Alphabot NFT’s dwelling in the digital realm. All secured by the Ethereum blockchain and dedicated to a cosmic mission. Their aim — to lay the foundations of a digital meta-city.
M00N City is an experiment to build a digital meta-city where:
- Your identity will be your avatar — PFP NFT
- Participation in the ecosystem will be driven by internal economics
- Gamification will be used for fun and profit (like elections for a municipal council)
- Community will rule
- Every citizen will have incentive to participate
- Success of the project means success for everyone
The core goal of the M00N City will be to build economy for decentralized apps development by selecting and funding them using a tokenized model called curation markets.
If you want to build together ping me on twitter,
0xMoonwalker