In this section, we will introduce the abstract
and interface
contracts in Solidity, using the interface of ERC721
as an example. They are used to write contract templates and reduce code redundancy.
Abstract contract
If a contract contains at least one unimplemented function (no contents in the function body {}
), it must be labelled as abstract
; Otherwise it will not compile. Moreover, the unimplemented function needs to be labelled as virtual
.
Take our previous Insertion Sort Contract as an example,
if we haven't figured out how to implement the insertion sort function, we can mark the contract as abstract
, and let others overwrite it in the future.
Interface
The interface
contract is similar to the abstract
contract, but it requires no functions to be implemented. Rules of the interface:
- Cannot contain state variables.
- Cannot contain constructors.
- Cannot inherit non-interface contracts.
- All functions must be external and cannot have contents in the function body.
- The contract that inherits the interface contract must implement all the functions defined in it.
Although the interface does not implement any functionality, it is the skeleton of smart contracts. The interface
defines what the contract does and how to interact with it: if a smart contract implements an interface (like ERC20
or ERC721
),
other Dapps and smart contracts will know how to interact with it. Because it provides two important pieces of information:
- The
bytes4
selector for each function in the contract, and the function signaturesfunction name (parameter type)
. - Interface id (see EIP165 for more information)
In addition, the interface is equivalent to the contract ABI
(Application Binary Interface),
and they can be converted to each other: compiling the interface contract will give you the contract ABI
,
and abi-to-sol tool will convert the ABI
back to the interface contract.
We take the IERC721
contract, the interface for the ERC721
token standard, as an example. It consists of 3 events and 9 functions,
which all ERC721
contracts need to implement. In the interface, each function ends with ;
instead of the function body { }
. Moreover, every function in the interface contract is by default virtual
, so you do not need to label the function as virtual
explicitly.
IERC721 Event
IERC721
contains 3 events.
Transfer
event: emitted during transfer, records the sending addressfrom
, the receiving addressto
, andtokenId
.Approval
event: emitted during approval, records the token owner addressowner
, the approved addressapproved
, andtokenId
.ApprovalForAll
event: emitted during batch approval, records the owner addressowner
of batch approval, the approved addressoperator
, and whether the approve is enabled or disabledapproved
.
IERC721 Function
IERC721
contains 3 events.
balanceOf
: Count all NFTs held by an owner.ownerOf
: Find the owner of an NFT (tokenId
).transferFrom
: Transfer ownership of an NFT withtokenId
fromfrom
toto
.safeTransferFrom
: Transfer ownership of an NFT withtokenId
fromfrom
toto
. Extra check: if the receiver is a contract address, it will be required to implement theERC721Receiver
interface.approve
: Enable or disable another address to manage your NFT.getApproved
: Get the approved address for a single NFT.setApprovalForAll
: Enable or disable approval for a third party to manage all your NFTs in this contract.isApprovedForAll
: Query if an address is an authorized operator for another address.safeTransferFrom
: Overloaded function for safe transfer, containingdata
in its parameters.
When to use an interface?
If we know that a contract implements the IERC721
interface, we can interact with it without knowing its detailed implementation.
The Bored Ape Yacht Club BAYC
is an ERC721
NFT, which implements all functions in the IERC721
interface. We can interact with the BAYC
contract with the IERC721
interface and its contract address, without knowing its source code.
For example, we can use balanceOf()
to query the BAYC
balance of an address or use safeTransferFrom()
to transfer a BAYC
NFT.
Remix demo
- Abstract example:
- Interface example:
Summary
In this chapter, we introduced the abstract
and interface
contracts in Solidity, which are used to write contract templates and reduce code redundancy.
We also learned the interface of the ERC721
token standard and how to interact with the BAYC
contract using the interface.