gpt4 book ai didi

ethereum - 在智能合约中使用 _hashTypedDataV4 并在前端使用 _signTypedData(etherjs) 无效

转载 作者:行者123 更新时间:2023-12-05 08:03:39 38 4
gpt4 key购买 nike

我正尝试在前端使用 _signTypedData(etherjs) 对 nft 数据进行编码,如下所示

 const domain = {
name: "og-nft",
version: "1",
};
const types = {
Nft: [
{ name: "URI", type: "string" },
{ name: "price", type: "uint256" },
],
};

// The data to sign
const [voucher, setVoucher] = useState({
URI: "",
price: '1',
});
const signature = await signer._signTypedData(domain, types, voucher);

引用以上 _signTypedData in docs

我将凭证和签名存储在 mongo 数据库中,我在 hardhat 上部署了智能合约,我通过使用 ECDSA.recover 查看凭证的签名者来验证签名的真实性

function verifyVoucher(NFTVoucher calldata voucher, bytes memory signature)
public
view
returns (address)
{
require(voucher.price > 0, "Price must be greater than 0");
// require(voucher.tokenId > 0, "Token ID must be greater than 0");
bytes32 hash = _hash(voucher);
//string memory hash="";
return ECDSA.recover(hash, signature);
}

但此结果与实际签名者不匹配。我想我在上面使用的哈希函数中犯了一些错误。

0xe8c795f9168269940b31a470ad82e89a453e88b9 signer
0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266 owner

下面是哈希函数。

function _hash(NFTVoucher calldata voucher)
internal
view
returns (bytes32)
{
return
_hashTypedDataV4(
keccak256(
abi.encode(
keccak256(
"Nft(string URI,uint256 price)"
),
keccak256(bytes(voucher.URI)),
voucher.price
)
)
);
}

引用以上_hashTypedDataV4

最佳答案

这是erc20permit的例子,希望对你有帮助

function permit(address owner, address spender, uint256 amount, uint256 deadline, uint8 v, bytes32 r, bytes32 s) public virtual override {
require(deadline >= block.timestamp, "ERC20Permit: expired deadline");

bytes32 hashStruct = keccak256(
abi.encode(
keccak256("Permit(address owner,address spender,uint256 value,uint256 nonce,uint256 deadline)"),
owner,
spender,
amount,
nonce[owner],
deadline
)
);

bytes32 hash = keccak256(
abi.encodePacked(
'\x19\x01',
keccak256(abi.encode( keccak256("EIP712Domain(string name,string version,uint256 chainId,address verifyingContract)"),
keccak256(bytes(name_)),
keccak256(bytes(version())),
chainId,
address(this)
),
hashStruct
)
);


address signer = ecrecover(hash, v, r, s);
require(
signer != address(0) && signer == owner,
"ERC20Permit: invalid signature"
);
nonces[owner]++;
_approve(owner, spender, amount);
}

关于ethereum - 在智能合约中使用 _hashTypedDataV4 并在前端使用 _signTypedData(etherjs) 无效,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/71732049/

38 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com