|
@@ -0,0 +1,51 @@
|
|
|
+import { Contract, ethers } from 'ethers'
|
|
|
+import { ChainId, chainInfoMap } from '../config/chain'
|
|
|
+import { newLogger } from '../utils/logger'
|
|
|
+
|
|
|
+export class MerklyClient {
|
|
|
+ wallet: ethers.Wallet
|
|
|
+ chainId: number
|
|
|
+ provider: ethers.JsonRpcProvider
|
|
|
+ router: ethers.Contract
|
|
|
+ static logger = newLogger('MerklyClient')
|
|
|
+
|
|
|
+ constructor(privateKey: string, chainId: number) {
|
|
|
+ this.chainId = chainId
|
|
|
+ this.provider = new ethers.JsonRpcProvider(chainInfoMap[chainId].rpcUrl)
|
|
|
+ this.wallet = new ethers.Wallet(privateKey, this.provider)
|
|
|
+ this.router = new Contract(
|
|
|
+ chainInfoMap[chainId].merklyInfo.routerAddress,
|
|
|
+ [
|
|
|
+ 'function quoteBridge(uint32 _destination, uint amount) external view returns (uint fee)',
|
|
|
+ 'function bridgeETH(uint32 _destination, uint amount) public payable returns (bytes32 messageId)',
|
|
|
+ 'function bridgeWETH(uint32 _destination, uint amount) public payable returns (bytes32 messageId)',
|
|
|
+ ],
|
|
|
+ this.wallet,
|
|
|
+ )
|
|
|
+ }
|
|
|
+
|
|
|
+ async bridge(toChainId: number = ChainId.ARBITRUM) {
|
|
|
+ const toInfo = chainInfoMap[toChainId].merklyInfo
|
|
|
+ if (!toInfo) {
|
|
|
+ throw new Error('Unsupported chain')
|
|
|
+ }
|
|
|
+ const balance = await this.provider.getBalance(this.wallet.address)
|
|
|
+ const quote = await this.router.quoteBridge(toInfo.merklyChainId, balance)
|
|
|
+ console.log('quote', ethers.formatEther(quote))
|
|
|
+ console.log('balance', ethers.formatEther(balance))
|
|
|
+ if (balance > quote) {
|
|
|
+ const feeData = await this.provider.getFeeData()
|
|
|
+ const estimatedGas = await this.router.bridgeETH.estimateGas(toInfo.merklyChainId, balance - quote, {
|
|
|
+ value: balance,
|
|
|
+ })
|
|
|
+ const gasCost = (feeData.gasPrice * estimatedGas * 108n) / 100n
|
|
|
+ console.log('gasCost', ethers.formatEther(gasCost))
|
|
|
+ const tx = await this.router.bridgeETH(toInfo.merklyChainId, balance - quote - gasCost, {
|
|
|
+ value: balance - gasCost,
|
|
|
+ gasLimit: (estimatedGas * 105n) / 100n,
|
|
|
+ gasPrice: feeData.gasPrice,
|
|
|
+ })
|
|
|
+ return tx.hash
|
|
|
+ }
|
|
|
+ }
|
|
|
+}
|