HomeEIPs
EIPsERC-6982
ERC-6982

Efficient Default Lockable Tokens

A gas-efficient approach to lockable ERC-721 tokens
FinalStandards Track: ERC
Created: 2023-05-02
Requires: EIP-165, EIP-721
Francesco Sullo (@sullof), Alexe Spataru (@urataps)
DiscussionsOriginal linkEdit
1 min read

Video
Anyone may contribute to propose contents.
Go propose
Original

Abstract

This proposal introduces a lockable interface for ERC-721 tokens that optimizes gas usage by eliminating unnecessary events. This interface forms the foundation for the creation and management of lockable ERC-721 tokens. It provides a gas-efficient approach by emitting a DefaultLocked(bool locked) event upon deployment, setting the initial lock status for all tokens, while individual Locked(uint256 indexed tokenId, bool locked) events handle subsequent status changes for specific tokens. The interface also includes a view function locked(uint256 tokenId) to return the current lock status of a token, and a view function defaultLocked() to query the default status of a newly minted token.

Motivation

Existing lockable token proposals often mandate the emission of an event each time a token is minted. This results in unnecessary gas consumption, especially in cases where tokens are permanently locked from inception to destruction (e.g., soulbounds or non-transferable badges). This proposal offers a more gas-efficient solution that only emits events upon contract deployment and status changes of individual tokens.

Specification

The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in RFC 2119 and RFC 8174.

The interface is defined as follows:

// ERC165 interfaceId 0x6b61a747 interface IERC6982 { /** * @dev MUST be emitted when the contract is deployed to establish the default lock status * for all tokens. Also, MUST be emitted again if the default lock status changes, * to ensure the default status for all tokens (without a specific `Locked` event) is updated. */ event DefaultLocked(bool locked); /** * @dev MUST be emitted when the lock status of a specific token changes. * This status overrides the default lock status for that specific token. */ event Locked(uint256 indexed tokenId, bool locked); /** * @dev Returns the current default lock status for tokens. * The returned value MUST reflect the status indicated by the most recent `DefaultLocked` event. */ function defaultLocked() external view returns (bool); /** * @dev Returns the lock status of a specific token. * If no `Locked` event has been emitted for the token, it MUST return the current default lock status. * The function MUST revert if the token does not exist. */ function locked(uint256 tokenId) external view returns (bool); }

The ERC-165 interfaceId is 0x6b61a747.

Rationale

This standard seeks to optimize gas consumption by minimizing the frequency of event emission. The DefaultLocked event is designed to establish the lock status for all tokens, thereby circumventing the need to emit an event each time a new token is minted. It's crucial to note that the DefaultLocked event can be emitted at any point in time, and is not restricted to only before the Locked events are emitted.

Tokens may alter their behavior under certain circumstances (such as after a reveal), prompting the re-emission of the DefaultLocked event to reflect the new default status. The primary objective here is to economize on gas usage by avoiding the need to emit a Locked event for each token when the default status changes.

The Locked event is utilized to document changes in the lock status of individual tokens.

The defaultLocked function returns the prevailing default lock status of a token. This function is beneficial as it fosters interaction with other contracts and averts potential conflicts with ERC-5192, which is in its final stage.

The locked function gives the current lock status of a particular token, further facilitating interaction with other contracts. If no changes have been made to a specific token ID, this function should return the value provided by the defaultLocked function.

Bear in mind that a token being designated as "locked" doesn't necessarily imply that it is entirely non-transferable. There might be certain conditions under which a token can still be transferred despite its locked status. Primarily, the locked status relates to a token's transferability on marketplaces and external exchanges.

To illustrate, let's consider the Cruna protocol. In this system, an NFT owner has the ability to activate what is termed an 'protector'. This is essentially a secondary wallet with the unique privilege of initiating key transactions. Upon setting an initiator, the token's status is rendered 'locked'. However, this does not impede the token's transferability if the initiation for the transfer comes from the designated protector.

Backwards Compatibility

This standard is fully backwards compatible with existing ERC-721 contracts. It can be easily integrated into existing contracts and will not cause any conflicts or disruptions.

Reference Implementation

An example implementation is located in the assets directory.

It solves a specific use case: token's owners losing the ownership when staking the asset in a pool. The implementation allow the pool to lock the asset, leaving the ownership to the owner. In the README you can find more details about how to compile and test the contracts.

Security Considerations

This EIP does not introduce any known security considerations. However, as with any smart contract standard, it is crucial to employ rigorous security measures in the implementation of this interface.

Copyright and related rights waived via CC0.

Related EIPs
ERC-5192
ERC-5192
ERC-5192: Minimal Soulbound NFTs
Learn more
ERC-5633
ERC-5633
ERC-5633: Composable Soulbound NFT, EIP-1155 Extension
Learn more
ERC-5753
ERC-5753
ERC-5753: Lockable Extension for EIP-721
Learn more
Further reading
Anyone may contribute to propose contents.
Go propose
Adopted by projects
Anyone may contribute to propose contents.
Go propose

Not miss a beat of EIPs' update?

Subscribe EIPs Fun to receive the latest updates of EIPs Good for Buidlers to follow up.

View all
Serve EIP builders, scale Ethereum.
Resources
GitHub
Supported by