forked from OffchainLabs/arbitrum-tutorials
-
Notifications
You must be signed in to change notification settings - Fork 0
/
exec.js
135 lines (116 loc) · 4.62 KB
/
exec.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
const { ethers } = require('hardhat')
const { providers, Wallet } = require('ethers')
const {
getL2Network,
addDefaultLocalNetwork,
L1ToL2MessageStatus,
} = require('@arbitrum/sdk')
const { arbLog, requireEnvVariables } = require('arb-shared-dependencies')
const {
AdminErc20Bridger,
} = require('@arbitrum/sdk/dist/lib/assetBridger/erc20Bridger')
const { expect } = require('chai')
require('dotenv').config()
requireEnvVariables(['DEVNET_PRIVKEY', 'L1RPC', 'L2RPC'])
/**
* Set up: instantiate L1 / L2 wallets connected to providers
*/
const walletPrivateKey = process.env.DEVNET_PRIVKEY
const l1Provider = new providers.JsonRpcProvider(process.env.L1RPC)
const l2Provider = new providers.JsonRpcProvider(process.env.L2RPC)
const l1Wallet = new Wallet(walletPrivateKey, l1Provider)
const l2Wallet = new Wallet(walletPrivateKey, l2Provider)
/**
* Set the initial supply of L1 token that we want to bridge
* Note that you can change the value
*/
const premine = ethers.utils.parseEther('3')
const main = async () => {
await arbLog(
'Setting Up Your Token With The Generic Custom Gateway Using Arbitrum SDK Library'
)
/**
* Add the default local network configuration to the SDK
* to allow this script to run on a local node
*/
addDefaultLocalNetwork()
/**
* Use l2Network to create an Arbitrum SDK AdminErc20Bridger instance
* We'll use AdminErc20Bridger for its convenience methods around registering tokens to the custom gateway
*/
const l2Network = await getL2Network(l2Provider)
const adminTokenBridger = new AdminErc20Bridger(l2Network)
const l1Gateway = l2Network.tokenBridge.l1CustomGateway
const l1Router = l2Network.tokenBridge.l1GatewayRouter
const l2Gateway = l2Network.tokenBridge.l2CustomGateway
/**
* Deploy our custom token smart contract to L1
* We give the custom token contract the address of l1CustomGateway and l1GatewayRouter as well as the initial supply (premine)
*/
const L1CustomToken = await (
await ethers.getContractFactory('L1Token')
).connect(l1Wallet)
console.log('Deploying custom token to L1')
const l1CustomToken = await L1CustomToken.deploy(l1Gateway, l1Router, premine)
await l1CustomToken.deployed()
console.log(`custom token is deployed to L1 at ${l1CustomToken.address}`)
/**
* Deploy our custom token smart contract to L2
* We give the custom token contract the address of l2CustomGateway and our l1CustomToken
*/
const L2CustomToken = await (
await ethers.getContractFactory('L2Token')
).connect(l2Wallet)
console.log('Deploying custom token to L2')
const l2CustomToken = await L2CustomToken.deploy(
l2Gateway,
l1CustomToken.address
)
await l2CustomToken.deployed()
console.log(`custom token is deployed to L2 at ${l2CustomToken.address}`)
console.log('Registering custom token on L2:')
/**
* Register custom token on our custom gateway
*/
const registerTokenTx = await adminTokenBridger.registerCustomToken(
l1CustomToken.address,
l2CustomToken.address,
l1Wallet,
l2Provider
)
const registerTokenRec = await registerTokenTx.wait()
console.log(
`Registering token txn confirmed on L1! 🙌 L1 receipt is: ${registerTokenRec.transactionHash}`
)
/**
* The L1 side is confirmed; now we listen and wait for the L2 side to be executed; we can do this by computing the expected txn hash of the L2 transaction.
* To compute this txn hash, we need our message's "sequence numbers", unique identifiers of each L1 to L2 message.
* We'll fetch them from the event logs with a helper method.
*/
const l1ToL2Msgs = await registerTokenRec.getL1ToL2Messages(l2Provider)
/**
* In principle, a single L1 txn can trigger any number of L1-to-L2 messages (each with its own sequencer number).
* In this case, the registerTokenOnL2 method created 2 L1-to-L2 messages;
* - (1) one to set the L1 token to the Custom Gateway via the Router, and
* - (2) another to set the L1 token to its L2 token address via the Generic-Custom Gateway
* Here, We check if both messages are redeemed on L2
*/
expect(l1ToL2Msgs.length, 'Should be 2 messages.').to.eq(2)
const setTokenTx = await l1ToL2Msgs[0].waitForStatus()
expect(setTokenTx.status, 'Set token not redeemed.').to.eq(
L1ToL2MessageStatus.REDEEMED
)
const setGateways = await l1ToL2Msgs[1].waitForStatus()
expect(setGateways.status, 'Set gateways not redeemed.').to.eq(
L1ToL2MessageStatus.REDEEMED
)
console.log(
'Your custom token is now registered on our custom gateway 🥳 Go ahead and make the deposit!'
)
}
main()
.then(() => process.exit(0))
.catch(error => {
console.error(error)
process.exit(1)
})