Skip to main content
Improve formatting, wording, punctuation, spelling, etc.
Source Link

The supportsInterfacesupportsInterface shouldn't be used to check individual functions, each. Each interface should have a single interfaceID, which, as you can see in the ERC-721 implementation you posted, is constructed as follows:

But itsit's important to note that when you call supportsInterface on 0x01ffc9a7, you are testing to see if your contract supports the whole ERC165 standard. It just so happens that that there is only one function.

So you shouldn't be calling supportsInterface on 0x8462151c, this would checking be checking for an interface which only contained the function tokensOfOwner().

In steadInstead, you should be checking against the InterfaceIDinterfaceID of the whole ERC721 interface. If your contract supports the whole interface, then by definition it will support any of the functions contained therein.

The idea is that anyone can find the specification for the interface, and just check the interfaceIdinterfaceID of that interface against your contract.

Why thisThis is relevant to what you posted is because basic ERC721 does not implement any of the following:

If standards are developing and evolving over time, then ERC721 version 0.0.1 (a number I just made up) may have an interfaceIdinterfaceID of 0x9f40b779 (which is the value of InterfaceID_ERC721 in the contract you provided). However, version 0.0.2 may add, change, or remove a function, which would completely change the interfaceID to something else. So as long as you specify that your contract complies to ERC721 0.0.1, someone else can look up the interface, and check it against your contract.

So the very short answer to your question is, you shouldn't be checking supportsInterfacesupportsInterface against a single function, but rather against the whole interface.

The supportsInterface shouldn't be used to check individual functions, each interface should have a single interfaceID, which as you see in the ERC-721 implementation you posted, is constructed as follows

But its important to note that when you call supportsInterface on 0x01ffc9a7 you are testing to see if your contract supports the whole ERC165 standard. It just so happens that that is only one function.

So you shouldn't be calling supportsInterface on 0x8462151c, this would checking be for an interface which only contained the function tokensOfOwner().

In stead you should be checking against the InterfaceID of the whole ERC721 interface. If your contract supports the whole interface, then by definition it will support any of the functions contained therein.

The idea is that anyone can find the specification for the interface, and just check the interfaceId of that interface against your contract.

Why this is relevant to what you posted is because basic ERC721 does not implement any of the following:

If standards are developing and evolving over time, then ERC721 version 0.0.1 (a number I just made up) may have an interfaceId of 0x9f40b779 (which is the value of InterfaceID_ERC721 in the contract you provided). However version 0.0.2 may add, change or remove a function, which would completely change the interfaceID to something else. So as long as you specify that your contract complies to ERC721 0.0.1, someone else can look up the interface, and check it against your contract.

So the very short answer to your question is, you shouldn't be checking supportsInterface against a single function, but rather against the whole interface.

supportsInterface shouldn't be used to check individual functions. Each interface should have a single interfaceID which, as you can see in the ERC-721 implementation you posted, is constructed as follows:

But it's important to note that when you call supportsInterface on 0x01ffc9a7, you are testing to see if your contract supports the whole ERC165 standard. It just so happens that there is only one function.

So you shouldn't be calling supportsInterface on 0x8462151c, this would be checking for an interface which only contained the function tokensOfOwner().

Instead, you should be checking against the interfaceID of the whole ERC721 interface. If your contract supports the whole interface, then by definition it will support any of the functions contained therein.

The idea is that anyone can find the specification for the interface, and just check the interfaceID of that interface against your contract.

This is relevant to what you posted because basic ERC721 does not implement any of the following:

If standards are developing and evolving over time, then ERC721 version 0.0.1 (a number I just made up) may have an interfaceID of 0x9f40b779 (which is the value of InterfaceID_ERC721 in the contract you provided). However, version 0.0.2 may add, change, or remove a function, which would completely change the interfaceID to something else. So as long as you specify that your contract complies to ERC721 0.0.1, someone else can look up the interface, and check it against your contract.

So the very short answer to your question is, you shouldn't be checking supportsInterface against a single function, but rather against the whole interface.

Source Link

The supportsInterface shouldn't be used to check individual functions, each interface should have a single interfaceID, which as you see in the ERC-721 implementation you posted, is constructed as follows

bytes4 constant InterfaceID_someInterface =
    bytes4(keccak256('function1(address)')) ^
    bytes4(keccak256('function2(uint,etc)')) ^
    ...
    bytes4(keccak256('functionN()'));

In the case of the ERC165 interface, there is only one function in that interface, supportsInterface, so the interfaceID is just

bytes4 constant InterfaceID_ERC165 =
    bytes4(keccak256('supportsInterface(bytes4)'));
//0x01ffc9a7

But its important to note that when you call supportsInterface on 0x01ffc9a7 you are testing to see if your contract supports the whole ERC165 standard. It just so happens that that is only one function.

So you shouldn't be calling supportsInterface on 0x8462151c, this would checking be for an interface which only contained the function tokensOfOwner().

In stead you should be checking against the InterfaceID of the whole ERC721 interface. If your contract supports the whole interface, then by definition it will support any of the functions contained therein.

The idea is that anyone can find the specification for the interface, and just check the interfaceId of that interface against your contract.

BUT, there are two problems with the implementation posted. First of all, they didn't provide the ERC721 or 165 interfaces. They just provided an abstract contract which contains a few related functions. So they didn't really give the thing you should be checking against.

Also, I don't think this implementation is an up-to-date or proper implementation of ERC721. The standard is still a work in progress, but you can see the non-finalised standard here.

There are actually interfaces for 3 standards here:

ERC721 (0x80ac58cd)

ERC721Metadata (0x5b5e139f) (optional)

ERC721Enumerable (0x780e9d63) (optional)

ERC721 just implements the basic requirements of a NFT, ERC721Metadata adds name, symbol and URI data functionality, and ERC721Enumerable adds some other functionality to do with token indexes.

Why this is relevant to what you posted is because basic ERC721 does not implement any of the following:

name() (this is from ERC721Metadata)

symbol() (this is from ERC721Metadata)

totalSupply() (this is from ERC721Enumerable)

transfer(address,uint256) (this is from ERC20 spec, 721 uses transferFrom and safeTransferFrom)

tokensOfOwner(address) (not part of the standards).

There are also some functions in the standard which you will see aren't implemented in the one you provided. It's likely that it was written when the standard was at a much earlier age. And indeed, this sort of situation is partially the purpose of the ERC165 specification.

If standards are developing and evolving over time, then ERC721 version 0.0.1 (a number I just made up) may have an interfaceId of 0x9f40b779 (which is the value of InterfaceID_ERC721 in the contract you provided). However version 0.0.2 may add, change or remove a function, which would completely change the interfaceID to something else. So as long as you specify that your contract complies to ERC721 0.0.1, someone else can look up the interface, and check it against your contract.

So the very short answer to your question is, you shouldn't be checking supportsInterface against a single function, but rather against the whole interface.

But I also don't think you should be using the contract you provided because it seems out of date, and the whole purpose of standards is to be compliant.