This repository has been archived by the owner on Jul 12, 2022. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 87
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Copies cb-sol-cli in, updates the install process to clone chainbridge-solidity and build the ABI files.
- Loading branch information
Showing
23 changed files
with
1,303 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1 +1,3 @@ | ||
.idea/ | ||
.idea/ | ||
node_modules/ | ||
chainbridge-solidity/ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
SOL_URL=https://github.com/ChainSafe/chainbridge-solidity | ||
|
||
|
||
fetch-contracts: | ||
@echo " > \033[32mFetching chainbridge-solidity contracts... \033[0m " | ||
git clone ${SOL_URL} && cd chainbridge-solidity && git checkout ${GIT_COMMIT} | ||
|
||
compile: | ||
cd chainbridge-solidity && npm install && npx truffle compile | ||
|
||
install: fetch-contracts compile | ||
@echo " > \033[32mInstalling cb-sol-cli... \033[0m " | ||
npm link . | ||
|
||
clean: | ||
rm -rf chainbridge-solidity/ |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,39 @@ | ||
# cb-sol-cli Documentation | ||
|
||
This CLI supports on-chain interactions with components of ChainBridge. | ||
|
||
## Installation | ||
|
||
Installation requires the ABI files from the contracts which will be fetched and built from the chainbridge-solidity repo. | ||
``` | ||
$ make install | ||
``` | ||
|
||
## Usage | ||
|
||
The root command (`cb-sol-cli`) has some options: | ||
``` | ||
--url <value> URL to connect to | ||
--gasLimit <value> Gas limit for transactions | ||
--gasPrice <value> Gas limit for transactions | ||
``` | ||
\ | ||
The keypair used for interactions can be configured with: | ||
``` | ||
--privateKey <value> Private key to use | ||
``` | ||
or | ||
``` | ||
--jsonWallet <path> Encrypted JSON wallet | ||
--jsonWalletPassword <value> Password for encrypted JSON wallet | ||
``` | ||
|
||
There are multiple subcommands provided: | ||
|
||
- [`deploy`](docs/deploy.md): Deploys contracts via RPC | ||
- [`bridge`](docs/bridge.md): Interactions with the bridge contract such as registering resource IDs and handler addresses | ||
- [`admin`](docs/admin.md): Interactions with the bridge contract for administering relayer set, relayer threshold, fees and more. | ||
- [`erc20`](docs/erc20.md): Interactions with ERC20 contracts and handlers | ||
- [`erc721`](docs/erc721.md): Interactions with ERC721 contracts and handler | ||
|
||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,115 @@ | ||
const ethers = require('ethers'); | ||
const constants = require('../constants'); | ||
|
||
const {Command} = require('commander'); | ||
const {setupParentArgs, waitForTx, log} = require("./utils") | ||
|
||
const isRelayerCmd = new Command("is-relayer") | ||
.description("Check if address is relayer") | ||
.option('--relayer <value>', 'Address to check', constants.relayerAddresses[0]) | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
|
||
let res = await bridgeInstance.isRelayer(args.relayer) | ||
console.log(`[${args._name}] Address ${args.relayer} ${res ? "is" : "is not"} a relayer.`) | ||
}) | ||
|
||
const addRelayerCmd = new Command("add-relayer") | ||
.description("Add a relayer") | ||
.option('--relayer <address>', 'Address of relayer', constants.relayerAddresses[0]) | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
log(args, `Adding ${args.relayer} as a relayer.`) | ||
let tx = await bridgeInstance.adminAddRelayer(args.relayer) | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const removeRelayerCmd = new Command("remove-relayer") | ||
.description("Remove a relayer") | ||
.option('--relayer <address>', 'Address of relayer', constants.relayerAddresses[0]) | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
log(args, `Removing relayer ${args.relayer}.`) | ||
let tx = await bridgeInstance.adminRemoveRelayer(args.relayer) | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const setThresholdCmd = new Command("set-threshold") | ||
.description("Set relayer threshold") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.option('--threshold <value>', 'New relayer threshold', 3) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
log(args, `Setting relayer threshold to ${args.threshold}`) | ||
let tx = await bridgeInstance.adminChangeRelayerThreshold(args.threshold) | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const pauseTransfersCmd = new Command("pause") | ||
.description("Pause deposits and proposal on the bridge") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
log(args, `Pausing deposits and proposals`) | ||
let tx = await bridgeInstance.adminPauseTransfers() | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const unpauseTransfersCmd = new Command("unpause") | ||
.description("Unpause deposits and proposals on the bridge") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
log(args, `Unpausing deposits and proposals`) | ||
let tx = await bridgeInstance.adminUnpauseTransfers() | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const changeFeeCmd = new Command("set-fee") | ||
.description("Set a new fee for deposits") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.option('--fee <value>', 'New fee (in wei)', 0) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
log(args, `Setting fee to ${args.fee} wei`) | ||
let tx = await bridgeInstance.adminChangeFee(args.fee) | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const withdrawCmd = new Command("withdraw") | ||
.description("Withdraw funds collected from fees") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.option('--handler <address>', 'Handler contract address', constants.ERC20_HANDLER_ADDRESS) | ||
.option('--tokenContract <address>', 'ERC20 or ERC721 token contract address', constants.ERC20_ADDRESS) | ||
.option('--recipient <address>', 'Address to withdraw to', constants.relayerAddresses[0]) | ||
.option('--amountOrId <value>', 'Token ID or amount to withdraw', 1) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
log(args, `Withdrawing tokens (${args.amountOrId}) in contract ${args.tokenContract} to recipient ${args.recipient}`) | ||
let tx = await bridgeInstance.adminWithdraw(args.handler, args.tokenContract, args.recipient, args.amountOrId) | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const adminCmd = new Command("admin") | ||
|
||
adminCmd.addCommand(isRelayerCmd) | ||
adminCmd.addCommand(addRelayerCmd) | ||
adminCmd.addCommand(removeRelayerCmd) | ||
adminCmd.addCommand(setThresholdCmd) | ||
adminCmd.addCommand(pauseTransfersCmd) | ||
adminCmd.addCommand(unpauseTransfersCmd) | ||
adminCmd.addCommand(changeFeeCmd) | ||
adminCmd.addCommand(withdrawCmd) | ||
|
||
module.exports = adminCmd |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,101 @@ | ||
const ethers = require('ethers'); | ||
const constants = require('../constants'); | ||
|
||
const {Command} = require('commander'); | ||
const {setupParentArgs, getFunctionBytes, waitForTx, log} = require("./utils") | ||
|
||
const EMPTY_SIG = "0x00000000" | ||
|
||
const registerResourceCmd = new Command("register-resource") | ||
.description("Register a resource ID with a contract address for a handler") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.option('--handler <address>', 'Handler address', constants.ERC20_HANDLER_ADDRESS) | ||
.option('--targetContract <address>', `Contract address to be registered`, constants.ERC20_ADDRESS) | ||
.option('--resourceId <address>', `Resource ID to be registered`, constants.ERC20_RESOURCEID) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
|
||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
log(args,`Registering contract ${args.targetContract} with resource ID ${args.resourceId} on handler ${args.handler}`); | ||
const tx = await bridgeInstance.adminSetResource(args.handler, args.resourceId, args.targetContract, { gasPrice: args.gasPrice, gasLimit: args.gasLimit}); | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const registerGenericResourceCmd = new Command("register-generic-resource") | ||
.description("Register a resource ID with a generic handler") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.option('--handler <address>', 'Handler contract address', constants.GENERIC_HANDLER_ADDRESS) | ||
.option('--targetContract <address>', `Contract address to be registered`, constants.CENTRIFUGE_ASSET_STORE_ADDRESS) | ||
.option('--resourceId <address>', `ResourceID to be registered`, constants.GENERIC_RESOURCEID) | ||
.option('--deposit <string>', "Deposit function signature", EMPTY_SIG) | ||
.option('--execute <string>', "Execute proposal function signature", EMPTY_SIG) | ||
.option('--hash', "Treat signature inputs as function prototype strings, hash and take the first 4 bytes", false) | ||
.action(async function(args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
|
||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
|
||
if (args.hash) { | ||
args.deposit = getFunctionBytes(args.deposit) | ||
args.execute = getFunctionBytes(args.execute) | ||
} | ||
|
||
log(args,`Registering generic resource ID ${args.resourceId} with contract ${args.targetContract} on handler ${args.handler}`) | ||
const tx = await bridgeInstance.adminSetGenericResource(args.handler, args.resourceId, args.targetContract, args.deposit, args.execute, { gasPrice: args.gasPrice, gasLimit: args.gasLimit}) | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const setBurnCmd = new Command("set-burn") | ||
.description("Set a token contract as burnable in a handler") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.option('--handler <address>', 'ERC20 handler contract address', constants.ERC20_HANDLER_ADDRESS) | ||
.option('--tokenContract <address>', `Token contract to be registered`, constants.ERC20_ADDRESS) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
|
||
log(args,`Setting contract ${args.tokenContract} as burnable on handler ${args.handler}`); | ||
const tx = await bridgeInstance.adminSetBurnable(args.handler, args.tokenContract, { gasPrice: args.gasPrice, gasLimit: args.gasLimit}); | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const queryProposalCmd = new Command("query-proposal") | ||
.description("Query a proposal on-chain") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.option('--depositNonce <address>', 'Nonce of proposal', 0) | ||
.option('--chainId <id>', 'Source chain ID of proposal', constants.DEFAULT_SOURCE_ID) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
|
||
// Instances | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
|
||
const prop = await bridgeInstance.getProposal(args.chainId, args.depositNonce) | ||
log(args, `Source: ${args.chainId} Nonce: ${args.depositNonce}`) | ||
log(args, `Votes: ${prop._yesVotes} Status: ${prop._status}`) | ||
}) | ||
|
||
|
||
const cancelProposalCmd = new Command("cancel-proposal") | ||
.description("Cancel a proposal that has passed the expiry threshold") | ||
.option('--bridge <address>', 'Bridge contract address', constants.BRIDGE_ADDRESS) | ||
.option('--chainId <id>', 'Chain ID of proposal to cancel', 0) | ||
.option('--depositNonce <value>', 'Deposit nonce of proposal to cancel', 0) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent) | ||
const bridgeInstance = new ethers.Contract(args.bridge, constants.ContractABIs.Bridge.abi, args.wallet); | ||
|
||
log(args, `Setting proposal with chain ID ${args.chainId} and deposit nonce ${args.depositNonce} status to 'Cancelled`); | ||
const tx = await bridgeInstance.adminCancelProposal(args.chainId, args.depositNonce); | ||
await waitForTx(args.provider, tx.hash) | ||
}) | ||
|
||
const bridgeCmd = new Command("bridge") | ||
|
||
bridgeCmd.addCommand(registerResourceCmd) | ||
bridgeCmd.addCommand(registerGenericResourceCmd) | ||
bridgeCmd.addCommand(setBurnCmd) | ||
bridgeCmd.addCommand(queryProposalCmd) | ||
bridgeCmd.addCommand(cancelProposalCmd) | ||
|
||
module.exports = bridgeCmd |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
const ethers = require('ethers'); | ||
const {Command} = require('commander'); | ||
|
||
const {setupParentArgs, log} = require("./utils") | ||
|
||
const constants = require('../constants'); | ||
|
||
const getHashCmd = new Command('getHash') | ||
.description('Returns if a the given hash exists') | ||
.requiredOption('--hash <value>', 'A hash to lookup', ethers.utils.hexZeroPad("0x", 32)) | ||
.option('--address <value>', 'Centrifuge asset store contract address', constants.CENTRIFUGE_ASSET_STORE_ADDRESS) | ||
.action(async function (args) { | ||
await setupParentArgs(args, args.parent.parent); | ||
const assetStore = new ethers.Contract(args.address, constants.ContractABIs.CentrifugeAssetStore.abi, args.wallet); | ||
const res = await assetStore._assetsStored(ethers.utils.hexZeroPad(args.hash, 32)); | ||
log(args, `The hash ${args.hash} was ${res ? "found!" : "NOT found!"}`); | ||
}) | ||
|
||
const centCmd = new Command("cent") | ||
|
||
centCmd.addCommand(getHashCmd) | ||
|
||
module.exports = centCmd |
Oops, something went wrong.