比特币交易交易(transaction)交易的互相关联:

资讯 6个月前 manoon
0

比特币交易

交易是比特币的核心,区块链的唯一目的就是安全可靠地存储交易。在区块链中,一旦交易被创建,任何人都不能修改或删除它。

对于每笔新交易,它的输入会引用(reference)上一笔交易的输出(这里有一个例外,coinbase 交易),而reference意味着支出。所谓前一个输出的报价,即前一个输出包含在另一笔交易的输入中,就是花费前的交易输出。交易的输出是硬币实际存储的地方。下图说明了事务之间的互连:

比特币交易交易(transaction)交易的互相关联:

注意:

某些输出未连接到某个输入

比特币交易交易(transaction)交易的互相关联:

一笔交易的输入可以参考之前多笔交易的输出

输入必须引用输出

在本文中,我们将使用“钱”、“硬币”、“花费”、“发送”、“帐户”等词。但在比特币中,没有这样的概念。一个交易只是一个锁定某些值的脚本,而这些值只能由锁定它们的人解锁

每笔比特币交易都会创建一个输出,输出将被区块链记录。将比特币发送给某人实际上意味着创建一个新的 UTXO 并将其注册到该人的地址,他可以使用该地址。

比特币交易交易(transaction)交易的互相关联:

交易的主要功能:

 func (cli *CLI) send(from, to string, amount int, nodeID string, mineNow bool) { if !ValidateAddress(from) { log.Panic("ERROR: Sender address is not valid") } if !ValidateAddress(to) { log.Panic("ERROR: Recipient address is not valid") } bc := NewBlockchain(nodeID)    //获取区块链实例 UTXOSet := UTXOSet{bc}    //创建UTXO集 defer bc.Db.Close() wallets, err := NewWallets(nodeID) if err != nil { log.Panic(err) } wallet := wallets.GetWallet(from) tx := NewUTXOTransaction(&wallet, to, amount, &UTXOSet) if mineNow { cbTx := NewCoinbaseTX(from, "") txs := []*Transaction{cbTx, tx} newBlock := bc.MineBlock(txs) UTXOSet.Update(newBlock) } else { sendTx(knownNodes[0], tx) } fmt.Println("Success!") }

我们从头分析整个交易过程,先用方法判断输入的地址是否是有效的比特币地址,然后从我们的blotDB数据库中获取区块链实例(我们用一个数据库来存储区块链数据,读者可以忽略)这里),读取数据库的代码如下

 func NewBlockchain(nodeID string) *Blockchain { dbFile := fmt.Sprintf(dbFile, nodeID) if dbExists(dbFile) == false { fmt.Println("No existing blockchain found. Create one first.") os.Exit(1) } var tip []byte db, err := bolt.Open(dbFile, 0600, nil)    //打开数据库 if err != nil { log.Panic(err) } err = db.Update(func(tx *bolt.Tx) error { b := tx.Bucket([]byte(blocksBucket)) tip = b.Get([]byte("l"))  //读取最新的区块链 return nil }) if err != nil { log.Panic(err) } bc := Blockchain{tip, db} return &bc }

比特币交易交易(transaction)交易的互相关联:

我们区块链的基本原型是

 type Blockchain struct { tip []byte Db  *bolt.DB } type Block struct { Timestamp     int64 Transactions  []*Transaction PrevBlockHash []byte Hash          []byte Nonce         int Height        int }

获取区块链实例后,我们创建一个utxo集合,其数据结构为

 type UTXOSet struct { Blockchain *Blockchain }

比特币交易交易(transaction)交易的互相关联:

然后我们从钱包文件中获取我们的钱包集合(wallets),然后调用我们的转账函数。

 func NewUTXOTransaction(wallet *Wallet, to string, amount int, UTXOSet *UTXOSet) *Transaction { var inputs []TXInput var outputs []TXOutput pubKeyHash := HashPubKey(wallet.PublicKey) acc, validOutputs := UTXOSet.FindSpendableOutputs(pubKeyHash, amount)    //找到能够使用的输出 if acc  amount { outputs = append(outputs, *NewTXOutput(acc-amount, from)) // a change    //找零输出 } tx := Transaction{nil, inputs, outputs} tx.ID = tx.Hash()    //创建一笔交易 UTXOSet.Blockchain.SignTransaction(&tx, wallet.PrivateKey)       //对交易签名 return &tx }

对于一个事务,它的数据结构是

 type Transaction struct { ID   []byte Vin  []TXInput Vout []TXOutput } type TXInput struct { Txid      []byte Vout      int Signature []byte PubKey    []byte } type TXOutput struct { Value      int PubKeyHash []byte } type UTXOSet struct { Blockchain *Blockchain }

对于一笔交易,输出主要由两部分组成:一定数量的比特币(Value)和一个锁定脚本(ScriptPubKey)。要花这笔钱,必须解锁脚本。一个输入是指前一个交易的一个输出:Txid 存储了前一个交易的 ID,Vout 存储了该交易中输出的所有输出的索引(因为一个交易可能有多个输出,你需要有信息表明具体是)Signature是签名比特币交易教程,Pubkey是公钥比特币交易教程,两者都保证用户不能花费属于他人的币。

func HashPubKey(pubKey []byte) []byte {// RIPEMD160(SHA256(PubKey)) publicSHA256 := sha256.Sum256(pubKey) RIPEMD160Hasher :=ripemd160.New() _, err: = RIPEMD160Hasher.Write(publicSHA256[:]) if err != nil {log.Panic(err)} publicRIPEMD160 := RIPEMD160Hasher.Sum(nil) return publicRIPEMD160} func (u UTXOSet) FindSpendableOutputs(pubkeyHash) [] (int, map[string][]int) {unspentOutputs := make(map[string][]int)//开辟一个内存空间用于累积输出 := 0 db := u.Blockchain.db//获取访问权限区块链数据库 err := db.View(func(tx *bolt.Tx) error {//读取数据库 b := tx.Bucket([]byte(utxoBucket)) c := b.Cursor() for k, v : = c.First(); k != nil; k, v = c.Next() {//遍历数据库txID := hex.EncodeToString(k) outs := DeserializeOutputs(v) for outIdx, out := range outs.Outputs {如果出来。IsLockedWithKey(pubkeyHash) && 累积

在创建新的输出时,我们必须找到所有花费的输出,并确保它们具有足够的价值(value)。这就是 FindSpendableOutputs 所做的。然后,对于找到的每个输出,都会创建一个引用。输出输入。接下来,我们创建两个输出:

一个被收件人的地址锁定。这是到其他地址的实际转账

以上就是教大家使用go语言详细实现比特币交易功能(Transaction)。更多资讯请关注html中文网其他相关文章!

版权声明:manoon 发表于 2021-11-10 20:57:10。
转载请注明:比特币交易交易(transaction)交易的互相关联: | 198区块链导航

暂无评论

暂无评论...