bitcoin 签名 message(sign message)

2022-3-29

Bitcoin 签名 message (sign message)

最近在做所有链的msg的签名,这里记录一下btc的sign message

需要用到的库

const bitcoin = require('bitcoinjs-lib')
const network = bitcoin.networks.bitcoin
const bip39 = require('bip39');
const ecc = require('tiny-secp256k1');
const { BIP32Factory } = require('bip32');
const bip32 = BIP32Factory(ecc)

同样,btc是使用bip39生成的助记词。

const mnemonic = bip39.generateMnemonic()

至于从助记词生成私钥,地址等

const mnemonic = 'hawk pepper almost brother forward plastic wisdom cotton volume attitude road shuffle'
const seed = bip39.mnemonicToSeedSync(mnemonic)
const rootKey = bip32.fromSeed(seed)

const path = "m/44'/0'/0'/0/0"; // bip44
const childKey = rootKey.derivePath(path);
// 看一下 p2pkh 格式的地址
const address = bitcoin.payments.p2pkh({ pubkey: childKey.publicKey, network }).address
// wif,一般钱包都是用的wif, 不使用childKey.privateKey
const wif = childKey.toWIF()

签名message,需要先对message进行处理,再用secp256k1 进行签名,为什么不直接使用childKey.sign 或者说是tiny-secp256k1的sign?因为childKey.sign不返回recovery,只是返回一个signature

const secp256k1 = require('secp256k1')
const message = 'youyouyouyouyouyouyouyouyouyouyo'

// magicHashMessage
const messageVISize = message.length < 0xfd ? 1 : message.length <= 0xfff ? 3 : message.length <= 0xffffffff ? 5 : 9
const newMessage = childKey.network.messagePrefix + new Array(messageVISize).fill(' ').join('') + message
const hash = bitcoin.crypto.hash256(Buffer.from(newMessage))
const sigObj = secp256k1.sign(hash, childKey.privateKey)
const recovery = 27 + sigObj.recovery + (childKey.compressed ? 4 : 0)
const result = Buffer.concat([Buffer.alloc(1, recovery), sigObj.signature])
console.log({result: result.toString('base64')});
//{
//  result: 'IFgldZkuldmxjksF6SXAzpz4660R2Ea95Qth68Y79sV/AWexGisvQ/wvLKHXlOT7JY1lrIQLTYYObxCNCyZIm7c='
//} 
//

评论区