sign.js 1.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647
  1. function toEthSignedMessageHash(messageHex) {
  2. const messageBuffer = Buffer.from(messageHex.substring(2), 'hex');
  3. const prefix = Buffer.from(`\u0019Ethereum Signed Message:\n${messageBuffer.length}`);
  4. return web3.utils.sha3(Buffer.concat([prefix, messageBuffer]));
  5. }
  6. /**
  7. * Create a signer between a contract and a signer for a voucher of method, args, and redeemer
  8. * Note that `method` is the web3 method, not the truffle-contract method
  9. * @param contract TruffleContract
  10. * @param signer address
  11. * @param redeemer address
  12. * @param methodName string
  13. * @param methodArgs any[]
  14. */
  15. const getSignFor =
  16. (contract, signer) =>
  17. (redeemer, methodName, methodArgs = []) => {
  18. const parts = [contract.address, redeemer];
  19. const REAL_SIGNATURE_SIZE = 2 * 65; // 65 bytes in hexadecimal string length
  20. const PADDED_SIGNATURE_SIZE = 2 * 96; // 96 bytes in hexadecimal string length
  21. const DUMMY_SIGNATURE = `0x${web3.utils.padLeft('', REAL_SIGNATURE_SIZE)}`;
  22. // if we have a method, add it to the parts that we're signing
  23. if (methodName) {
  24. if (methodArgs.length > 0) {
  25. parts.push(
  26. contract.contract.methods[methodName](...methodArgs.concat([DUMMY_SIGNATURE]))
  27. .encodeABI()
  28. .slice(0, -1 * PADDED_SIGNATURE_SIZE),
  29. );
  30. } else {
  31. const abi = contract.abi.find(abi => abi.name === methodName);
  32. parts.push(abi.signature);
  33. }
  34. }
  35. // return the signature of the "Ethereum Signed Message" hash of the hash of `parts`
  36. const messageHex = web3.utils.soliditySha3(...parts);
  37. return web3.eth.sign(messageHex, signer);
  38. };
  39. module.exports = {
  40. toEthSignedMessageHash,
  41. getSignFor,
  42. };