我需要创建一个比特币家族文本签名工具。
研究这个问题后,我找到了NBitcoin包并用它实现了以下代码:
using System;
using System.Data;
using System.Text;
using NBitcoin;
using NBitcoin.Crypto;
using NBitcoin.DataEncoders;
class Program
{
static void Main(string[] args)
{
var privateKey = new Key();
var bitcoinPrivateKey = privateKey.GetWif(Network.Main);
var bitcoinPublicKey = bitcoinPrivateKey.PubKey;
var address = bitcoinPublicKey.GetAddress(ScriptPubKeyType.Segwit, Network.Main);
Console.WriteLine(address);
var message = "test";
byte[] messageBytes = Encoding.UTF8.GetBytes(message);
uint256 hash = new uint256(Hashes.SHA256(messageBytes));
var signature = privateKey.Sign(hash);
var signatureBytes = signature.ToDER();
string signatureBase64 = Encoders.Base64.EncodeData(signatureBytes);
Console.WriteLine("Signature: " + signatureBase64);
}
}
但由于某种原因,生成的签名对于 https://www.verifybitcoinmessage.com/
无效**更新了
根据chatgpt,我需要使用
Bitcoin Message Signing
标准签署消息
static void Main(string[] args)
{
var privateKey = new Key();
var bitcoinPrivateKey = privateKey.GetWif(Network.Main);
var bitcoinPublicKey = bitcoinPrivateKey.PubKey;
var address = bitcoinPublicKey.GetAddress(ScriptPubKeyType.Legacy, Network.Main);
Console.WriteLine("Address: " + address);
var message = "test";
// Sign the message using the Bitcoin Message Signing standard
string signatureBase64 = SignBitcoinMessage(privateKey, message);
Console.WriteLine("Signature: " + signatureBase64);
}
/// <summary>
/// Signs a message using the Bitcoin Message Signing standard.
/// This method prepares the message with the appropriate prefix and length encoding,
/// hashes it twice with SHA-256, and then signs it using the provided private key.
/// The resulting signature is returned in Base64 format.
/// </summary>
/// <param name="privateKey">The private key to sign the message with.</param>
/// <param name="message">The message to be signed.</param>
/// <returns>A Base64 encoded signature of the message.</returns>
static string SignBitcoinMessage(Key privateKey, string message)
{
byte[] messageBytes = Encoding.UTF8.GetBytes(message);
// Structure for the message in Bitcoin Signed Message format
byte[] prefixBytes = Encoding.UTF8.GetBytes("Bitcoin Signed Message:\n");
byte[] lengthBytes = new VarInt((ulong)messageBytes.Length).ToBytes();
byte[] fullMessage = new byte[prefixBytes.Length + lengthBytes.Length + messageBytes.Length];
Buffer.BlockCopy(prefixBytes, 0, fullMessage, 0, prefixBytes.Length);
Buffer.BlockCopy(lengthBytes, 0, fullMessage, prefixBytes.Length, lengthBytes.Length);
Buffer.BlockCopy(messageBytes, 0, fullMessage, prefixBytes.Length + lengthBytes.Length, messageBytes.Length);
// Double SHA-256 hashing
uint256 hash = new uint256(Hashes.SHA256(Hashes.SHA256(fullMessage)));
ECDSASignature signature = privateKey.Sign(hash);
// Serialize and format the signature
var sigBytes = signature.ToCompact();
byte[] fullSignature = new byte[sigBytes.Length + 1];
fullSignature[0] = (byte)(27 + 4 + (privateKey.PubKey.IsCompressed ? 4 : 0)); // Include key flag
Buffer.BlockCopy(sigBytes, 0, fullSignature, 1, sigBytes.Length);
return Encoders.Base64.EncodeData(fullSignature);
}
但这也没有帮助
我使用了错误的软件包。 正确的包是NBitcoin-std2
using NBitcoin;
Key Key = new Key(); //Create private key
//We can take private key
var privateKey = Key.GetBitcoinSecret(Network.Main);
//Get the public key, and derive the address on the Main network
BitcoinAddress address = privateKey.PubKey.GetAddress(ScriptPubKeyType.Segwit, Network.Main);
Console.WriteLine("Address:" + address + "\n");
//For the sign to data , create secret object.
BitcoinSecret secret = new BitcoinSecret(Key, Network.Main);
string message = $"test";
Console.WriteLine("Message:" + message + "\n");
//sign message with private key.
string signature = secret.PrivateKey.SignMessage(message);
Console.WriteLine("Signature:" + signature + "\n");