ERC 223 Token Standard
ERC223 is a superset of the ERC20 standard allowing the use of tokens as first-class value transfer assets.
Article published on Callisto Blog on 29th September 2021.

EIP 223

You can read the original discussion and formal description here.

Current Implementation

Main ERC223 contracts:
  • IERC223.sol: Token interface. The minimal common API ERC223. Tokens and receivers must implement in order to interact with each other.
  • ERC223.sol: Token contract. Defines the logic of the basic ERC223 token. This functionality can be extended with additional functions (such as burn(), mint(), ownership or approve / transferFrom pattern of ERC20).
  • Recipient interface: A dummy receiver that is intended to accept ERC223 tokens. Use contract MyContract is IERC223Recipient to make a contract capable of accepting ERC223 token transactions. A contract that does not support IERC223Recipient interface can receive tokens if this contract implements a permissive fallback function (this method of token receiving is not recommended). If a contract does not implement IERC223Recipient tokenReceived function and does not implement a permissive fallback function then this contract can not receive ERC223 tokens.

Extensions of the Base Functionality

  • ERC223Mintable.sol: Minting functionality for ERC223 tokens. Use contract MyToken is ERC223Mintable to make your token mintable. The address used to deploy this contract will receive Minter functionality and will be allowed to assign new minters and increase the token totalSupply.
  • ERC223Burnable.sol: Burning functionality implementation for ERC223 tokens. Use contract MyToken is ERC223Burnable to make your token burnable. Allows any address to burn its tokens by calling the burn function of the contract. There is no possibility to burn someone else’s tokens in this implementation.

ERC223 Token Standard

The ERC20 token standard suffers from critical issues, which have caused a loss of approximately $3,000,000 to date (December 31, 2017). The primary and most significant issue is the lack of an event handling mechanism in the ERC20 standard.
ERC223 is a superset of ERC20. It is a step forward towards economic abstraction at the application/contract level, allowing the use of tokens as first-class value transfer assets in the development of smart contracts. It is also a more secure standard, as it does not allow token transfers to contracts that do not explicitly support token reception.
1
contract ERC223 {
2
function transfer(address to, uint value, bytes data) {
3
uint codeLength;
4
assembly {
5
codeLength := extcodesize(_to)
6
}
7
balances[msg.sender] = balances[msg.sender].sub(_value);
8
balances[_to] = balances[_to].add(_value);
9
if(codeLength>0) {
10
// Require proper transaction handling.
11
ERC223Receiver receiver = ERC223Receiver(_to);
12
receiver.tokenReceived(msg.sender, _value, _data);
13
}
14
}
15
}
Copied!

The Main ERC20 Issues that ERC223 Solves

  1. 1.
    Lost Tokens: There are two different ways to transfer ERC20 tokens depending on whether the receiving address is a contract or a wallet address. You must call transfer to send tokens to a wallet address or call approve on the token contract and then transferFrom on the receiving contract to send tokens to the contract. Accidentally calling transfer on a contract address will result in a loss of tokens in the receiving contract.
  2. 2.
    Impossibility to handle incoming token transactions / lack of event handling in ERC20: An ERC20 token transaction is a call of the transfer function in the token contract. ERC20 token contract does not notify the receiver that the transaction occurs. Also, there is no way to handle incoming token transactions on the contract and no way to reject any non-supported tokens.
  3. 3.
    Optimization of ERC20 address-to-contract communication: You should call approve on one token contract and then call transferFrom on another contract when you want to deposit your tokens into it. In fact, address-to-contract transfer is a couple of two different transactions in ERC20. It also costs twice more gas compared to ERC223 transfers. In ERC223, the address-to-contract transfer is a single transaction, just like the address-to-address transfer.
  4. 4.
    Ether transactions and token transactions behave differently: one of the goals of developing ERC223 was to make token transactions similar to Ether transactions to avoid users’ mistakes when transferring tokens and make interaction with token transactions easier for contract developers.

ERC223 Advantages

  1. 1.
    Prevents accidental loss of tokens in contracts that are not designed to work with sent tokens.
  2. 2.
    Allows users to send their tokens anywhere with a single transfer function. No difference if the receiver is a contract or not. No need to learn how the token contract works for an ordinary user to send tokens.
  3. 3.
    Allows contract developers to handle incoming token transactions.
  4. 4.
    Transferring ERC223 to the contract consumes 2 times less gas than approving ERC20 and transferring it to the receiving contract.
  5. 5.
    Allows tokens to be deposited into a contract in a single transaction. Preventing further bloating of the blockchain.
  6. 6.
    Makes token transactions similar to Ether transactions.
ERC223 tokens are backwards compatible with ERC20 tokens. It means that ERC223 supports every ERC20 functional and contracts or services working with ERC20 tokens will work with ERC223 tokens correctly.
ERC223 tokens should be sent by calling the transfer function on token contract with no difference if the receiver is a contract or a wallet address.
  • If the receiver is a wallet, an ERC223 token transfer will be identical to an ERC20 transfer.
  • If the receiver is a contract, the ERC223 token contract will try to call the tokenReceived function on the receiver contract. If there is no tokenReceived function on the receiver contract, the transaction will fail.
The tokenReceived function is analogue of fallback function for Ether transactions. It can be used to handle incoming transactions.
There is a way to attach bytes _data to token transactions, similar to the _data attached to Ether transactions. It will pass through token contract and will be handled by tokenReceived function on the receiver contract. There is also a way to call transfer function on ERC223 token contract with no data argument or using ERC20 ABI with no data on transfer function. In this case _data will be empty bytes array.

Reason for Designing the ERC223 Token Standard.

Here is a description of the ERC20 token standard problems that ERC223 solves:
ERC20 token standard is leading to money losses for end users. The main problem is the lack of possibility to handle incoming ERC20 transactions performed via the ERC20 token transfer function.
If you send 100 ETH to a contract that is not intended to work with Ether, then it will reject a transaction, and nothing bad will happen. If you send 100 ERC20 tokens to a contract that is not intended to work with ERC20 tokens, then it will not reject tokens because it can’t recognize an incoming transaction. As a result, your tokens will get stuck at the contract’s balance.
How much ERC20 tokens are currently lost (31 Dec, 2017):
  1. 1.
    QTUM, $1,358,441 lost. watch on Etherscan
  2. 2.
    EOS, $1,015,131 lost. watch on Etherscan
  3. 3.
    GNT, $249,627 lost. watch on Etherscan
  4. 4.
    STORJ, $217,477 lost. watch on Etherscan
  5. 5.
    Tronix , $201,232 lost. watch on Etherscan
  6. 6.
    DGD, $151,826 lost. watch on Etherscan
  7. 7.
    OMG, $149,941 lost. watch on Etherscan
  8. 8.
    STORJ, $102,560 lost. watch on Etherscan
  9. 9.
    MANA, $101,967 lost. watch on Etherscan
Another disadvantage of ERC20 standard that ERC223 solves:
  1. 1.
    Lack of transfer handling possibility.
  2. 2.
    Loss of tokens.
  3. 3.
    Token-transactions should match Ethereum ideology of uniformity. Users should always call transfer () function whenever they want to transfer their tokens. It doesn’t matter if the user is depositing to a contract or sending to an externally owned account.
This allows contracts to handle incoming token transactions and prevents accidentally sent tokens from being accepted by contracts (and stuck in the contract balance).
For example, decentralized exchange will not require a user to call approve () then call deposit () (which is internally calling transferFrom () to withdraw approved tokens). Token transaction will automatically be handled at the exchange contract.
The most important here is a call of tokenReceived when performing a transaction to a contract.

Appendix