From cec6dc91e4d0485db6e57654d18dfc66bbdad647 Mon Sep 17 00:00:00 2001 From: Priya Narayanaswamy Date: Wed, 18 Dec 2024 19:38:22 +0100 Subject: [PATCH 1/3] chore: Split transactions into separate components --- src/components/transactions/eip747.js | 100 +++ src/components/transactions/erc1155.js | 294 +++++++++ src/components/transactions/erc20.js | 366 +++++++++++ src/components/transactions/erc721.js | 463 ++++++++++++++ src/components/transactions/send.js | 359 +++++++++++ src/index.html | 652 +------------------ src/index.js | 850 ++----------------------- 7 files changed, 1631 insertions(+), 1453 deletions(-) create mode 100644 src/components/transactions/eip747.js create mode 100644 src/components/transactions/erc1155.js create mode 100644 src/components/transactions/erc20.js create mode 100644 src/components/transactions/erc721.js create mode 100644 src/components/transactions/send.js diff --git a/src/components/transactions/eip747.js b/src/components/transactions/eip747.js new file mode 100644 index 00000000..b8e50a42 --- /dev/null +++ b/src/components/transactions/eip747.js @@ -0,0 +1,100 @@ +import globalContext from '../..'; + +export function eip747Component(parentContainer) { + parentContainer.insertAdjacentHTML( + 'beforeend', + `
+
+
+

+ EIP 747 +

+ +
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ +
+ +

+ EIP 747: +

+
+
+
`, + ); + + // ERC 747 Section + const eip747ContractAddress = document.getElementById( + 'eip747ContractAddress', + ); + const eip747Symbol = document.getElementById('eip747Symbol'); + const eip747Decimals = document.getElementById('eip747Decimals'); + const eip747WatchButton = document.getElementById('eip747WatchButton'); + const eip747Status = document.getElementById('eip747Status'); + + /** + * EIP 747 + */ + + eip747WatchButton.onclick = async () => { + eip747Status.innerHTML = 'Adding token...'; + + try { + const result = await globalContext.provider.request({ + method: 'wallet_watchAsset', + params: { + type: 'ERC20', + options: { + address: eip747ContractAddress.value, + symbol: eip747Symbol.value, + decimals: parseInt(eip747Decimals.value, 10), + image: 'https://metamask.github.io/test-dapp/metamask-fox.svg', + }, + }, + }); + eip747Status.innerHTML = 'NFT added successfully'; + console.log(result); + } catch (error) { + eip747Status.innerHTML = + 'There was an error adding the token. See console for details.'; + console.error(error); + } + }; +} diff --git a/src/components/transactions/erc1155.js b/src/components/transactions/erc1155.js new file mode 100644 index 00000000..402f76cb --- /dev/null +++ b/src/components/transactions/erc1155.js @@ -0,0 +1,294 @@ +import globalContext from '../..'; + +export function erc1155Component(parentContainer) { + parentContainer.insertAdjacentHTML( + 'beforeend', + `
+
+
+

+ ERC 1155 +

+ +

+ Token(s): +

+ + + +
+ + +
+ +
+ + +
+ +
+ +
+ +
+ + +
+ +
+ + +
+ +
+ +
+ +
+ +
+ +
+ +
+ +
+ + +
+ +
+ +
+ +

+ ERC 1155 methods results: +

+
+
+
`, + ); + + const deployERC1155Button = document.getElementById('deployERC1155Button'); + const batchMintTokenIds = document.getElementById('batchMintTokenIds'); + const batchMintIdAmounts = document.getElementById('batchMintIdAmounts'); + const batchMintButton = document.getElementById('batchMintButton'); + const batchTransferTokenIds = document.getElementById( + 'batchTransferTokenIds', + ); + const batchTransferTokenAmounts = document.getElementById( + 'batchTransferTokenAmounts', + ); + const batchTransferFromButton = document.getElementById( + 'batchTransferFromButton', + ); + const setApprovalForAllERC1155Button = document.getElementById( + 'setApprovalForAllERC1155Button', + ); + const revokeERC1155Button = document.getElementById('revokeERC1155Button'); + const watchAssetInput = document.getElementById('watchAssetInput'); + const watchAssetButton = document.getElementById('watchAssetButton'); + const erc1155Status = document.getElementById('erc1155Status'); + const erc1155TokenAddresses = document.getElementById( + 'erc1155TokenAddresses', + ); + + /** + * ERC1155 Token + */ + + let erc1155Contract; + deployERC1155Button.onclick = async () => { + erc1155Status.innerHTML = 'Deploying'; + + try { + erc1155Contract = await globalContext.erc1155Factory.deploy(); + await erc1155Contract.deployTransaction.wait(); + } catch (error) { + erc1155Status.innerHTML = 'Deployment Failed!'; + throw error; + } + + if (erc1155Contract.address === undefined) { + return; + } + + console.log( + `Contract mined! address: ${erc1155Contract.address} transactionHash: ${erc1155Contract.deployTransaction.hash}`, + ); + + erc1155TokenAddresses.innerHTML = erc1155TokenAddresses.innerHTML + .concat(', ', erc1155Contract.address) + .split(', ') + .filter(Boolean) + .join(', '); + + erc1155Status.innerHTML = 'Deployed'; + batchTransferTokenIds.disabled = false; + batchTransferTokenAmounts.disabled = false; + batchMintButton.disabled = false; + batchTransferFromButton.disabled = false; + setApprovalForAllERC1155Button.disabled = false; + revokeERC1155Button.disabled = false; + watchAssetInput.disabled = false; + watchAssetButton.disabled = false; + }; + + batchMintButton.onclick = async () => { + erc1155Status.innerHTML = 'Batch Mint initiated'; + const contract = erc1155Contract || globalContext.erc1155Contract; + + const params = [ + globalContext.accounts[0], + batchMintTokenIds.value.split(',').map(Number), + batchMintIdAmounts.value.split(',').map(Number), + '0x', + ]; + + let result; + + try { + result = await contract.mintBatch(...params); + } catch (error) { + erc1155Status.innerHTML = 'Mint Failed!'; + throw error; + } + + console.log(result); + erc1155Status.innerHTML = 'Batch Minting completed'; + }; + + batchTransferFromButton.onclick = async () => { + erc1155Status.innerHTML = 'Batch Transfer From initiated'; + const contract = erc1155Contract || globalContext.erc1155Contract; + + const params = [ + globalContext.accounts[0], + '0x2f318C334780961FB129D2a6c30D0763d9a5C970', + batchTransferTokenIds.value.split(',').map(Number), + batchTransferTokenAmounts.value.split(',').map(Number), + '0x', + ]; + + let result; + + try { + result = await contract.safeBatchTransferFrom(...params); + } catch (error) { + erc1155Status.innerHTML = 'Transaction Failed!'; + throw error; + } + console.log(result); + erc1155Status.innerHTML = 'Batch Transfer From completed'; + }; + + setApprovalForAllERC1155Button.onclick = async () => { + erc1155Status.innerHTML = 'Set Approval For All initiated'; + const contract = erc1155Contract || globalContext.erc1155Contract; + let result = await contract.setApprovalForAll( + '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', + true, + { + from: globalContext.accounts[0], + }, + ); + result = await result.wait(); + console.log(result); + erc1155Status.innerHTML = 'Set Approval For All completed'; + }; + + revokeERC1155Button.onclick = async () => { + erc1155Status.innerHTML = 'Revoke initiated'; + const contract = erc1155Contract || globalContext.erc1155Contract; + let result = await contract.setApprovalForAll( + '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', + false, + { + from: globalContext.accounts[0], + }, + ); + result = await result.wait(); + console.log(result); + erc1155Status.innerHTML = 'Revoke completed'; + }; + + watchAssetButton.onclick = async () => { + try { + const contract = erc1155Contract || globalContext.erc1155Contract; + const watchAssetResult = await globalContext.provider.request({ + method: 'wallet_watchAsset', + params: { + type: 'ERC1155', + options: { + address: contract.address, + tokenId: watchAssetInput.value, + }, + }, + }); + console.log(watchAssetResult); + } catch (error) { + console.error(error); + } + }; +} diff --git a/src/components/transactions/erc20.js b/src/components/transactions/erc20.js new file mode 100644 index 00000000..33c4ad49 --- /dev/null +++ b/src/components/transactions/erc20.js @@ -0,0 +1,366 @@ +import globalContext from '../..'; + +export function erc20Component(parentContainer) { + parentContainer.insertAdjacentHTML( + 'beforeend', + `
+
+
+

+ ERC 20 +

+ +

+ Token(s): +

+ +
+ + +
+ + + + + + + + + + + +
+
+ + +
+ + + + + + + + +
+
+ + +
+ +
+ + +
+ +

+ Allowance amount: +

+
+
+ + +
+ +
+ + +
+ +
+ + + + +

+ ERC 20 methods result: +

+
+
+
`, + ); + + const erc20TokenAddresses = document.getElementById('erc20TokenAddresses'); + const createToken = document.getElementById('createToken'); + const watchAssets = document.getElementById('watchAssets'); + const transferTokens = document.getElementById('transferTokens'); + const transferFromTokens = document.getElementById('transferFromTokens'); + const approveTokens = document.getElementById('approveTokens'); + const increaseTokenAllowance = document.getElementById( + 'increaseTokenAllowance', + ); + const allowanceOwnerInput = document.getElementById('allowanceOwner'); + const allowanceSpenderInput = document.getElementById('allowanceSpender'); + const allowanceAmountResult = document.getElementById( + 'allowanceAmountResult', + ); + const getAllowance = document.getElementById('getAllowance'); + const transferTokensWithoutGas = document.getElementById( + 'transferTokensWithoutGas', + ); + const approveTokensWithoutGas = document.getElementById( + 'approveTokensWithoutGas', + ); + + const tokenMethodsResult = document.getElementById('tokenMethodsResult'); + const decimalUnitsInput = document.getElementById('tokenDecimals'); + const approveTokensToInput = document.getElementById('approveTo'); + const transferFromSenderInput = document.getElementById( + 'transferFromSenderInput', + ); + const transferFromRecipientInput = document.getElementById( + 'transferFromRecipientInput', + ); + const tokenSymbol = 'TST'; + + /** + * ERC20 Token + */ + + let hstContract; + createToken.onclick = async () => { + const _initialAmount = 10; + const _tokenName = 'TST'; + + try { + hstContract = await globalContext.hstFactory.deploy( + _initialAmount, + _tokenName, + decimalUnitsInput.value, + tokenSymbol, + ); + await hstContract.deployTransaction.wait(); + } catch (error) { + erc20TokenAddresses.innerHTML = 'Creation Failed'; + throw error; + } + + if (hstContract.address === undefined) { + return; + } + + console.log( + `Contract mined! address: ${hstContract.address} transactionHash: ${hstContract.deployTransaction.hash}`, + ); + erc20TokenAddresses.innerHTML = erc20TokenAddresses.innerHTML + .concat(', ', hstContract.address) + .split(', ') + .filter(Boolean) + .join(', '); + watchAssets.disabled = false; + transferTokens.disabled = false; + transferFromTokens.disabled = false; + approveTokens.disabled = false; + increaseTokenAllowance.disabled = false; + allowanceOwnerInput.disabled = false; + allowanceSpenderInput.disabled = false; + allowanceAmountResult.disabled = false; + getAllowance.disabled = false; + transferTokensWithoutGas.disabled = false; + approveTokensWithoutGas.disabled = false; + approveTokensToInput.disabled = false; + transferFromSenderInput.disabled = false; + transferFromRecipientInput.disabled = false; + }; + + watchAssets.onclick = async () => { + const contractAddresses = erc20TokenAddresses.innerHTML.split(', '); + + const promises = contractAddresses.map((erc20Address) => { + return globalContext.provider.request({ + method: 'wallet_watchAsset', + params: { + type: 'ERC20', + options: { + address: erc20Address, + symbol: tokenSymbol, + decimals: decimalUnitsInput.value, + image: 'https://metamask.github.io/test-dapp/metamask-fox.svg', + }, + }, + }); + }); + + Promise.all(promises).then((result) => { + console.log('result', result); + }); + }; + + transferTokens.onclick = async () => { + const contract = hstContract || globalContext.hstContract; + const result = await contract.transfer( + '0x2f318C334780961FB129D2a6c30D0763d9a5C970', + decimalUnitsInput.value === '0' + ? 1 + : `${1.5 * 10 ** decimalUnitsInput.value}`, + { from: globalContext.accounts[0] }, + ); + console.log('result', result); + }; + + approveTokens.onclick = async () => { + const contract = hstContract || globalContext.hstContract; + const result = await contract.approve( + approveTokensToInput.value, + `${7 * 10 ** decimalUnitsInput.value}`, + { from: globalContext.accounts[0] }, + ); + console.log('result', result); + }; + + increaseTokenAllowance.onclick = async () => { + const contract = hstContract || globalContext.hstContract; + const result = await contract.increaseAllowance( + approveTokensToInput.value, + `${1 * 10 ** decimalUnitsInput.value}`, + { from: globalContext.accounts[0] }, + ); + console.log('result', result); + }; + + getAllowance.onclick = async () => { + const contract = hstContract || globalContext.hstContract; + const result = await contract.allowance( + allowanceOwnerInput.value, + allowanceSpenderInput.value, + { from: globalContext.accounts[0] }, + ); + const allowance = result.toNumber() / 10 ** decimalUnitsInput.value; + allowanceAmountResult.innerHTML = allowance.toFixed( + decimalUnitsInput.value, + ); + }; + + transferFromTokens.onclick = async () => { + try { + const contract = hstContract || globalContext.hstContract; + const result = await contract.transferFrom( + transferFromSenderInput.value, + transferFromRecipientInput.value, + decimalUnitsInput.value === '0' + ? 1 + : `${1.5 * 10 ** decimalUnitsInput.value}`, + { from: globalContext.accounts[0] }, + ); + console.log('result', result); + tokenMethodsResult.innerHTML = result; + } catch (error) { + tokenMethodsResult.innerHTML = error.message; + } + }; + + transferTokensWithoutGas.onclick = async () => { + const contract = hstContract || globalContext.hstContract; + const result = await contract.transfer( + '0x2f318C334780961FB129D2a6c30D0763d9a5C970', + decimalUnitsInput.value === '0' + ? 1 + : `${1.5 * 10 ** decimalUnitsInput.value}`, + { + gasPrice: '20000000000', + }, + ); + console.log('result', result); + }; + + approveTokensWithoutGas.onclick = async () => { + const contract = hstContract || globalContext.hstContract; + const result = await contract.approve( + '0x2f318C334780961FB129D2a6c30D0763d9a5C970', + `${7 * 10 ** decimalUnitsInput.value}`, + { + gasPrice: '20000000000', + }, + ); + console.log('result', result); + }; +} diff --git a/src/components/transactions/erc721.js b/src/components/transactions/erc721.js new file mode 100644 index 00000000..164a28e1 --- /dev/null +++ b/src/components/transactions/erc721.js @@ -0,0 +1,463 @@ +import { recoverTypedSignature } from '@metamask/eth-sig-util'; +import { toChecksumAddress } from 'ethereumjs-util'; +import { splitSig } from '../../signatures/utils'; +import globalContext from '../..'; + +export function erc721Component(parentContainer) { + parentContainer.insertAdjacentHTML( + 'beforeend', + `
+
+
+

+ ERC 721 +

+ +

+ Token(s): +

+ + + +
+ + +
+ +
+ +
+ +
+ + +
+ +
+ +
+ +
+ +
+ +
+
+ +
+ + +
+ +
+ +
+ +
+ +
+ +
+ +
+ +
+ + +
+ +
+ +
+ +
+ + + +

+ Result: + +

r:

+

s:

+

v:

+

+ + + +

+ Recovery result: + +

+
+ +

+ ERC 721 methods result: +

+
+
+
`, + ); + + // NFTs Section + const deployNFTsButton = document.getElementById('deployNFTsButton'); + const mintButton = document.getElementById('mintButton'); + const watchNFTsButton = document.getElementById('watchNFTsButton'); + const watchNFTButtons = document.getElementById('watchNFTButtons'); + + const mintAmountInput = document.getElementById('mintAmountInput'); + const approveTokenInput = document.getElementById('approveTokenInput'); + const approveButton = document.getElementById('approveButton'); + const watchNFTInput = document.getElementById('watchNFTInput'); + const watchNFTButton = document.getElementById('watchNFTButton'); + const setApprovalForAllButton = document.getElementById( + 'setApprovalForAllButton', + ); + const revokeButton = document.getElementById('revokeButton'); + const transferTokenInput = document.getElementById('transferTokenInput'); + const transferFromButton = document.getElementById('transferFromButton'); + const nftsStatus = document.getElementById('nftsStatus'); + const erc721TokenAddresses = document.getElementById('erc721TokenAddresses'); + // 721 Permit + const sign721Permit = document.getElementById('sign721Permit'); + const sign721PermitResult = document.getElementById('sign721PermitResult'); + const sign721PermitResultR = document.getElementById('sign721PermitResultR'); + const sign721PermitResultS = document.getElementById('sign721PermitResultS'); + const sign721PermitResultV = document.getElementById('sign721PermitResultV'); + const sign721PermitVerify = document.getElementById('sign721PermitVerify'); + const sign721PermitVerifyResult = document.getElementById( + 'sign721PermitVerifyResult', + ); + + /** + * ERC721 Token + */ + + let nftsContract; + + deployNFTsButton.onclick = async () => { + nftsStatus.innerHTML = 'Deploying'; + + try { + nftsContract = await globalContext.nftsFactory.deploy(); + await nftsContract.deployTransaction.wait(); + } catch (error) { + nftsStatus.innerHTML = 'Deployment Failed'; + throw error; + } + + if (nftsContract.address === undefined) { + return; + } + + console.log( + `Contract mined! address: ${nftsContract.address} transactionHash: ${nftsContract.deployTransaction.hash}`, + ); + + erc721TokenAddresses.innerHTML = erc721TokenAddresses.innerHTML + .concat(', ', nftsContract.address) + .split(', ') + .filter(Boolean) + .join(', '); + + nftsStatus.innerHTML = 'Deployed'; + mintButton.disabled = false; + sign721Permit.disabled = false; + mintAmountInput.disabled = false; + }; + + watchNFTsButton.onclick = async () => { + const contract = nftsContract || globalContext.nftsContract; + const currentTokenId = await contract.currentTokenId(); + const nftsContractAddress = contract.address; + let watchNftsResult; + try { + watchNftsResult = await globalContext.provider.sendAsync( + Array.from({ length: currentTokenId }, (_, i) => i + 1).map( + (tokenId) => { + return { + method: 'wallet_watchAsset', + params: { + type: 'ERC721', + options: { + address: nftsContractAddress, + tokenId: tokenId.toString(), + }, + }, + }; + }, + ), + ); + } catch (error) { + console.error(error); + } + console.log(watchNftsResult); + }; + + mintButton.onclick = async () => { + const contract = nftsContract || globalContext.nftsContract; + nftsStatus.innerHTML = 'Mint initiated'; + let result = await contract.mintNFTs(mintAmountInput.value, { + from: globalContext.accounts[0], + }); + result = await result.wait(); + console.log(result); + nftsStatus.innerHTML = 'Mint completed'; + approveTokenInput.disabled = false; + approveButton.disabled = false; + watchNFTInput.disabled = false; + watchNFTButton.disabled = false; + setApprovalForAllButton.disabled = false; + revokeButton.disabled = false; + transferTokenInput.disabled = false; + transferFromButton.disabled = false; + watchNFTsButton.disabled = false; + watchNFTButtons.innerHTML = ''; + }; + + sign721Permit.onclick = async () => { + const from = globalContext.accounts[0]; + const msgParams = await getNFTMsgParams(); + console.log(msgParams); + + let sign; + let r; + let s; + let v; + + try { + sign = await globalContext.provider.request({ + method: 'eth_signTypedData_v4', + params: [from, JSON.stringify(msgParams)], + }); + const { _r, _s, _v } = splitSig(sign); + r = `0x${_r.toString('hex')}`; + s = `0x${_s.toString('hex')}`; + v = _v.toString(); + + sign721PermitResult.innerHTML = sign; + sign721PermitResultR.innerHTML = `r: ${r}`; + sign721PermitResultS.innerHTML = `s: ${s}`; + sign721PermitResultV.innerHTML = `v: ${v}`; + sign721PermitVerify.disabled = false; + } catch (err) { + console.error(err); + sign721PermitResult.innerHTML = `Error: ${err.message}`; + } + }; + + /** + * Sign Permit Verification + */ + sign721PermitVerify.onclick = async () => { + const from = globalContext.accounts[0]; + const msgParams = await getNFTMsgParams(); + + try { + const sign = sign721PermitResult.innerHTML; + const recoveredAddr = recoverTypedSignature({ + data: msgParams, + signature: sign, + version: 'V4', + }); + if (toChecksumAddress(recoveredAddr) === toChecksumAddress(from)) { + console.log(`Successfully verified signer as ${recoveredAddr}`); + sign721PermitVerifyResult.innerHTML = recoveredAddr; + } else { + console.log( + `Failed to verify signer when comparing ${recoveredAddr} to ${from}`, + ); + } + } catch (err) { + console.error(err); + sign721PermitVerifyResult.innerHTML = `Error: ${err.message}`; + } + }; + + watchNFTButton.onclick = async () => { + const contract = nftsContract || globalContext.nftsContract; + let watchNftsResult; + try { + watchNftsResult = await globalContext.provider.request({ + method: 'wallet_watchAsset', + params: { + type: 'ERC721', + options: { + address: contract.address, + tokenId: watchNFTInput.value, + }, + }, + }); + } catch (error) { + console.error(error); + } + console.log(watchNftsResult); + }; + + approveButton.onclick = async () => { + const contract = nftsContract || globalContext.nftsContract; + nftsStatus.innerHTML = 'Approve initiated'; + let result = await contract.approve( + '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', + approveTokenInput.value, + { + from: globalContext.accounts[0], + }, + ); + result = await result.wait(); + console.log(result); + nftsStatus.innerHTML = 'Approve completed'; + }; + + setApprovalForAllButton.onclick = async () => { + nftsStatus.innerHTML = 'Set Approval For All initiated'; + const contract = nftsContract || globalContext.nftsContract; + let result = await contract.setApprovalForAll( + '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', + true, + { + from: globalContext.accounts[0], + }, + ); + result = await result.wait(); + console.log(result); + nftsStatus.innerHTML = 'Set Approval For All completed'; + }; + + revokeButton.onclick = async () => { + nftsStatus.innerHTML = 'Revoke initiated'; + const contract = nftsContract || globalContext.nftsContract; + let result = await contract.setApprovalForAll( + '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', + false, + { + from: globalContext.accounts[0], + }, + ); + result = await result.wait(); + console.log(result); + nftsStatus.innerHTML = 'Revoke completed'; + }; + + transferFromButton.onclick = async () => { + nftsStatus.innerHTML = 'Transfer From initiated'; + const contract = nftsContract || globalContext.nftsContract; + let result = await contract.transferFrom( + globalContext.accounts[0], + '0x2f318C334780961FB129D2a6c30D0763d9a5C970', + transferTokenInput.value, + { + from: globalContext.accounts[0], + }, + ); + result = await result.wait(); + console.log(result); + nftsStatus.innerHTML = 'Transfer From completed'; + }; + + async function getNFTMsgParams() { + const contract = nftsContract || globalContext.nftsContract; + return { + domain: { + name: 'My NFT', + version: '1', + chainId: globalContext.chainIdInt, + verifyingContract: contract.address, + }, + types: { + Permit: [ + { name: 'spender', type: 'address' }, + { name: 'tokenId', type: 'uint256' }, + { name: 'nonce', type: 'uint256' }, + { name: 'deadline', type: 'uint256' }, + ], + }, + primaryType: 'Permit', + message: { + spender: '0x0521797E19b8E274E4ED3bFe5254FAf6fac96F08', + tokenId: '3606393', + nonce: '0', + deadline: '1734995006', + }, + }; + } +} diff --git a/src/components/transactions/send.js b/src/components/transactions/send.js new file mode 100644 index 00000000..9a35c755 --- /dev/null +++ b/src/components/transactions/send.js @@ -0,0 +1,359 @@ +import globalContext from '../..'; + +export function sendComponent(parentContainer) { + parentContainer.insertAdjacentHTML( + 'beforeend', + `
+
+
+

+ Send Eth +

+ + + + + + + + +
+

+ Piggy bank contract +

+ + + + + + + +

+ Contract Status: Not clicked +

+
+

+ Failing contract +

+ + + + + +

+ Failing Contract Status: Not clicked +

+
+

+ Multisig contract +

+ + + + + +

+ Multisig Contract Status: Not clicked +

+
+
+
`, + ); + + const sendButton = document.getElementById('sendButton'); + const sendEIP1559Button = document.getElementById('sendEIP1559Button'); + const sendEIP1559WithoutGasButton = document.getElementById( + 'sendEIP1559WithoutGasButton', + ); + // const sendDeeplinkButton = document.getElementById('sendDeeplinkButton'); + const deployButton = document.getElementById('deployButton'); + const depositButton = document.getElementById('depositButton'); + const withdrawButton = document.getElementById('withdrawButton'); + const contractStatus = document.getElementById('contractStatus'); + const deployFailingButton = document.getElementById('deployFailingButton'); + const sendFailingButton = document.getElementById('sendFailingButton'); + const failingContractStatus = document.getElementById( + 'failingContractStatus', + ); + const deployMultisigButton = document.getElementById('deployMultisigButton'); + const sendMultisigButton = document.getElementById('sendMultisigButton'); + const multisigContractStatus = document.getElementById( + 'multisigContractStatus', + ); + + /** + * Sending ETH + */ + + sendButton.onclick = async () => { + const result = await globalContext.provider.request({ + method: 'eth_sendTransaction', + params: [ + { + from: globalContext.accounts[0], + to: '0x0c54FcCd2e384b4BB6f2E405Bf5Cbc15a017AaFb', + value: '0x0', + gasLimit: '0x5208', + gasPrice: '0x2540be400', + type: '0x0', + }, + ], + }); + console.log(result); + }; + + sendEIP1559Button.onclick = async () => { + const result = await globalContext.provider.request({ + method: 'eth_sendTransaction', + params: [ + { + from: globalContext.accounts[0], + to: '0x0c54FcCd2e384b4BB6f2E405Bf5Cbc15a017AaFb', + value: '0x0', + gasLimit: '0x5028', + maxFeePerGas: '0x2540be400', + maxPriorityFeePerGas: '0x3b9aca00', + }, + ], + }); + console.log(result); + }; + + sendEIP1559WithoutGasButton.onclick = async () => { + const result = await globalContext.provider.request({ + method: 'eth_sendTransaction', + params: [ + { + from: globalContext.accounts[0], + to: '0x0c54FcCd2e384b4BB6f2E405Bf5Cbc15a017AaFb', + value: '0x0', + }, + ], + }); + console.log(result); + }; + + /** + * Piggy bank + */ + let piggybankContract; + + deployButton.onclick = async () => { + contractStatus.innerHTML = 'Deploying'; + try { + piggybankContract = await globalContext.piggybankFactory.deploy(); + await piggybankContract.deployTransaction.wait(); + } catch (error) { + contractStatus.innerHTML = 'Deployment Failed'; + throw error; + } + + console.log(piggybankContract.address); + if (piggybankContract.address === undefined) { + return; + } + + console.log( + `Contract mined! address: ${piggybankContract.address} transactionHash: ${piggybankContract.deployTransaction.hash}`, + ); + contractStatus.innerHTML = 'Deployed'; + depositButton.disabled = false; + withdrawButton.disabled = false; + }; + + depositButton.onclick = async () => { + contractStatus.innerHTML = 'Deposit initiated'; + const contract = piggybankContract || globalContext.piggybankContract; + const result = await contract.deposit({ + from: globalContext.accounts[0], + value: '0x3782dace9d900000', + }); + console.log(result); + const receipt = await result.wait(); + console.log(receipt); + contractStatus.innerHTML = 'Deposit completed'; + }; + + withdrawButton.onclick = async () => { + const contract = piggybankContract || globalContext.piggybankContract; + const result = await contract.withdraw('0xde0b6b3a7640000', { + from: globalContext.accounts[0], + }); + console.log(result); + const receipt = await result.wait(); + console.log(receipt); + contractStatus.innerHTML = 'Withdrawn'; + }; + + /** + * Failing + */ + + let failingContract; + deployFailingButton.onclick = async () => { + failingContractStatus.innerHTML = 'Deploying'; + + try { + failingContract = await globalContext.failingContractFactory.deploy(); + await failingContract.deployTransaction.wait(); + } catch (error) { + failingContractStatus.innerHTML = 'Deployment Failed'; + throw error; + } + + if (failingContract.address === undefined) { + return; + } + + console.log( + `Contract mined! address: ${failingContract.address} transactionHash: ${failingContract.deployTransaction.hash}`, + ); + failingContractStatus.innerHTML = 'Deployed'; + sendFailingButton.disabled = false; + }; + + sendFailingButton.onclick = async () => { + try { + const contract = failingContract || globalContext.failingContract; + const result = await globalContext.provider.request({ + method: 'eth_sendTransaction', + params: [ + { + from: globalContext.accounts[0], + to: contract.address, + value: '0x0', + gasLimit: '0x5028', + maxFeePerGas: '0x2540be400', + maxPriorityFeePerGas: '0x3b9aca00', + }, + ], + }); + failingContractStatus.innerHTML = + 'Failed transaction process completed as expected.'; + console.log('send failing contract result', result); + } catch (error) { + console.log('error', error); + throw error; + } + }; + + /** + * Multisig + */ + + let multisigContract; + deployMultisigButton.onclick = async () => { + multisigContractStatus.innerHTML = 'Deploying'; + try { + multisigContract = await globalContext.multisigFactory.deploy(); + await multisigContract.deployTransaction.wait(); + } catch (error) { + multisigContractStatus.innerHTML = 'Deployment Failed'; + throw error; + } + + if (multisigContract.address === undefined) { + return; + } + + console.log( + `Contract mined! address: ${multisigContract.address} transactionHash: ${multisigContract.deployTransaction.hash}`, + ); + multisigContractStatus.innerHTML = 'Deployed'; + sendMultisigButton.disabled = false; + }; + + sendMultisigButton.onclick = async () => { + try { + const contract = multisigContract || globalContext.multisigContract; + const result = await globalContext.provider.request({ + method: 'eth_sendTransaction', + params: [ + { + from: globalContext.accounts[0], + to: contract.address, + value: '0x16345785D8A0', // 24414062500000 + gasLimit: '0x5028', + maxFeePerGas: '0x2540be400', + maxPriorityFeePerGas: '0x3b9aca00', + }, + ], + }); + multisigContractStatus.innerHTML = 'Transaction completed as expected.'; + console.log('send multisig contract result', result); + } catch (error) { + console.log('error', error); + throw error; + } + }; +} diff --git a/src/index.html b/src/index.html index f0f845a0..7b2155dd 100644 --- a/src/index.html +++ b/src/index.html @@ -195,657 +195,7 @@

-
-
-
-
-
-

- Send Eth -

- - - - - - - - -
-

- Piggy bank contract -

- - - - - - - -

- Contract Status: Not clicked -

-
-

- Failing contract -

- - - - - -

- Failing Contract Status: Not clicked -

-
-

- Multisig contract -

- - - - - -

- Multisig Contract Status: Not clicked -

-
-
-
- -
-
-
-

- ERC 20 -

- -

- Token(s): -

- -
- - -
- - - - - - - - - - - -
-
- - -
- - - - - - - - -
-
- - -
- -
- - -
- -

- Allowance amount: -

-
-
- - -
- -
- - -
- -
- - - - -

- ERC 20 methods result: -

-
-
-
-
-
-
-

- ERC 721 -

- -

- Token(s): -

- - - -
- - -
- -
- -
- -
- - -
- -
- -
- -
- -
- -
-
- -
- - -
- -
- -
- -
- -
- -
- -
- -
- - -
- -
- -
- -
- - - -

- Result: - -

r:

-

s:

-

v:

-

- - - -

- Recovery result: - -

-
- -

- ERC 721 methods result: -

-
-
-
-
-
-
-

- ERC 1155 -

- -

- Token(s): -

- - - -
- - -
- -
- - -
- -
- -
- -
- - -
- -
- - -
- -
- -
- -
- -
- -
- -
- -
- - -
- -
- -
- -

- ERC 1155 methods results: -

-
-
-
-
-
-
-

- EIP 747 -

- -
- - -
- -
- - -
- -
- - -
- -
- -
- -

- EIP 747: -

-
-
-
-
+
diff --git a/src/index.js b/src/index.js index 37ea2ec8..10ac7d9c 100644 --- a/src/index.js +++ b/src/index.js @@ -1,15 +1,12 @@ import MetaMaskOnboarding from '@metamask/onboarding'; // eslint-disable-next-line camelcase -import { recoverTypedSignature } from '@metamask/eth-sig-util'; import { ethers } from 'ethers'; -import { toChecksumAddress } from 'ethereumjs-util'; import { handleSdkConnect, handleWalletConnect, walletConnect, } from './connections'; import Constants from './constants.json'; -import { splitSig } from './signatures/utils'; import { NETWORKS_BY_CHAIN_ID } from './onchain-sample-contracts'; import { getPermissionsDisplayString } from './utils'; @@ -33,6 +30,11 @@ import { } from './components/signatures'; import { ensResolutionComponent } from './components/resolutions/ens-resolution'; import { sendFormComponent } from './components/forms/send-form'; +import { sendComponent } from './components/transactions/send'; +import { erc20Component } from './components/transactions/erc20'; +import { erc721Component } from './components/transactions/erc721'; +import { erc1155Component } from './components/transactions/erc1155'; +import { eip747Component } from './components/transactions/eip747'; const { hstBytecode, @@ -57,6 +59,18 @@ const globalContext = { chainIdPadded: undefined, networkName: undefined, _connected: false, + piggybankContract: undefined, + piggybankFactory: undefined, + failingContractFactory: undefined, + failingContract: undefined, + multisigContract: undefined, + multisigFactory: undefined, + hstContract: undefined, + hstFactory: undefined, + nftsContract: undefined, + nftsFactory: undefined, + erc1155Contract: undefined, + erc1155Factory: undefined, get connected() { return this._connected; }, @@ -134,6 +148,17 @@ const revokeAccountsPermissionButton = document.getElementById( 'revokeAccountsPermission', ); +const transactionsContainer = + document.getElementById('components-tranactions') || document.body; +const transactionsRow = document.createElement('div'); +transactionsRow.className = 'row'; +transactionsContainer.appendChild(transactionsRow); +sendComponent(transactionsRow); +erc20Component(transactionsRow); +erc721Component(transactionsRow); +erc1155Component(transactionsRow); +eip747Component(transactionsRow); + // Contract Section const deployButton = document.getElementById('deployButton'); const depositButton = document.getElementById('depositButton'); @@ -169,14 +194,7 @@ const nftsStatus = document.getElementById('nftsStatus'); const erc721TokenAddresses = document.getElementById('erc721TokenAddresses'); // 721 Permit const sign721Permit = document.getElementById('sign721Permit'); -const sign721PermitResult = document.getElementById('sign721PermitResult'); -const sign721PermitResultR = document.getElementById('sign721PermitResultR'); -const sign721PermitResultS = document.getElementById('sign721PermitResultS'); -const sign721PermitResultV = document.getElementById('sign721PermitResultV'); const sign721PermitVerify = document.getElementById('sign721PermitVerify'); -const sign721PermitVerifyResult = document.getElementById( - 'sign721PermitVerifyResult', -); // ERC 1155 Section @@ -201,11 +219,7 @@ const erc1155Status = document.getElementById('erc1155Status'); const erc1155TokenAddresses = document.getElementById('erc1155TokenAddresses'); // ERC 747 Section -const eip747ContractAddress = document.getElementById('eip747ContractAddress'); -const eip747Symbol = document.getElementById('eip747Symbol'); -const eip747Decimals = document.getElementById('eip747Decimals'); const eip747WatchButton = document.getElementById('eip747WatchButton'); -const eip747Status = document.getElementById('eip747Status'); // Send Eth Section const sendButton = document.getElementById('sendButton'); @@ -223,7 +237,6 @@ const transferFromSenderInput = document.getElementById( const transferFromRecipientInput = document.getElementById( 'transferFromRecipientInput', ); -const tokenSymbol = 'TST'; const erc20TokenAddresses = document.getElementById('erc20TokenAddresses'); const createToken = document.getElementById('createToken'); const watchAssets = document.getElementById('watchAssets'); @@ -878,19 +891,6 @@ const handleScrollTo = async ({ delay = false } = {}) => { * Contracts */ -let hstFactory; -let piggybankFactory; -let nftsFactory; -let failingContractFactory; -let multisigFactory; -let erc1155Factory; -let hstContract; -let piggybankContract; -let nftsContract; -let failingContract; -let multisigContract; -let erc1155Contract; - // Must be called after the active provider changes const initializeContracts = () => { try { @@ -900,63 +900,63 @@ const initializeContracts = () => { 'any', ); if (deployedContractAddress) { - hstContract = new ethers.Contract( + globalContext.hstContract = new ethers.Contract( deployedContractAddress, hstAbi, globalContext.ethersProvider.getSigner(), ); - piggybankContract = new ethers.Contract( + globalContext.piggybankContract = new ethers.Contract( deployedContractAddress, piggybankAbi, globalContext.ethersProvider.getSigner(), ); - nftsContract = new ethers.Contract( + globalContext.nftsContract = new ethers.Contract( deployedContractAddress, nftsAbi, globalContext.ethersProvider.getSigner(), ); - failingContract = new ethers.Contract( + globalContext.failingContract = new ethers.Contract( deployedContractAddress, failingContractAbi, globalContext.ethersProvider.getSigner(), ); - multisigContract = new ethers.Contract( + globalContext.multisigContract = new ethers.Contract( deployedContractAddress, multisigAbi, globalContext.ethersProvider.getSigner(), ); - erc1155Contract = new ethers.Contract( + globalContext.erc1155Contract = new ethers.Contract( deployedContractAddress, erc1155Abi, globalContext.ethersProvider.getSigner(), ); } - hstFactory = new ethers.ContractFactory( + globalContext.hstFactory = new ethers.ContractFactory( hstAbi, hstBytecode, globalContext.ethersProvider.getSigner(), ); - piggybankFactory = new ethers.ContractFactory( + globalContext.piggybankFactory = new ethers.ContractFactory( piggybankAbi, piggybankBytecode, globalContext.ethersProvider.getSigner(), ); - nftsFactory = new ethers.ContractFactory( + globalContext.nftsFactory = new ethers.ContractFactory( nftsAbi, nftsBytecode, globalContext.ethersProvider.getSigner(), ); - failingContractFactory = new ethers.ContractFactory( + globalContext.failingContractFactory = new ethers.ContractFactory( failingContractAbi, failingContractBytecode, globalContext.ethersProvider.getSigner(), ); - multisigFactory = new ethers.ContractFactory( + globalContext.multisigFactory = new ethers.ContractFactory( multisigAbi, multisigBytecode, globalContext.ethersProvider.getSigner(), ); - erc1155Factory = new ethers.ContractFactory( + globalContext.erc1155Factory = new ethers.ContractFactory( erc1155Abi, erc1155Bytecode, globalContext.ethersProvider.getSigner(), @@ -1074,7 +1074,9 @@ const updateContractElements = () => { multisigContractStatus.innerHTML = 'Deployed'; sendMultisigButton.disabled = false; // ERC721 Token - NFTs contract - erc721TokenAddresses.innerHTML = nftsContract ? nftsContract.address : ''; + erc721TokenAddresses.innerHTML = globalContext.nftsContract + ? globalContext.nftsContract.address + : ''; nftsStatus.innerHTML = 'Deployed'; mintButton.disabled = false; sign721Permit.disabled = false; @@ -1091,8 +1093,8 @@ const updateContractElements = () => { watchNFTButtons.innerHTML = ''; // ERC 1155 Multi Token - erc1155TokenAddresses.innerHTML = erc1155Contract - ? erc1155Contract.address + erc1155TokenAddresses.innerHTML = globalContext.erc1155Contract + ? globalContext.erc1155Contract.address : ''; erc1155Status.innerHTML = 'Deployed'; batchMintButton.disabled = false; @@ -1106,7 +1108,9 @@ const updateContractElements = () => { watchAssetInput.disabled = false; watchAssetButton.disabled = false; // ERC20 Token - Send Tokens - erc20TokenAddresses.innerHTML = hstContract ? hstContract.address : ''; + erc20TokenAddresses.innerHTML = globalContext.hstContract + ? globalContext.hstContract.address + : ''; watchAssets.disabled = false; transferTokens.disabled = false; transferFromTokens.disabled = false; @@ -1126,738 +1130,6 @@ const updateContractElements = () => { // Initializes form button onclicks const initializeFormElements = () => { - /** - * Piggy bank - */ - - deployButton.onclick = async () => { - contractStatus.innerHTML = 'Deploying'; - - try { - piggybankContract = await piggybankFactory.deploy(); - await piggybankContract.deployTransaction.wait(); - } catch (error) { - contractStatus.innerHTML = 'Deployment Failed'; - throw error; - } - - if (piggybankContract.address === undefined) { - return; - } - - console.log( - `Contract mined! address: ${piggybankContract.address} transactionHash: ${piggybankContract.deployTransaction.hash}`, - ); - contractStatus.innerHTML = 'Deployed'; - depositButton.disabled = false; - withdrawButton.disabled = false; - }; - - depositButton.onclick = async () => { - contractStatus.innerHTML = 'Deposit initiated'; - const result = await piggybankContract.deposit({ - from: globalContext.accounts[0], - value: '0x3782dace9d900000', - }); - console.log(result); - const receipt = await result.wait(); - console.log(receipt); - contractStatus.innerHTML = 'Deposit completed'; - }; - - withdrawButton.onclick = async () => { - const result = await piggybankContract.withdraw('0xde0b6b3a7640000', { - from: globalContext.accounts[0], - }); - console.log(result); - const receipt = await result.wait(); - console.log(receipt); - contractStatus.innerHTML = 'Withdrawn'; - }; - - /** - * Failing - */ - - deployFailingButton.onclick = async () => { - failingContractStatus.innerHTML = 'Deploying'; - - try { - failingContract = await failingContractFactory.deploy(); - await failingContract.deployTransaction.wait(); - } catch (error) { - failingContractStatus.innerHTML = 'Deployment Failed'; - throw error; - } - - if (failingContract.address === undefined) { - return; - } - - console.log( - `Contract mined! address: ${failingContract.address} transactionHash: ${failingContract.deployTransaction.hash}`, - ); - failingContractStatus.innerHTML = 'Deployed'; - sendFailingButton.disabled = false; - }; - - sendFailingButton.onclick = async () => { - try { - const result = await globalContext.provider.request({ - method: 'eth_sendTransaction', - params: [ - { - from: globalContext.accounts[0], - to: failingContract.address, - value: '0x0', - gasLimit: '0x5028', - maxFeePerGas: '0x2540be400', - maxPriorityFeePerGas: '0x3b9aca00', - }, - ], - }); - failingContractStatus.innerHTML = - 'Failed transaction process completed as expected.'; - console.log('send failing contract result', result); - } catch (error) { - console.log('error', error); - throw error; - } - }; - - /** - * Multisig - */ - - deployMultisigButton.onclick = async () => { - multisigContractStatus.innerHTML = 'Deploying'; - - try { - multisigContract = await multisigFactory.deploy(); - await multisigContract.deployTransaction.wait(); - } catch (error) { - multisigContractStatus.innerHTML = 'Deployment Failed'; - throw error; - } - - if (multisigContract.address === undefined) { - return; - } - - console.log( - `Contract mined! address: ${multisigContract.address} transactionHash: ${multisigContract.deployTransaction.hash}`, - ); - multisigContractStatus.innerHTML = 'Deployed'; - sendMultisigButton.disabled = false; - }; - - sendMultisigButton.onclick = async () => { - try { - const result = await globalContext.provider.request({ - method: 'eth_sendTransaction', - params: [ - { - from: globalContext.accounts[0], - to: multisigContract.address, - value: '0x16345785D8A0', // 24414062500000 - gasLimit: '0x5028', - maxFeePerGas: '0x2540be400', - maxPriorityFeePerGas: '0x3b9aca00', - }, - ], - }); - multisigContractStatus.innerHTML = 'Transaction completed as expected.'; - console.log('send multisig contract result', result); - } catch (error) { - console.log('error', error); - throw error; - } - }; - - /** - * ERC721 Token - */ - - deployNFTsButton.onclick = async () => { - nftsStatus.innerHTML = 'Deploying'; - - try { - nftsContract = await nftsFactory.deploy(); - await nftsContract.deployTransaction.wait(); - } catch (error) { - nftsStatus.innerHTML = 'Deployment Failed'; - throw error; - } - - if (nftsContract.address === undefined) { - return; - } - - console.log( - `Contract mined! address: ${nftsContract.address} transactionHash: ${nftsContract.deployTransaction.hash}`, - ); - - erc721TokenAddresses.innerHTML = erc721TokenAddresses.innerHTML - .concat(', ', nftsContract.address) - .split(', ') - .filter(Boolean) - .join(', '); - - nftsStatus.innerHTML = 'Deployed'; - mintButton.disabled = false; - sign721Permit.disabled = false; - mintAmountInput.disabled = false; - }; - - watchNFTsButton.onclick = async () => { - const currentTokenId = await nftsContract.currentTokenId(); - const nftsContractAddress = nftsContract.address; - let watchNftsResult; - try { - watchNftsResult = await globalContext.provider.sendAsync( - Array.from({ length: currentTokenId }, (_, i) => i + 1).map( - (tokenId) => { - return { - method: 'wallet_watchAsset', - params: { - type: 'ERC721', - options: { - address: nftsContractAddress, - tokenId: tokenId.toString(), - }, - }, - }; - }, - ), - ); - } catch (error) { - console.error(error); - } - console.log(watchNftsResult); - }; - - mintButton.onclick = async () => { - nftsStatus.innerHTML = 'Mint initiated'; - let result = await nftsContract.mintNFTs(mintAmountInput.value, { - from: globalContext.accounts[0], - }); - result = await result.wait(); - console.log(result); - nftsStatus.innerHTML = 'Mint completed'; - approveTokenInput.disabled = false; - approveButton.disabled = false; - watchNFTInput.disabled = false; - watchNFTButton.disabled = false; - setApprovalForAllButton.disabled = false; - revokeButton.disabled = false; - transferTokenInput.disabled = false; - transferFromButton.disabled = false; - watchNFTsButton.disabled = false; - watchNFTButtons.innerHTML = ''; - }; - - sign721Permit.onclick = async () => { - const from = globalContext.accounts[0]; - const msgParams = await getNFTMsgParams(); - console.log(msgParams); - - let sign; - let r; - let s; - let v; - - try { - sign = await globalContext.provider.request({ - method: 'eth_signTypedData_v4', - params: [from, JSON.stringify(msgParams)], - }); - const { _r, _s, _v } = splitSig(sign); - r = `0x${_r.toString('hex')}`; - s = `0x${_s.toString('hex')}`; - v = _v.toString(); - - sign721PermitResult.innerHTML = sign; - sign721PermitResultR.innerHTML = `r: ${r}`; - sign721PermitResultS.innerHTML = `s: ${s}`; - sign721PermitResultV.innerHTML = `v: ${v}`; - sign721PermitVerify.disabled = false; - } catch (err) { - console.error(err); - sign721PermitResult.innerHTML = `Error: ${err.message}`; - } - }; - - /** - * Sign Permit Verification - */ - sign721PermitVerify.onclick = async () => { - const from = globalContext.accounts[0]; - const msgParams = await getNFTMsgParams(); - - try { - const sign = sign721PermitResult.innerHTML; - const recoveredAddr = recoverTypedSignature({ - data: msgParams, - signature: sign, - version: 'V4', - }); - if (toChecksumAddress(recoveredAddr) === toChecksumAddress(from)) { - console.log(`Successfully verified signer as ${recoveredAddr}`); - sign721PermitVerifyResult.innerHTML = recoveredAddr; - } else { - console.log( - `Failed to verify signer when comparing ${recoveredAddr} to ${from}`, - ); - } - } catch (err) { - console.error(err); - sign721PermitVerifyResult.innerHTML = `Error: ${err.message}`; - } - }; - - watchNFTButton.onclick = async () => { - let watchNftsResult; - try { - watchNftsResult = await globalContext.provider.request({ - method: 'wallet_watchAsset', - params: { - type: 'ERC721', - options: { - address: nftsContract.address, - tokenId: watchNFTInput.value, - }, - }, - }); - } catch (error) { - console.error(error); - } - console.log(watchNftsResult); - }; - - approveButton.onclick = async () => { - nftsStatus.innerHTML = 'Approve initiated'; - let result = await nftsContract.approve( - '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', - approveTokenInput.value, - { - from: globalContext.accounts[0], - }, - ); - result = await result.wait(); - console.log(result); - nftsStatus.innerHTML = 'Approve completed'; - }; - - setApprovalForAllButton.onclick = async () => { - nftsStatus.innerHTML = 'Set Approval For All initiated'; - let result = await nftsContract.setApprovalForAll( - '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', - true, - { - from: globalContext.accounts[0], - }, - ); - result = await result.wait(); - console.log(result); - nftsStatus.innerHTML = 'Set Approval For All completed'; - }; - - revokeButton.onclick = async () => { - nftsStatus.innerHTML = 'Revoke initiated'; - let result = await nftsContract.setApprovalForAll( - '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', - false, - { - from: globalContext.accounts[0], - }, - ); - result = await result.wait(); - console.log(result); - nftsStatus.innerHTML = 'Revoke completed'; - }; - - transferFromButton.onclick = async () => { - nftsStatus.innerHTML = 'Transfer From initiated'; - let result = await nftsContract.transferFrom( - globalContext.accounts[0], - '0x2f318C334780961FB129D2a6c30D0763d9a5C970', - transferTokenInput.value, - { - from: globalContext.accounts[0], - }, - ); - result = await result.wait(); - console.log(result); - nftsStatus.innerHTML = 'Transfer From completed'; - }; - - /** - * ERC1155 Token - */ - - deployERC1155Button.onclick = async () => { - erc1155Status.innerHTML = 'Deploying'; - - try { - erc1155Contract = await erc1155Factory.deploy(); - await erc1155Contract.deployTransaction.wait(); - } catch (error) { - erc1155Status.innerHTML = 'Deployment Failed!'; - throw error; - } - - if (erc1155Contract.address === undefined) { - return; - } - - console.log( - `Contract mined! address: ${erc1155Contract.address} transactionHash: ${erc1155Contract.deployTransaction.hash}`, - ); - - erc1155TokenAddresses.innerHTML = erc1155TokenAddresses.innerHTML - .concat(', ', erc1155Contract.address) - .split(', ') - .filter(Boolean) - .join(', '); - - erc1155Status.innerHTML = 'Deployed'; - batchTransferTokenIds.disabled = false; - batchTransferTokenAmounts.disabled = false; - batchMintButton.disabled = false; - batchTransferFromButton.disabled = false; - setApprovalForAllERC1155Button.disabled = false; - revokeERC1155Button.disabled = false; - watchAssetInput.disabled = false; - watchAssetButton.disabled = false; - }; - - batchMintButton.onclick = async () => { - erc1155Status.innerHTML = 'Batch Mint initiated'; - - const params = [ - globalContext.accounts[0], - batchMintTokenIds.value.split(',').map(Number), - batchMintIdAmounts.value.split(',').map(Number), - '0x', - ]; - - let result; - - try { - result = await erc1155Contract.mintBatch(...params); - } catch (error) { - erc1155Status.innerHTML = 'Mint Failed!'; - throw error; - } - - console.log(result); - erc1155Status.innerHTML = 'Batch Minting completed'; - }; - - batchTransferFromButton.onclick = async () => { - erc1155Status.innerHTML = 'Batch Transfer From initiated'; - - const params = [ - globalContext.accounts[0], - '0x2f318C334780961FB129D2a6c30D0763d9a5C970', - batchTransferTokenIds.value.split(',').map(Number), - batchTransferTokenAmounts.value.split(',').map(Number), - '0x', - ]; - - let result; - - try { - result = await erc1155Contract.safeBatchTransferFrom(...params); - } catch (error) { - erc1155Status.innerHTML = 'Transaction Failed!'; - throw error; - } - console.log(result); - erc1155Status.innerHTML = 'Batch Transfer From completed'; - }; - - setApprovalForAllERC1155Button.onclick = async () => { - erc1155Status.innerHTML = 'Set Approval For All initiated'; - let result = await erc1155Contract.setApprovalForAll( - '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', - true, - { - from: globalContext.accounts[0], - }, - ); - result = await result.wait(); - console.log(result); - erc1155Status.innerHTML = 'Set Approval For All completed'; - }; - - revokeERC1155Button.onclick = async () => { - erc1155Status.innerHTML = 'Revoke initiated'; - let result = await erc1155Contract.setApprovalForAll( - '0x9bc5baF874d2DA8D216aE9f137804184EE5AfEF4', - false, - { - from: globalContext.accounts[0], - }, - ); - result = await result.wait(); - console.log(result); - erc1155Status.innerHTML = 'Revoke completed'; - }; - - watchAssetButton.onclick = async () => { - try { - const watchAssetResult = await globalContext.provider.request({ - method: 'wallet_watchAsset', - params: { - type: 'ERC1155', - options: { - address: erc1155Contract.address, - tokenId: watchAssetInput.value, - }, - }, - }); - console.log(watchAssetResult); - } catch (error) { - console.error(error); - } - }; - - /** - * EIP 747 - */ - - eip747WatchButton.onclick = async () => { - eip747Status.innerHTML = 'Adding token...'; - - try { - const result = await globalContext.provider.request({ - method: 'wallet_watchAsset', - params: { - type: 'ERC20', - options: { - address: eip747ContractAddress.value, - symbol: eip747Symbol.value, - decimals: parseInt(eip747Decimals.value, 10), - image: 'https://metamask.github.io/test-dapp/metamask-fox.svg', - }, - }, - }); - eip747Status.innerHTML = 'NFT added successfully'; - console.log(result); - } catch (error) { - eip747Status.innerHTML = - 'There was an error adding the token. See console for details.'; - console.error(error); - } - }; - - /** - * Sending ETH - */ - - sendButton.onclick = async () => { - const result = await globalContext.provider.request({ - method: 'eth_sendTransaction', - params: [ - { - from: globalContext.accounts[0], - to: '0x0c54FcCd2e384b4BB6f2E405Bf5Cbc15a017AaFb', - value: '0x0', - gasLimit: '0x5208', - gasPrice: '0x2540be400', - type: '0x0', - }, - ], - }); - console.log(result); - }; - - sendEIP1559Button.onclick = async () => { - const result = await globalContext.provider.request({ - method: 'eth_sendTransaction', - params: [ - { - from: globalContext.accounts[0], - to: '0x0c54FcCd2e384b4BB6f2E405Bf5Cbc15a017AaFb', - value: '0x0', - gasLimit: '0x5028', - maxFeePerGas: '0x2540be400', - maxPriorityFeePerGas: '0x3b9aca00', - }, - ], - }); - console.log(result); - }; - - sendEIP1559WithoutGasButton.onclick = async () => { - const result = await globalContext.provider.request({ - method: 'eth_sendTransaction', - params: [ - { - from: globalContext.accounts[0], - to: '0x0c54FcCd2e384b4BB6f2E405Bf5Cbc15a017AaFb', - value: '0x0', - }, - ], - }); - console.log(result); - }; - - /** - * ERC20 Token - */ - - createToken.onclick = async () => { - const _initialAmount = 10; - const _tokenName = 'TST'; - - try { - hstContract = await hstFactory.deploy( - _initialAmount, - _tokenName, - decimalUnitsInput.value, - tokenSymbol, - ); - await hstContract.deployTransaction.wait(); - } catch (error) { - erc20TokenAddresses.innerHTML = 'Creation Failed'; - throw error; - } - - if (hstContract.address === undefined) { - return; - } - - console.log( - `Contract mined! address: ${hstContract.address} transactionHash: ${hstContract.deployTransaction.hash}`, - ); - erc20TokenAddresses.innerHTML = erc20TokenAddresses.innerHTML - .concat(', ', hstContract.address) - .split(', ') - .filter(Boolean) - .join(', '); - watchAssets.disabled = false; - transferTokens.disabled = false; - transferFromTokens.disabled = false; - approveTokens.disabled = false; - increaseTokenAllowance.disabled = false; - allowanceOwnerInput.disabled = false; - allowanceSpenderInput.disabled = false; - allowanceAmountResult.disabled = false; - getAllowance.disabled = false; - transferTokensWithoutGas.disabled = false; - approveTokensWithoutGas.disabled = false; - approveTokensToInput.disabled = false; - transferFromSenderInput.disabled = false; - transferFromRecipientInput.disabled = false; - }; - - watchAssets.onclick = async () => { - const contractAddresses = erc20TokenAddresses.innerHTML.split(', '); - - const promises = contractAddresses.map((erc20Address) => { - return globalContext.provider.request({ - method: 'wallet_watchAsset', - params: { - type: 'ERC20', - options: { - address: erc20Address, - symbol: tokenSymbol, - decimals: decimalUnitsInput.value, - image: 'https://metamask.github.io/test-dapp/metamask-fox.svg', - }, - }, - }); - }); - - Promise.all(promises).then((result) => { - console.log('result', result); - }); - }; - - transferTokens.onclick = async () => { - const result = await hstContract.transfer( - '0x2f318C334780961FB129D2a6c30D0763d9a5C970', - decimalUnitsInput.value === '0' - ? 1 - : `${1.5 * 10 ** decimalUnitsInput.value}`, - { from: globalContext.accounts[0] }, - ); - console.log('result', result); - }; - - approveTokens.onclick = async () => { - const result = await hstContract.approve( - approveTokensToInput.value, - `${7 * 10 ** decimalUnitsInput.value}`, - { from: globalContext.accounts[0] }, - ); - console.log('result', result); - }; - - increaseTokenAllowance.onclick = async () => { - const result = await hstContract.increaseAllowance( - approveTokensToInput.value, - `${1 * 10 ** decimalUnitsInput.value}`, - { from: globalContext.accounts[0] }, - ); - console.log('result', result); - }; - - getAllowance.onclick = async () => { - const result = await hstContract.allowance( - allowanceOwnerInput.value, - allowanceSpenderInput.value, - { from: globalContext.accounts[0] }, - ); - const allowance = result.toNumber() / 10 ** decimalUnitsInput.value; - allowanceAmountResult.innerHTML = allowance.toFixed( - decimalUnitsInput.value, - ); - }; - - transferFromTokens.onclick = async () => { - try { - const result = await hstContract.transferFrom( - transferFromSenderInput.value, - transferFromRecipientInput.value, - decimalUnitsInput.value === '0' - ? 1 - : `${1.5 * 10 ** decimalUnitsInput.value}`, - { from: globalContext.accounts[0] }, - ); - console.log('result', result); - tokenMethodsResult.innerHTML = result; - } catch (error) { - tokenMethodsResult.innerHTML = error.message; - } - }; - - transferTokensWithoutGas.onclick = async () => { - const result = await hstContract.transfer( - '0x2f318C334780961FB129D2a6c30D0763d9a5C970', - decimalUnitsInput.value === '0' - ? 1 - : `${1.5 * 10 ** decimalUnitsInput.value}`, - { - gasPrice: '20000000000', - }, - ); - console.log('result', result); - }; - - approveTokensWithoutGas.onclick = async () => { - const result = await hstContract.approve( - '0x2f318C334780961FB129D2a6c30D0763d9a5C970', - `${7 * 10 ** decimalUnitsInput.value}`, - { - gasPrice: '20000000000', - }, - ); - console.log('result', result); - }; - /** * Permissions */ @@ -1954,32 +1226,6 @@ const initializeFormElements = () => { } }; - async function getNFTMsgParams() { - return { - domain: { - name: 'My NFT', - version: '1', - chainId: globalContext.chainIdInt, - verifyingContract: nftsContract.address, - }, - types: { - Permit: [ - { name: 'spender', type: 'address' }, - { name: 'tokenId', type: 'uint256' }, - { name: 'nonce', type: 'uint256' }, - { name: 'deadline', type: 'uint256' }, - ], - }, - primaryType: 'Permit', - message: { - spender: '0x0521797E19b8E274E4ED3bFe5254FAf6fac96F08', - tokenId: '3606393', - nonce: '0', - deadline: '1734995006', - }, - }; - } - /** * Providers */ From 07ebb183943049428c1c84d8f1162bc7ea51940e Mon Sep 17 00:00:00 2001 From: Priya Narayanaswamy Date: Wed, 18 Dec 2024 19:44:53 +0100 Subject: [PATCH 2/3] chore: add index.js to export all modules --- src/index.js | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/src/index.js b/src/index.js index 10ac7d9c..47e6a5f3 100644 --- a/src/index.js +++ b/src/index.js @@ -30,11 +30,13 @@ import { } from './components/signatures'; import { ensResolutionComponent } from './components/resolutions/ens-resolution'; import { sendFormComponent } from './components/forms/send-form'; -import { sendComponent } from './components/transactions/send'; -import { erc20Component } from './components/transactions/erc20'; -import { erc721Component } from './components/transactions/erc721'; -import { erc1155Component } from './components/transactions/erc1155'; -import { eip747Component } from './components/transactions/eip747'; +import { + sendComponent, + erc20Component, + erc1155Component, + eip747Component, + erc721Component, +} from './components/transactions'; const { hstBytecode, From 1dc89e639560b36d6b08c8f3796775536b482eb9 Mon Sep 17 00:00:00 2001 From: Priya Narayanaswamy Date: Wed, 18 Dec 2024 19:48:57 +0100 Subject: [PATCH 3/3] chore: add index.js to export all modules --- src/components/transactions/index.js | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 src/components/transactions/index.js diff --git a/src/components/transactions/index.js b/src/components/transactions/index.js new file mode 100644 index 00000000..f885a52a --- /dev/null +++ b/src/components/transactions/index.js @@ -0,0 +1,5 @@ +export * from './eip747'; +export * from './erc20'; +export * from './erc721'; +export * from './erc1155'; +export * from './send';