Last active
December 15, 2022 09:52
-
-
Save Theo6890/938beafe9890406bcb65163340c3fb48 to your computer and use it in GitHub Desktop.
Sign message with etherjs using following ethereum format signature EIP-1271. If your signature contains complex data follow the EIP-712 to structure your signature & hash: this will allow end users to see the data they sign instead of an incomprehensible bytes32. For safe signatures follow these recommendations https://swcregistry.io/docs/SWC-121
This file contains hidden or 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
const { ethers } = require('ethers'); | |
/** | |
* @notice Path to where your .env file is. If the .env is at the root of your project, | |
* you can simply write `require('dotenv').config()` | |
*/ | |
require('dotenv').config({ path: '../../.env' }); | |
async function main() { | |
// instanciation can also be done using a private key | |
const wallet = new ethers.Wallet.fromMnemonic(process.env.SEED); | |
// by default the address at index 0 is used | |
walletAddr = await wallet.getAddress(); | |
console.log('walletAddr: ', walletAddr); | |
/// @dev in solidity this will be written: `bytes memory rawEncodedMsg = abi.encode(param1, param2, ...)` | |
const rawEncodedMsg = ethers.utils.defaultAbiCoder.encode( | |
['uint256', 'uint256', 'address', 'address', 'uint256', 'uint256'], | |
[ | |
parseInt(process.env.ID), | |
ethers.BigNumber.from(process.env.AMOUNT), | |
process.env.FROM, | |
process.env.TO, | |
parseInt(process.env.TIMESTAMP), | |
parseInt(process.env.CHAIN_ID), | |
] | |
); | |
/** | |
* @dev Create the hash of the original message. | |
* In solidity this will be written: `bytes32 hash = keccak256(rawEncodedMsg)` | |
*/ | |
const encodedMessage = ethers.utils.keccak256(rawEncodedMsg); | |
/** | |
* @dev If only a bytes32 is needed we can encode the message in one line (like below), | |
* using: `ethers.utils.solidityKeccak256` | |
*/ | |
console.log('raw encoded msg: ', rawEncodedMsg); | |
console.log('encoded msg: ', encodedMessage); | |
/** | |
* @dev Equivalent of OpenZeppelin: ECDSA.toEthSignedMessageHash(bytes memory s), which is: | |
* `keccak256(abi.encodePacked("\x19Ethereum Signed Message:\n", Strings.toString(s.length), s));` | |
*/ | |
let ethSignedMessageHash = ethers.utils.solidityKeccak256( | |
['string', 'string', 'bytes'], | |
[ | |
'\x19Ethereum Signed Message:\n', | |
ethers.utils.hexDataLength(rawEncodedMsg).toString(), | |
rawEncodedMsg, | |
] | |
); | |
console.log('ethSignedMessageHash: ', ethSignedMessageHash); | |
// etherjs specific format requirements for signature | |
let messageHashBytes = ethers.utils.arrayify(rawEncodedMsg); | |
/// @dev equivalent of: ethereum.request({method: 'personal_sign', params: [walletAddr, messageHash]}) | |
let signature = await wallet.signMessage(messageHashBytes); | |
console.log('signature: ', signature); | |
///@dev Pass r,s & v in Rewards contract | |
console.log('v: ', ethers.utils.splitSignature(signature).v); | |
console.log('r: ', ethers.utils.splitSignature(signature).r); | |
console.log('s: ', ethers.utils.splitSignature(signature).s); | |
} | |
main().then(console.log).catch(console.error); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment