diff --git a/src/constants/abi.ts b/src/constants/abi.ts new file mode 100644 index 0000000..2af6593 --- /dev/null +++ b/src/constants/abi.ts @@ -0,0 +1,449 @@ +export default [ + { + anonymous: false, + inputs: [ + { + indexed: true, + internalType: 'address', + name: 'owner', + type: 'address', + }, + { + indexed: true, + internalType: 'address', + name: 'approved', + type: 'address', + }, + { + indexed: true, + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'Approval', + type: 'event', + }, + { + anonymous: false, + inputs: [ + { + indexed: true, + internalType: 'address', + name: 'owner', + type: 'address', + }, + { + indexed: true, + internalType: 'address', + name: 'operator', + type: 'address', + }, + { + indexed: false, + internalType: 'bool', + name: 'approved', + type: 'bool', + }, + ], + name: 'ApprovalForAll', + type: 'event', + }, + { + anonymous: false, + inputs: [ + { + indexed: true, + internalType: 'address', + name: 'previousOwner', + type: 'address', + }, + { + indexed: true, + internalType: 'address', + name: 'newOwner', + type: 'address', + }, + ], + name: 'OwnershipTransferred', + type: 'event', + }, + { + anonymous: false, + inputs: [ + { + indexed: true, + internalType: 'address', + name: 'from', + type: 'address', + }, + { + indexed: true, + internalType: 'address', + name: 'to', + type: 'address', + }, + { + indexed: true, + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'Transfer', + type: 'event', + }, + { + inputs: [ + { + internalType: 'address', + name: 'to', + type: 'address', + }, + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'approve', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'Burn', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'address', + name: 'to', + type: 'address', + }, + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'GTransfer', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'address', + name: 'to', + type: 'address', + }, + { + internalType: 'bytes', + name: 'signature', + type: 'bytes', + }, + ], + name: 'Mint', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [], + name: 'renounceOwnership', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'address', + name: 'from', + type: 'address', + }, + { + internalType: 'address', + name: 'to', + type: 'address', + }, + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'safeTransferFrom', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'address', + name: 'from', + type: 'address', + }, + { + internalType: 'address', + name: 'to', + type: 'address', + }, + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + { + internalType: 'bytes', + name: 'data', + type: 'bytes', + }, + ], + name: 'safeTransferFrom', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'address', + name: 'operator', + type: 'address', + }, + { + internalType: 'bool', + name: 'approved', + type: 'bool', + }, + ], + name: 'setApprovalForAll', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'address', + name: 'from', + type: 'address', + }, + { + internalType: 'address', + name: 'to', + type: 'address', + }, + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'transferFrom', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'address', + name: 'newOwner', + type: 'address', + }, + ], + name: 'transferOwnership', + outputs: [], + stateMutability: 'nonpayable', + type: 'function', + }, + { + inputs: [ + { + internalType: 'string', + name: 'tokenName', + type: 'string', + }, + { + internalType: 'string', + name: 'tokenSymbol', + type: 'string', + }, + ], + stateMutability: 'nonpayable', + type: 'constructor', + }, + { + inputs: [ + { + internalType: 'address', + name: 'owner', + type: 'address', + }, + ], + name: 'balanceOf', + outputs: [ + { + internalType: 'uint256', + name: '', + type: 'uint256', + }, + ], + stateMutability: 'view', + type: 'function', + }, + { + inputs: [ + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'getApproved', + outputs: [ + { + internalType: 'address', + name: '', + type: 'address', + }, + ], + stateMutability: 'view', + type: 'function', + }, + { + inputs: [ + { + internalType: 'address', + name: 'owner', + type: 'address', + }, + { + internalType: 'address', + name: 'operator', + type: 'address', + }, + ], + name: 'isApprovedForAll', + outputs: [ + { + internalType: 'bool', + name: '', + type: 'bool', + }, + ], + stateMutability: 'view', + type: 'function', + }, + { + inputs: [], + name: 'name', + outputs: [ + { + internalType: 'string', + name: '', + type: 'string', + }, + ], + stateMutability: 'view', + type: 'function', + }, + { + inputs: [], + name: 'owner', + outputs: [ + { + internalType: 'address', + name: '', + type: 'address', + }, + ], + stateMutability: 'view', + type: 'function', + }, + { + inputs: [ + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'ownerOf', + outputs: [ + { + internalType: 'address', + name: '', + type: 'address', + }, + ], + stateMutability: 'view', + type: 'function', + }, + { + inputs: [ + { + internalType: 'bytes4', + name: 'interfaceId', + type: 'bytes4', + }, + ], + name: 'supportsInterface', + outputs: [ + { + internalType: 'bool', + name: '', + type: 'bool', + }, + ], + stateMutability: 'view', + type: 'function', + }, + { + inputs: [], + name: 'symbol', + outputs: [ + { + internalType: 'string', + name: '', + type: 'string', + }, + ], + stateMutability: 'view', + type: 'function', + }, + { + inputs: [ + { + internalType: 'uint256', + name: 'tokenId', + type: 'uint256', + }, + ], + name: 'tokenURI', + outputs: [ + { + internalType: 'string', + name: '', + type: 'string', + }, + ], + stateMutability: 'view', + type: 'function', + }, +]; diff --git a/src/pages/Nft/NftToken/List/components/AddNftModel.tsx b/src/pages/Nft/NftToken/List/components/AddNftModel.tsx index 5c71ffc..33d3268 100644 --- a/src/pages/Nft/NftToken/List/components/AddNftModel.tsx +++ b/src/pages/Nft/NftToken/List/components/AddNftModel.tsx @@ -3,10 +3,10 @@ import { createForm } from '@formily/core'; import { createSchemaField } from '@formily/react'; import Modal, { ModalProps } from '@/components/Modal'; import { Form, FormItem, Input, NumberPicker } from '@formily/antd'; -import { Button } from 'antd'; -import { initWeb3, NFTMint } from '@/utils/web3'; +import { Button, message } from 'antd'; +import { initWeb3, NFTMint, web3 } from '@/utils/web3'; import { getContractInfo } from '@/services/contract'; -import { getNFTContractList, mintNFT } from '@/services/nft'; +import { checkAssetID, getNFTContractList, getSignature, mintNFT } from '@/services/nft'; import { ContractType } from '@/constants/enum/contract'; interface AddNftModalPropsType extends ModalProps { @@ -29,23 +29,39 @@ const AddNftModal = ({ onOk, onCancel, ...rest }: AddNftModalPropsType) => { const handleOk = async () => { form.submit(async () => { - setLoading(true); const formState = form.getFormState(); - await initWeb3(); - const contractInfo = await getContractInfo({ erc: ContractType.NFT721 }); - const res = await getNFTContractList(); - const tx_hash = await NFTMint({ - abi: contractInfo.abi, - address: res.items[0].address, - toAddress: formState.values.toAddress, - name: formState.values.name, - }); - formState.values.tx_hash = tx_hash; - await mintNFT(formState.values); - setLoading(false); - onOk(); + await checkAssetID({ assetid: formState.values.assetid }); + setLoading(true); + const isInit = await initWeb3(); + if (isInit) { + const contractInfo = (await getContractInfo({ erc: ContractType.NFT721 })) as any; + const res = (await getNFTContractList()) as any; + const signature = (await getSignature({ address: web3.eth.defaultAccount })) as any; + console.log('signature = ', signature); + let tx_hash = ''; + try { + tx_hash = await NFTMint({ + abi: contractInfo.abi, + address: res.items[0].address, + toAddress: formState.values.address, + sign: signature, + }); + } catch (error) { + setLoading(false); + message.error('创建失败'); + onCancel(); + return; + } + formState.values.tx_hash = tx_hash; + await mintNFT(formState.values); + setLoading(false); + onOk(); + } else { + setLoading(false); + } }); }; + const handleCancel = () => { onCancel(); }; @@ -62,40 +78,20 @@ const AddNftModal = ({ onOk, onCancel, ...rest }: AddNftModalPropsType) => { 确认 , ]} + onCancel={handleCancel} {...rest} >
- - - void; onOk: () => void; + onCancel: () => void; } const SchemaField = createSchemaField({ @@ -40,8 +40,8 @@ const AddAccountModal = ({ onOk, onCancel, ...rest }: AddAccountModalPropsType) const form = createForm({ effects: () => { UseAsyncDataSource('role', async (field) => { - const list = roleListData; - const option = []; + const list = roleListData as any; + const option = [] as any; for (let index = 0; index < list.items.length; index++) { const element = list.items[index]; const item = { diff --git a/src/services/nft.ts b/src/services/nft.ts index b3ac4fd..2f9f4c7 100644 --- a/src/services/nft.ts +++ b/src/services/nft.ts @@ -72,6 +72,34 @@ export const mintNFT = (data) => { }); }; +/** + * getSignature + * @param {object} data + * + * @returns {array} data + */ +export const getSignature = (data) => { + return request.request({ + url: '/nft/sign/get', + method: 'post', + data, + }); +}; + +/** + * mintNFT + * @param {object} data + * + * @returns {array} data + */ +export const checkAssetID = (data) => { + return request.request({ + url: '/nft/assetid/check', + method: 'post', + data, + }); +}; + /** * 更新NFT信息 * @param {object} data diff --git a/src/utils/web3.ts b/src/utils/web3.ts index 55cb8c8..5fa44fd 100644 --- a/src/utils/web3.ts +++ b/src/utils/web3.ts @@ -2,6 +2,7 @@ import Web3 from 'web3'; import detectEthereumProvider from '@metamask/detect-provider'; import { message } from 'antd'; import BigNumber from 'bignumber.js'; +import abi from '@/constants/abi'; let provider: any; @@ -70,7 +71,7 @@ export async function transfer(abi: string, address: string, toAddress: string) const contract = new web3.eth.Contract(eval('(' + abi + ')'), address); await contract.methods .transfer(toAddress, new BigNumber(1 * Math.pow(10, 18))) - .send({ from: web3.eth.defaultAccount }, function (error, transactionHash) { + .send({ from: web3.eth.defaultAccount, gas: 3000000 }, function (error, transactionHash) { if (!error) { console.log('transactionHash is ' + transactionHash); } else { @@ -85,6 +86,7 @@ export async function transfer(abi: string, address: string, toAddress: string) * @param abi 合约ABI * @param address 合约地址 * @param toAddress 转账地址 + * @param sign 签名 */ export async function NFTMint(params: any) { @@ -94,12 +96,13 @@ export async function NFTMint(params: any) { let tx_hash = ''; const contract = new web3.eth.Contract(eval('(' + params.abi + ')'), params.address); await contract.methods - .Mint(params.toAddress) - .send({ from: web3.eth.defaultAccount }, function (error, transactionHash) { + .Mint(params.toAddress, params.sign) + .send({ from: web3.eth.defaultAccount, gas: 3000000 }, function (error, transactionHash) { if (!error) { tx_hash = transactionHash; } else { - console.log(error); + console.log('error = ', error); + return tx_hash; } }); return tx_hash;