It is not something that needs to be solved with an EIP that removes all ability to use the existing and properly standardized tokens. The ability to standardize the process without significant feature loss is possible.
I noticed that this EIP uses the same Transfer event as EIP-721, and uses the EIP721Metadata interface. I assume this is hoping to be compatible with existing NFT indexers out of the box.
However, this EIP states that the contract must not implement EIP-721, which means that the contract will not advertise EIP-712 compatibility through EIP-165.
This is going to be an issue for some indexers.
The origin of the issue is in the fact that indexing parameters in an event changes the way the event data is encoded but not the topic0 of the event. topic0 is to events what bytes4 function selectors are to functions. The consequence of that is that EIP-20’s Transfer and EIP-721’s Transfer have different data encoding but similar topic0.
So when you listen for Transfer event all over the blockchain, you’ll get EIP-20 and EIP-721 transfers at the same time.
export function fetchERC721(address: Address): ERC721Contract | null {
let erc721 = IERC721.bind(address)
// Try load entry
let contract = ERC721Contract.load(address)
if (contract != null) {
return contract
}
// Detect using ERC165
let detectionId = address.concat(Bytes.fromHexString('80ac58cd')) // Address + ERC721
let detectionAccount = Account.load(detectionId)
// On missing cache
if (detectionAccount == null) {
detectionAccount = new Account(detectionId)
let introspection_01ffc9a7 = supportsInterface(erc721, '01ffc9a7') // ERC165
let introspection_80ac58cd = supportsInterface(erc721, '80ac58cd') // ERC721
let introspection_00000000 = supportsInterface(erc721, '00000000', false)
let isERC721 = introspection_01ffc9a7 && introspection_80ac58cd && introspection_00000000
detectionAccount.asERC721 = isERC721 ? address : null
detectionAccount.save()
}
// If an ERC721, build entry
if (detectionAccount.asERC721) {
contract = new ERC721Contract(address)
let try_name = erc721.try_name()
let try_symbol = erc721.try_symbol()
contract.name = try_name.reverted ? '' : try_name.value
contract.symbol = try_symbol.reverted ? '' : try_symbol.value
contract.supportsMetadata = supportsInterface(erc721, '5b5e139f') // ERC721Metadata
contract.asAccount = address
contract.save()
let account = fetchAccount(address)
account.asERC721 = address
account.save()
}
return contract
}
This function will return null if the address is not an EIP-721 contract.
By not including that interfaceId, EIP-4973 contracts will be disregarded by this indexing systems (and probably others) which will assume its an EIP-20 contract.
Updates to the specification and reference implementation
Removed EIP-2098 support as EIP-1271 expects a “naively” concatenated signature and not an EIP-2098-style compact signature. This was pushed upstream with @frangio removing support for EIP-2098 in the SignatureChecker library.
For ERC4973 users, this is a big interface change. Please give us feedback.
I think the benefits are that it’ll streamline development. ERC4973 defines a generalization of signature-based allow lists. ERC5192 is about lockable NFTs. Composed, they create Soulbound tokens.
I like that this EIP is converging using signatures to prove the token acceptance from the 2 sides of the agreement. That something i’ve myself implemented to build the ticketing/credentials protocol Rouge.
But I feel that the EIP is trying to drive to much how this should be implemented and organized. Why not remove give and take from the specs and replace by having just a mandatory event Bound having 1 or two signatures (from issuer and receiver of the token) - of course also metadata & tokenId -. In case the event is emitted by an issuer’s tx, its signature is superfluous and can be null, and respectively if the event is emitted by a receiver tx, its signature can be null.
Wallet should only be able to tell if the token had approval from both sides to be bound, so only one event should be enough.
I also feel that unequip should be removed from the specs and replace by a symmetric event Unbound with the same double approval mechanism above.