package main
import (
"bytes"
"crypto/ecdsa"
"fmt"
"github.com/ethereum/go-ethereum/common/hexutil"
"github.com/ethereum/go-ethereum/crypto"
)
func main() {
hexPrivateKey := "0xae78c8b502571dba876742437f8bc78b689cf8518356c0921393d89caaf284ce"
dataToSign := "bou"
privateKey, err := crypto.HexToECDSA(hexPrivateKey[2:])
if err != nil {
log.Fatal(err)
}
// keccak256 hash of the data
dataBytes := []byte(dataToSign)
hashData := crypto.Keccak256Hash(dataBytes)
signatureBytes, err := crypto.Sign(hashData.Bytes(), privateKey)
if err != nil {
log.Fatal(err)
}
signature = hexutil.Encode(signatureBytes)
fmt.Println(signature) // 0xc83d417a3b99535e784a72af0d9772c019c776aa0dfe4313c001a5548f6cf254477f5334c30da59531bb521278edc98f1959009253dda4ee9f63fe5562ead5aa00
}
const hexPrivateKey = "0xae78c8b502571dba876742437f8bc78b689cf8518356c0921393d89caaf284ce";
const signingKey = new ethers.utils.SigningKey(hexPrivateKey);
const signature = signingKey.signDigest(ethers.utils.id("bou"));
//{ r: '0xc83d417a3b99535e784a72af0d9772c019c776aa0dfe4313c001a5548f6cf254',
// s: '0x477f5334c30da59531bb521278edc98f1959009253dda4ee9f63fe5562ead5aa',
// _vs: '0x477f5334c30da59531bb521278edc98f1959009253dda4ee9f63fe5562ead5aa',
// recoveryParam: 0,
// v: 27 }
ethers.utils.joinSignature(signature);
// "0xc83d417a3b99535e784a72af0d9772c019c776aa0dfe4313c001a5548f6cf254477f5334c30da59531bb521278edc98f1959009253dda4ee9f63fe5562ead5aa1b"
As we see:
- Go result:
0xc83d417a3b99535e784a72af0d9772c019c776aa0dfe4313c001a5548f6cf254477f5334c30da59531bb521278edc98f1959009253dda4ee9f63fe5562ead5aa00
signingKey.signDigest
result:0xc83d417a3b99535e784a72af0d9772c019c776aa0dfe4313c001a5548f6cf254477f5334c30da59531bb521278edc98f1959009253dda4ee9f63fe5562ead5aa1b
Their last one byte are different: 00 (Go) / 1b (signingKey.signDigest)
I don't know what went wrong that made them different.
https://github.com/ethers-io/ethers.js/issues/823#issuecomment-1692766895
Why joinSignature must return 0x1c
or 0x1b
?