Skip to content

Commit

Permalink
refactor: SignedTx deserialization possible + unittest
Browse files Browse the repository at this point in the history
  • Loading branch information
randomshinichi committed Aug 13, 2019
1 parent 9b0c0dd commit 56ed4ac
Show file tree
Hide file tree
Showing 5 changed files with 105 additions and 6 deletions.
45 changes: 42 additions & 3 deletions aeternity/transactions.go
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ func Hash(tx *SignedTx) (txhash string, err error) {

// SignHashTx wraps a *Tx struct in a SignedTx, then calculates the signature
// and hash.
func SignHashTx(kp *Account, tx rlp.Encoder, networkID string) (signedTx SignedTx, txhash, signature string, err error) {
func SignHashTx(kp *Account, tx Transaction, networkID string) (signedTx SignedTx, txhash, signature string, err error) {
signedTx = NewSignedTx([][]byte{}, tx)
sigBytes, err := Sign(kp, &signedTx, networkID)
if err != nil {
Expand Down Expand Up @@ -160,13 +160,18 @@ func SerializeTx(tx rlp.Encoder) (string, error) {
return txStr, nil
}

// DeserializeTx takes a tx_ string and returns the corresponding Tx struct
func DeserializeTx(txRLP string) (Transaction, error) {
// DeserializeTxStr takes a tx_ string and returns the corresponding Tx struct
func DeserializeTxStr(txRLP string) (Transaction, error) {
rawRLP, err := Decode(txRLP)
if err != nil {
return nil, err
}
return DeserializeTx(rawRLP)
}

// DeserializeTx takes a RLP serialized transaction as a bytearray and returns
// the corresponding Tx struct
func DeserializeTx(rawRLP []byte) (Transaction, error) {
tx, err := GetTransactionType(rawRLP)
if err != nil {
return nil, err
Expand Down Expand Up @@ -243,6 +248,40 @@ func (tx *SignedTx) EncodeRLP(w io.Writer) (err error) {
return nil
}

type signedTxRLP struct {
ObjectTag uint
RlpMessageVersion uint
Signatures [][]byte
WrappedTx []byte
}

func (stx *signedTxRLP) ReadRLP(s *rlp.Stream) (err error) {
var blob []byte
if blob, err = s.Raw(); err != nil {
return
}
if err = rlp.DecodeBytes(blob, stx); err != nil {
return
}
return
}

// DecodeRLP implements rlp.Decoder
func (tx *SignedTx) DecodeRLP(s *rlp.Stream) (err error) {
stx := &signedTxRLP{}
if err = stx.ReadRLP(s); err != nil {
return
}
wtx, err := DeserializeTx(stx.WrappedTx)
if err != nil {
return
}

tx.Signatures = stx.Signatures
tx.Tx = wtx
return
}

// NewSignedTx ensures that all fields of SignedTx are filled out.
func NewSignedTx(Signatures [][]byte, tx rlp.Encoder) (s SignedTx) {
return SignedTx{
Expand Down
60 changes: 60 additions & 0 deletions aeternity/transactions_test.go
Original file line number Diff line number Diff line change
@@ -1,9 +1,69 @@
package aeternity

import (
"fmt"
"reflect"
"testing"

"github.com/aeternity/aepp-sdk-go/utils"
)

func getRLPSerialized(tx1 string, tx2 string) ([]interface{}, []interface{}) {
tx1Bytes, _ := Decode(tx1)
tx1RLP := DecodeRLPMessage(tx1Bytes)
tx2Bytes, _ := Decode(tx2)
tx2RLP := DecodeRLPMessage(tx2Bytes)
return tx1RLP, tx2RLP
}

func TestSignedTx(t *testing.T) {
tests := []struct {
name string
tx Transaction
wantRLP string
wantErr bool
}{
{
name: "ak_2a1j2Mk9YSmC1gioUq4PWRm3bsv887MbuRVwyv4KaUGoR1eiKi signed SpendTx",
tx: &SignedTx{
Signatures: [][]byte{
[]byte{10, 209, 197, 35, 33, 60, 73, 235, 31, 242, 68, 40, 83, 36, 49, 185, 210, 155, 146, 245, 148, 195, 118, 71, 232, 136, 84, 192, 104, 87, 114, 107, 26, 152, 167, 129, 192, 67, 213, 184, 220, 130, 126, 105, 22, 118, 228, 212, 198, 176, 0, 222, 210, 252, 185, 230, 18, 201, 238, 96, 105, 70, 40, 12},
},
Tx: &SpendTx{
SenderID: "ak_2a1j2Mk9YSmC1gioUq4PWRm3bsv887MbuRVwyv4KaUGoR1eiKi",
RecipientID: "ak_Egp9yVdpxmvAfQ7vsXGvpnyfNq71msbdUpkMNYGTeTe8kPL3v",
Amount: *utils.NewIntFromUint64(10),
Fee: *utils.NewIntFromUint64(10),
Payload: []byte("Hello World"),
TTL: uint64(10),
Nonce: uint64(1),
},
},
wantRLP: "tx_+KALAfhCuEAK0cUjITxJ6x/yRChTJDG50puS9ZTDdkfoiFTAaFdyaxqYp4HAQ9W43IJ+aRZ25NTGsADe0vy55hLJ7mBpRigMuFj4VgwBoQHOp63kcMn5nZ1OQAiAqG8dSbtES2LxGp67ZLvP63P+86EBHxOjsIvwAUAGYqaLadh194A87EwIZH9u1dhMeJe9UKMKCgoBi0hlbGxvIFdvcmxk+91GKg==",
wantErr: false,
},
}

for _, tt := range tests {
t.Run(fmt.Sprintf("%s EncodeRLP", tt.name), func(t *testing.T) {
gotRLP, err := SerializeTx(tt.tx)
if (err != nil) != tt.wantErr {
t.Errorf("%s error = %v, wantErr %v", tt.name, err, tt.wantErr)
}
if gotRLP != tt.wantRLP {
gotRLPRawBytes, wantRLPRawBytes := getRLPSerialized(gotRLP, tt.wantRLP)
t.Errorf("%s = \n%v\n%v, want \n%v\n%v", tt.name, gotRLP, gotRLPRawBytes, tt.wantRLP, wantRLPRawBytes)
}
})
t.Run(fmt.Sprintf("%s DecodeRLP", tt.name), func(t *testing.T) {
tx, err := DeserializeTxStr(tt.wantRLP)

if (err != nil) != tt.wantErr {
t.Errorf("%s error = %v, wantErr %v", tt.name, err, tt.wantErr)
}
if !(reflect.DeepEqual(tx, tt.tx)) {
t.Errorf("Deserialized Transaction %+v does not deep equal %+v", tx, tt.tx)
}
})
}
}
2 changes: 1 addition & 1 deletion aeternity/tx_aens_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -190,7 +190,7 @@ func TestAENSTx(t *testing.T) {

})
t.Run(fmt.Sprintf("%s DecodeRLP", tt.name), func(t *testing.T) {
tx, err := DeserializeTx(tt.wantRLP)
tx, err := DeserializeTxStr(tt.wantRLP)
if (err != nil) != tt.wantErr {
t.Errorf("%s error = %v, wantErr %v", tt.name, err, tt.wantErr)
}
Expand Down
2 changes: 1 addition & 1 deletion aeternity/tx_contracts_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -148,7 +148,7 @@ func TestContractTx(t *testing.T) {
}
})
t.Run(fmt.Sprintf("%s DecodeRLP", tt.name), func(t *testing.T) {
tx, err := DeserializeTx(tt.wantRLP)
tx, err := DeserializeTxStr(tt.wantRLP)

if (err != nil) != tt.wantErr {
t.Errorf("%s error = %v, wantErr %v", tt.name, err, tt.wantErr)
Expand Down
2 changes: 1 addition & 1 deletion aeternity/tx_oracles_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,7 @@ func TestOracleTx(t *testing.T) {
}
})
t.Run(fmt.Sprintf("%s DecodeRLP", tt.name), func(t *testing.T) {
tx, err := DeserializeTx(tt.wantRLP)
tx, err := DeserializeTxStr(tt.wantRLP)

if (err != nil) != tt.wantErr {
t.Errorf("%s error = %v, wantErr %v", tt.name, err, tt.wantErr)
Expand Down

0 comments on commit 56ed4ac

Please sign in to comment.