Swap ERC20 and ERC721 tokens atomically using Plasma Asset Swaps
This document will help you understand the Plasma asset swaps that can be performed while using Matic. This allows you to create applications such as decentralized exchanges, NFT marketplaces and similar while using our Plasma construction, which piggybacks on the security of Ethereum.
Introduction to EIP712 and signed transfer
This section aims to provide an introduction to the swap of mapped assets on Matic plasma chain.
Note: For tokens deployed on Matic directly - the process isn't required. The process only applies to tokens that are mapped on to Matic.
The transfer process is enabled by making use of the new RPC call
eth_SignTypedData, introduced in EIP712 - this is done to avoid the complexity of allowance on plasma chains and to add simplicity to plasma fraud proofs.
The construction includes introduction of a new method in each associated asset contract - ERC721 and ERC20 on matic plasma chain, called
transferWithSig. And a
Marketplace.sol smart contract that executes the swap.
The method definition is as follows:
bytes calldata sig - signature of the user on an order of spending a set amount of tokens in exchange of another set of tokens (creating an order)
uint256 amount - the amount of tokens user signs on
bytes32 data is a
keccak256 hash of the matching order (order id, token, amount)
uint256 expiration - the block number at which the order is to be expired
address to - order filler's address
The above method, when called from an external contract, validates the passed signature - the construction of which follows EIP712, recovers the user address and transfers the specified amount of tokens from the user's account to the specified account.
Asset Swap Protocol
Now this particular functionality - of transferring assets from a user's account using their signature - can be employed in a number of ways. One of them being that of a DEX-like marketplace that executes atomic swaps between tokens.
An order comprises of an order id, token address, amount (or token id). A user signs on an order and generates a signature. This signature is then used to transfer the signed amount of assets on user's behalf.
Below is a detailed spec of the Marketplace smart contract deployed on Matic chain, that performs atomic asset swaps.
The above contract executes the swap without prior approval or allowance transaction.
The function executeOrder takes two bytestreams that represent two orders that are to be settled along with the order filler (the participant that fulfills the order). Order settlement happens with the execution of transferWithSig method on the two tokens from both the orders:
Tutorial (ERC20/721 Swap)
Here is a short tutorial for you to try out execution of plasma-backed asset swaps on matic. A boilerplate codebase is ready for you to clone here. The repository consists of all the relevant contracts, which are, ChildERC20, ChildERC721, Marketplace and their dependencies along with the scripts that will guide you through the tutorial ahead.
- Best to use node v10.17.0 (npm v6.11.3)
Clone the repository and install dependencies
NOTE: All tokens that are mapped on to Matic (mapping is what enables movement of assets to and fro main chain - or root chain) are deployed on matic sidechain in the form of ChildERC20 and ChildERC721 tokens.
The version of ChildERC20 and ChildERC721 used in this tutorial include one additional function:
These are to help us mint the required tokens before we perform the swap.
Step 1 - Setup
1 - Compile contracts and deploy
Once you've cloned the repository, compile and migrate the contracts onto your preferred network.
Change directory to scripts
cd into the
2 - Fill in contracts' and accounts' details
config.js file sitting under
/scripts/erc20-721/ directory, and fill in the values of the variables mentioned.
provider - the network provider your contracts are deployed on
erc20 - address of the erc20 contract
erc721 - address of the erc721 contract
marketplace - address of the marketplace contract
amount - amount of erc20 tokens you'd like to exchange for the
tokenid - the id of the erc721 token you'd like to exchange for
amount of erc20 tokens
privateKey2 - the private keys of the accounts participating in the swap
You can leave
expiration untouched for now.
Note: Best to use a wallet - instead of hardcoding the private keys in your code - when building for production.
Step 2 - Mint
1 - Mint tokens into both accounts
to mint tokens in the two accounts.
The following function in the script mints the specified amount of tokens in the first account and the NFT of specified tokenId in the second account.
Running the script should display the transaction hashes of the two mints.
You can view the balances of the two accounts anytime by running:
This will display the balances of both the accounts for both the tokens.
Step 3 - Swap
To swap between the two accounts we first create two signatures - this is equivalent to creating two orders.
In the script,
encode function prepares the bytestreams of data that are the first two parameters of the
executeOrder function in
Marketplace.sol smart contract.
Next, we create two signature objects - which are essentially our two orders we'd like to match and execute via our Marketplace smart contract.
And executing the two orders:
Run the following to execute swap:
A successful swap displays a transaction hash. Next you can check the balances -
Deploying and Swapping on Matic
If you'd like to deploy and test on Matic network, the steps would only differ in migrating your smart contracts onto Matic and changing contract addresses in the config file.
From root directory, run:
or, for Matic beta network, run:
Once you have your contract addresses, fill them in the config file under
/scripts/erc20-721/ along with the provider, which will be the following for the two networks:
<Mumbai testnet RPC URL>. Sign up for a free dedicated RPC URL at https://rpc.maticvigil.com/ or other hosted node providers.
Matic beta mainnet:
Once the config file is ready, inside the
/scripts/erc20-721/ run the following -
To mint tokens
To check balances
Once the swap is successful, you can check and confirm the balances again