github.com/bytom/bytom@v1.1.2-0.20221014091027-bbcba3df6075/protocol/bc/tx.go (about) 1 package bc 2 3 import ( 4 "github.com/bytom/bytom/crypto/sha3pool" 5 "github.com/bytom/bytom/errors" 6 ) 7 8 // Convenience routines for accessing entries of specific types by ID. 9 var ( 10 ErrEntryType = errors.New("invalid entry type") 11 ErrMissingEntry = errors.New("missing entry") 12 ) 13 14 // Tx is a wrapper for the entries-based representation of a transaction. 15 type Tx struct { 16 *TxHeader 17 ID Hash 18 Entries map[Hash]Entry 19 InputIDs []Hash // 1:1 correspondence with TxData.Inputs 20 21 SpentOutputIDs []Hash 22 } 23 24 // SigHash ... 25 func (tx *Tx) SigHash(n uint32) (hash Hash) { 26 hasher := sha3pool.Get256() 27 defer sha3pool.Put256(hasher) 28 29 tx.InputIDs[n].WriteTo(hasher) 30 tx.ID.WriteTo(hasher) 31 hash.ReadFrom(hasher) 32 return hash 33 } 34 35 // OriginalOutput try to get the output entry by given hash 36 func (tx *Tx) OriginalOutput(id Hash) (*OriginalOutput, error) { 37 e, ok := tx.Entries[id] 38 if !ok || e == nil { 39 return nil, errors.Wrapf(ErrMissingEntry, "id %x", id.Bytes()) 40 } 41 42 o, ok := e.(*OriginalOutput) 43 if !ok { 44 return nil, errors.Wrapf(ErrEntryType, "entry %x has unexpected type %T", id.Bytes(), e) 45 } 46 return o, nil 47 } 48 49 // Spend try to get the spend entry by given hash 50 func (tx *Tx) Spend(id Hash) (*Spend, error) { 51 e, ok := tx.Entries[id] 52 if !ok || e == nil { 53 return nil, errors.Wrapf(ErrMissingEntry, "id %x", id.Bytes()) 54 } 55 56 sp, ok := e.(*Spend) 57 if !ok { 58 return nil, errors.Wrapf(ErrEntryType, "entry %x has unexpected type %T", id.Bytes(), e) 59 } 60 return sp, nil 61 } 62 63 // Issuance try to get the issuance entry by given hash 64 func (tx *Tx) Issuance(id Hash) (*Issuance, error) { 65 e, ok := tx.Entries[id] 66 if !ok || e == nil { 67 return nil, errors.Wrapf(ErrMissingEntry, "id %x", id.Bytes()) 68 } 69 70 iss, ok := e.(*Issuance) 71 if !ok { 72 return nil, errors.Wrapf(ErrEntryType, "entry %x has unexpected type %T", id.Bytes(), e) 73 } 74 return iss, nil 75 } 76 77 // VetoInput try to get the veto entry by given hash 78 func (tx *Tx) VetoInput(id Hash) (*VetoInput, error) { 79 e, ok := tx.Entries[id] 80 if !ok || e == nil { 81 return nil, errors.Wrapf(ErrMissingEntry, "id %x", id.Bytes()) 82 } 83 84 sp, ok := e.(*VetoInput) 85 if !ok { 86 return nil, errors.Wrapf(ErrEntryType, "entry %x has unexpected type %T", id.Bytes(), e) 87 } 88 return sp, nil 89 } 90 91 // VoteOutput try to get the vote output entry by given hash 92 func (tx *Tx) VoteOutput(id Hash) (*VoteOutput, error) { 93 e, ok := tx.Entries[id] 94 if !ok || e == nil { 95 return nil, errors.Wrapf(ErrMissingEntry, "id %x", id.Bytes()) 96 } 97 98 o, ok := e.(*VoteOutput) 99 if !ok { 100 return nil, errors.Wrapf(ErrEntryType, "entry %x has unexpected type %T", id.Bytes(), e) 101 } 102 return o, nil 103 }