在以太坊中签名和验证消息



我正在尝试在这里遵循本教程:

但是在教程中,他没有指定如何实现合约。所以我尝试用松露和甘纳许-cli来做。在松露测试中,我尝试使用以下代码:

const amount = web3.toWei(5, 'ether');
const Contract = await GmsPay.new({from : Sender, value : web3.toWei(10, 'ether')});
const hash = Web3Beta.utils.soliditySha3(
{t : 'address', v : Recipient},
{t : 'uint256', v : amount},
{t : 'uint256', v : 1},
{t : 'address', v : Contract.address}
);
const sig = await Web3Beta.eth.sign(hash, Sender);
const res = await Contract.claimPayment(amount, 1, sig, {from : Recipient});

但我只是不断得到,"错误:处理事务时的虚拟机异常:还原"。使用调试器,我看到我的代码执行到:

require(recoverSigner(message, sig) == owner);

即使我把那行去掉,最后一行仍然不起作用。我做错了什么?任何帮助将不胜感激。

在我的松露测试中遇到了类似的挑战,使用"recoverSigner(message, sig( == owner"检查。在比较了 R,S,V,SOLIDITY RECOVERSigner(( 函数中生成的值与使用 ethereumjs-util 的 fromRpcSig(( 函数在测试端生成的相同值后,我意识到 recoverSigner 将 V 作为 0 返回,而 fromRpcSig 的这个值为 27。这一行提供了有效的答案。

最终的 splitSignature(( 函数包含在下面,如果您遇到类似的问题。

function splitSignature(bytes memory sig)
internal
pure
returns (uint8, bytes32, bytes32)
{
require(sig.length == 65);
bytes32 r;
bytes32 s;
uint8 v;
assembly {
// first 32 bytes, after the length prefix
r := mload(add(sig, 32))
// second 32 bytes
s := mload(add(sig, 64))
// final byte (first byte of the next 32 bytes)
v := byte(0, mload(add(sig, 96)))
}
// support both versions of `eth_sign` responses
if (v < 27) 
v += 27;
return (v, r, s);
}

最新更新