github.com/stellar/stellar-etl@v1.0.1-0.20240312145900-4874b6bf2b89/internal/transform/transaction_test.go (about)

     1  package transform
     2  
     3  import (
     4  	"fmt"
     5  	"testing"
     6  	"time"
     7  
     8  	"github.com/guregu/null"
     9  	"github.com/lib/pq"
    10  	"github.com/stretchr/testify/assert"
    11  
    12  	"github.com/stellar/go/ingest"
    13  	"github.com/stellar/go/xdr"
    14  )
    15  
    16  func TestTransformTransaction(t *testing.T) {
    17  	type inputStruct struct {
    18  		transaction   ingest.LedgerTransaction
    19  		historyHeader xdr.LedgerHeaderHistoryEntry
    20  	}
    21  	type transformTest struct {
    22  		input      inputStruct
    23  		wantOutput TransactionOutput
    24  		wantErr    error
    25  	}
    26  	genericInput := inputStruct{genericLedgerTransaction, genericLedgerHeaderHistoryEntry}
    27  	negativeSeqInput := genericInput
    28  	negativeSeqEnvelope := genericBumpOperationEnvelopeForTransaction
    29  	negativeSeqEnvelope.Tx.SeqNum = xdr.SequenceNumber(-1)
    30  	negativeSeqInput.transaction.Envelope.V1 = &negativeSeqEnvelope
    31  
    32  	badTimeboundInput := genericInput
    33  	badTimeboundEnvelope := genericBumpOperationEnvelopeForTransaction
    34  	badTimeboundEnvelope.Tx.Cond.Type = xdr.PreconditionTypePrecondTime
    35  	badTimeboundEnvelope.Tx.Cond.TimeBounds = &xdr.TimeBounds{
    36  		MinTime: 1594586912,
    37  		MaxTime: 100,
    38  	}
    39  	badTimeboundInput.transaction.Envelope.V1 = &badTimeboundEnvelope
    40  
    41  	badFeeChargedInput := genericInput
    42  	badFeeChargedInput.transaction.Result.Result.FeeCharged = -1
    43  
    44  	hardCodedTransaction, hardCodedLedgerHeader, err := makeTransactionTestInput()
    45  	assert.NoError(t, err)
    46  	hardCodedOutput, err := makeTransactionTestOutput()
    47  	assert.NoError(t, err)
    48  
    49  	tests := []transformTest{
    50  		transformTest{
    51  			negativeSeqInput,
    52  			TransactionOutput{},
    53  			fmt.Errorf("The account's sequence number (-1) is negative for ledger 0; transaction 1 (transaction id=4096)"),
    54  		},
    55  		{
    56  			badFeeChargedInput,
    57  			TransactionOutput{},
    58  			fmt.Errorf("The fee charged (-1) is negative for ledger 0; transaction 1 (transaction id=4096)"),
    59  		},
    60  		{
    61  			badTimeboundInput,
    62  			TransactionOutput{},
    63  			fmt.Errorf("The max time is earlier than the min time (100 < 1594586912) for ledger 0; transaction 1 (transaction id=4096)"),
    64  		},
    65  	}
    66  
    67  	for i := range hardCodedTransaction {
    68  		tests = append(tests, transformTest{
    69  			input:      inputStruct{hardCodedTransaction[i], hardCodedLedgerHeader[i]},
    70  			wantOutput: hardCodedOutput[i],
    71  			wantErr:    nil,
    72  		})
    73  	}
    74  
    75  	for _, test := range tests {
    76  		actualOutput, actualError := TransformTransaction(test.input.transaction, test.input.historyHeader)
    77  		assert.Equal(t, test.wantErr, actualError)
    78  		assert.Equal(t, test.wantOutput, actualOutput)
    79  	}
    80  }
    81  
    82  func makeTransactionTestOutput() (output []TransactionOutput, err error) {
    83  	correctTime, err := time.Parse("2006-1-2 15:04:05 MST", "2020-07-09 05:28:42 UTC")
    84  	output = []TransactionOutput{
    85  		TransactionOutput{
    86  			TxEnvelope:                   "AAAAAgAAAACI4aa0pXFSj6qfJuIObLw/5zyugLRGYwxb7wFSr3B9eAABX5ABjydzAABBtwAAAAEAAAAAAAAAAAAAAABfBqt0AAAAAQAAABdITDVhQ2dvelFISVc3c1NjNVhkY2ZtUgAAAAABAAAAAQAAAAAcR0GXGO76pFs4y38vJVAanjnLg4emNun7zAx0pHcDGAAAAAIAAAAAAAAAAAAAAAAAAAAAAQIDAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=",
    87  			TxResult:                     "AAAAAAAAASz/////AAAAAQAAAAAAAAAAAAAAAAAAAAA=",
    88  			TxMeta:                       "AAAAAQAAAAAAAAAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACAAAAAwAAAAAAAAAFAQIDBAUGBwgJAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFVU1NEAAAAAGtY3WxokwttAx3Fu/riPvoew/C7WMK8jZONR8Hfs75zAAAAHgAAAAAAAYagAAAAAAAAA+gAAAAAAAAB9AAAAAAAAAAZAAAAAAAAAAEAAAAAAAAABQECAwQFBgcICQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABVVNTRAAAAABrWN1saJMLbQMdxbv64j76HsPwu1jCvI2TjUfB37O+cwAAAB4AAAAAAAGKiAAAAAAAAARMAAAAAAAAAfYAAAAAAAAAGgAAAAAAAAACAAAAAwAAAAAAAAAFAQIDBAUGBwgJAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFVU1NEAAAAAGtY3WxokwttAx3Fu/riPvoew/C7WMK8jZONR8Hfs75zAAAAHgAAAAAAAYagAAAAAAAAA+gAAAAAAAAB9AAAAAAAAAAZAAAAAAAAAAEAAAAAAAAABQECAwQFBgcICQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABVVNTRAAAAABrWN1saJMLbQMdxbv64j76HsPwu1jCvI2TjUfB37O+cwAAAB4AAAAAAAGKiAAAAAAAAARMAAAAAAAAAfYAAAAAAAAAGgAAAAAAAAAA",
    89  			TxFeeMeta:                    "AAAAAA==",
    90  			TransactionHash:              "a87fef5eeb260269c380f2de456aad72b59bb315aaac777860456e09dac0bafb",
    91  			LedgerSequence:               30521816,
    92  			TransactionID:                131090201534533632,
    93  			Account:                      testAccount1Address,
    94  			AccountSequence:              112351890582290871,
    95  			MaxFee:                       90000,
    96  			FeeCharged:                   300,
    97  			OperationCount:               1,
    98  			CreatedAt:                    correctTime,
    99  			MemoType:                     "MemoTypeMemoText",
   100  			Memo:                         "HL5aCgozQHIW7sSc5XdcfmR",
   101  			TimeBounds:                   "[0,1594272628)",
   102  			Successful:                   false,
   103  			ClosedAt:                     time.Date(2020, time.July, 9, 5, 28, 42, 0, time.UTC),
   104  			ResourceFee:                  0,
   105  			SorobanResourcesInstructions: 0,
   106  			SorobanResourcesReadBytes:    0,
   107  			SorobanResourcesWriteBytes:   0,
   108  			TransactionResultCode:        "TransactionResultCodeTxFailed",
   109  		},
   110  		TransactionOutput{
   111  			TxEnvelope:                   "AAAABQAAAABnzACGTDuJFoxqr+C8NHCe0CHFBXLi+YhhNCIILCIpcgAAAAAAABwgAAAAAgAAAACI4aa0pXFSj6qfJuIObLw/5zyugLRGYwxb7wFSr3B9eAAAAAACFPY2AAAAfQAAAAEAAAAAAAAAAAAAAABfBqt0AAAAAQAAABdITDVhQ2dvelFISVc3c1NjNVhkY2ZtUgAAAAABAAAAAQAAAAAcR0GXGO76pFs4y38vJVAanjnLg4emNun7zAx0pHcDGAAAAAIAAAAAAAAAAAAAAAAAAAAAAQIDAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA==",
   112  			TxResult:                     "AAAAAAAAASwAAAABqH/vXusmAmnDgPLeRWqtcrWbsxWqrHd4YEVuCdrAuvsAAAAAAAAAZAAAAAAAAAABAAAAAAAAAAAAAAAAAAAAAAAAAAA=",
   113  			TxMeta:                       "AAAAAQAAAAAAAAAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACAAAAAwAAAAAAAAAFAQIDBAUGBwgJAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFVU1NEAAAAAGtY3WxokwttAx3Fu/riPvoew/C7WMK8jZONR8Hfs75zAAAAHgAAAAAAAYagAAAAAAAAA+gAAAAAAAAB9AAAAAAAAAAZAAAAAAAAAAEAAAAAAAAABQECAwQFBgcICQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABVVNTRAAAAABrWN1saJMLbQMdxbv64j76HsPwu1jCvI2TjUfB37O+cwAAAB4AAAAAAAGKiAAAAAAAAARMAAAAAAAAAfYAAAAAAAAAGgAAAAAAAAACAAAAAwAAAAAAAAAFAQIDBAUGBwgJAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFVU1NEAAAAAGtY3WxokwttAx3Fu/riPvoew/C7WMK8jZONR8Hfs75zAAAAHgAAAAAAAYagAAAAAAAAA+gAAAAAAAAB9AAAAAAAAAAZAAAAAAAAAAEAAAAAAAAABQECAwQFBgcICQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABVVNTRAAAAABrWN1saJMLbQMdxbv64j76HsPwu1jCvI2TjUfB37O+cwAAAB4AAAAAAAGKiAAAAAAAAARMAAAAAAAAAfYAAAAAAAAAGgAAAAAAAAAA",
   114  			TxFeeMeta:                    "AAAAAA==",
   115  			TransactionHash:              "a87fef5eeb260269c380f2de456aad72b59bb315aaac777860456e09dac0bafb",
   116  			LedgerSequence:               30521817,
   117  			TransactionID:                131090205829500928,
   118  			Account:                      testAccount1Address,
   119  			AccountSequence:              150015399398735997,
   120  			MaxFee:                       0,
   121  			FeeCharged:                   300,
   122  			OperationCount:               1,
   123  			CreatedAt:                    correctTime,
   124  			MemoType:                     "MemoTypeMemoText",
   125  			Memo:                         "HL5aCgozQHIW7sSc5XdcfmR",
   126  			TimeBounds:                   "[0,1594272628)",
   127  			Successful:                   true,
   128  			InnerTransactionHash:         "a87fef5eeb260269c380f2de456aad72b59bb315aaac777860456e09dac0bafb",
   129  			FeeAccount:                   testAccount3Address,
   130  			NewMaxFee:                    7200,
   131  			ClosedAt:                     time.Date(2020, time.July, 9, 5, 28, 42, 0, time.UTC),
   132  			ResourceFee:                  0,
   133  			SorobanResourcesInstructions: 0,
   134  			SorobanResourcesReadBytes:    0,
   135  			SorobanResourcesWriteBytes:   0,
   136  			TransactionResultCode:        "TransactionResultCodeTxFeeBumpInnerSuccess", //inner fee bump success
   137  		},
   138  		TransactionOutput{
   139  			TxEnvelope:                   "AAAAAgAAAAAcR0GXGO76pFs4y38vJVAanjnLg4emNun7zAx0pHcDGAAAAGQBpLyvsiV6gwAAAAIAAAABAAAAAAAAAAAAAAAAXwardAAAAAEAAAAFAAAACgAAAAAAAAAAAAAAAAAAAAAAAAABAAAAAAMCAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAAABdITDVhQ2dvelFISVc3c1NjNVhkY2ZtUgAAAAABAAAAAQAAAABrWN1saJMLbQMdxbv64j76HsPwu1jCvI2TjUfB37O+cwAAAAIAAAAAAAAAAAAAAAAAAAAAAQIDAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA=",
   140  			TxResult:                     "AAAAAAAAAGT////5AAAAAA==",
   141  			TxMeta:                       "AAAAAQAAAAAAAAAgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACAAAAAwAAAAAAAAAFAQIDBAUGBwgJAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFVU1NEAAAAAGtY3WxokwttAx3Fu/riPvoew/C7WMK8jZONR8Hfs75zAAAAHgAAAAAAAYagAAAAAAAAA+gAAAAAAAAB9AAAAAAAAAAZAAAAAAAAAAEAAAAAAAAABQECAwQFBgcICQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABVVNTRAAAAABrWN1saJMLbQMdxbv64j76HsPwu1jCvI2TjUfB37O+cwAAAB4AAAAAAAGKiAAAAAAAAARMAAAAAAAAAfYAAAAAAAAAGgAAAAAAAAACAAAAAwAAAAAAAAAFAQIDBAUGBwgJAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFVU1NEAAAAAGtY3WxokwttAx3Fu/riPvoew/C7WMK8jZONR8Hfs75zAAAAHgAAAAAAAYagAAAAAAAAA+gAAAAAAAAB9AAAAAAAAAAZAAAAAAAAAAEAAAAAAAAABQECAwQFBgcICQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABVVNTRAAAAABrWN1saJMLbQMdxbv64j76HsPwu1jCvI2TjUfB37O+cwAAAB4AAAAAAAGKiAAAAAAAAARMAAAAAAAAAfYAAAAAAAAAGgAAAAAAAAAA",
   142  			TxFeeMeta:                    "AAAAAA==",
   143  			TransactionHash:              "a87fef5eeb260269c380f2de456aad72b59bb315aaac777860456e09dac0bafb",
   144  			LedgerSequence:               30521818,
   145  			TransactionID:                131090210124468224,
   146  			Account:                      testAccount2Address,
   147  			AccountSequence:              118426953012574851,
   148  			MaxFee:                       100,
   149  			FeeCharged:                   100,
   150  			OperationCount:               1,
   151  			CreatedAt:                    correctTime,
   152  			MemoType:                     "MemoTypeMemoText",
   153  			Memo:                         "HL5aCgozQHIW7sSc5XdcfmR",
   154  			TimeBounds:                   "[0,1594272628)",
   155  			Successful:                   false,
   156  			LedgerBounds:                 "[5,10)",
   157  			ExtraSigners:                 pq.StringArray{"GABQEAIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB7QL"},
   158  			MinAccountSequenceAge:        null.IntFrom(0),
   159  			MinAccountSequenceLedgerGap:  null.IntFrom(0),
   160  			ClosedAt:                     time.Date(2020, time.July, 9, 5, 28, 42, 0, time.UTC),
   161  			ResourceFee:                  0,
   162  			SorobanResourcesInstructions: 0,
   163  			SorobanResourcesReadBytes:    0,
   164  			SorobanResourcesWriteBytes:   0,
   165  			TransactionResultCode:        "TransactionResultCodeTxInsufficientBalance",
   166  		},
   167  	}
   168  	return
   169  }
   170  func makeTransactionTestInput() (transaction []ingest.LedgerTransaction, historyHeader []xdr.LedgerHeaderHistoryEntry, err error) {
   171  	hardCodedMemoText := "HL5aCgozQHIW7sSc5XdcfmR"
   172  	hardCodedTransactionHash := xdr.Hash([32]byte{0xa8, 0x7f, 0xef, 0x5e, 0xeb, 0x26, 0x2, 0x69, 0xc3, 0x80, 0xf2, 0xde, 0x45, 0x6a, 0xad, 0x72, 0xb5, 0x9b, 0xb3, 0x15, 0xaa, 0xac, 0x77, 0x78, 0x60, 0x45, 0x6e, 0x9, 0xda, 0xc0, 0xba, 0xfb})
   173  	genericResultResults := &[]xdr.OperationResult{
   174  		xdr.OperationResult{
   175  			Tr: &xdr.OperationResultTr{
   176  				Type: xdr.OperationTypeCreateAccount,
   177  				CreateAccountResult: &xdr.CreateAccountResult{
   178  					Code: 0,
   179  				},
   180  			},
   181  		},
   182  	}
   183  	hardCodedMeta := xdr.TransactionMeta{
   184  		V:  1,
   185  		V1: genericTxMeta,
   186  	}
   187  
   188  	source := xdr.MuxedAccount{
   189  		Type:    xdr.CryptoKeyTypeKeyTypeEd25519,
   190  		Ed25519: &xdr.Uint256{3, 2, 1},
   191  	}
   192  	destination := xdr.MuxedAccount{
   193  		Type:    xdr.CryptoKeyTypeKeyTypeEd25519,
   194  		Ed25519: &xdr.Uint256{1, 2, 3},
   195  	}
   196  	signerKey := xdr.SignerKey{
   197  		Type:    xdr.SignerKeyTypeSignerKeyTypeEd25519,
   198  		Ed25519: source.Ed25519,
   199  	}
   200  	transaction = []ingest.LedgerTransaction{
   201  		ingest.LedgerTransaction{
   202  			Index:      1,
   203  			UnsafeMeta: hardCodedMeta,
   204  			Envelope: xdr.TransactionEnvelope{
   205  				Type: xdr.EnvelopeTypeEnvelopeTypeTx,
   206  				V1: &xdr.TransactionV1Envelope{
   207  					Tx: xdr.Transaction{
   208  						SourceAccount: testAccount1,
   209  						SeqNum:        112351890582290871,
   210  						Memo: xdr.Memo{
   211  							Type: xdr.MemoTypeMemoText,
   212  							Text: &hardCodedMemoText,
   213  						},
   214  						Fee: 90000,
   215  						Cond: xdr.Preconditions{
   216  							Type: xdr.PreconditionTypePrecondTime,
   217  							TimeBounds: &xdr.TimeBounds{
   218  								MinTime: 0,
   219  								MaxTime: 1594272628,
   220  							},
   221  						},
   222  						Operations: []xdr.Operation{
   223  							xdr.Operation{
   224  								SourceAccount: &testAccount2,
   225  								Body: xdr.OperationBody{
   226  									Type: xdr.OperationTypePathPaymentStrictReceive,
   227  									PathPaymentStrictReceiveOp: &xdr.PathPaymentStrictReceiveOp{
   228  										Destination: destination,
   229  									},
   230  								},
   231  							},
   232  						},
   233  					},
   234  				},
   235  			},
   236  			Result: xdr.TransactionResultPair{
   237  				TransactionHash: hardCodedTransactionHash,
   238  				Result: xdr.TransactionResult{
   239  					FeeCharged: 300,
   240  					Result: xdr.TransactionResultResult{
   241  						Code:    xdr.TransactionResultCodeTxFailed,
   242  						Results: genericResultResults,
   243  					},
   244  				},
   245  			},
   246  		},
   247  		ingest.LedgerTransaction{
   248  			Index:      1,
   249  			UnsafeMeta: hardCodedMeta,
   250  			Envelope: xdr.TransactionEnvelope{
   251  				Type: xdr.EnvelopeTypeEnvelopeTypeTxFeeBump,
   252  				FeeBump: &xdr.FeeBumpTransactionEnvelope{
   253  					Tx: xdr.FeeBumpTransaction{
   254  						FeeSource: testAccount3,
   255  						Fee:       7200,
   256  						InnerTx: xdr.FeeBumpTransactionInnerTx{
   257  							Type: xdr.EnvelopeTypeEnvelopeTypeTx,
   258  							V1: &xdr.TransactionV1Envelope{
   259  								Tx: xdr.Transaction{
   260  									SourceAccount: testAccount1,
   261  									SeqNum:        150015399398735997,
   262  									Memo: xdr.Memo{
   263  										Type: xdr.MemoTypeMemoText,
   264  										Text: &hardCodedMemoText,
   265  									},
   266  									Cond: xdr.Preconditions{
   267  										Type: xdr.PreconditionTypePrecondTime,
   268  										TimeBounds: &xdr.TimeBounds{
   269  											MinTime: 0,
   270  											MaxTime: 1594272628,
   271  										},
   272  									},
   273  									Operations: []xdr.Operation{
   274  										xdr.Operation{
   275  											SourceAccount: &testAccount2,
   276  											Body: xdr.OperationBody{
   277  												Type: xdr.OperationTypePathPaymentStrictReceive,
   278  												PathPaymentStrictReceiveOp: &xdr.PathPaymentStrictReceiveOp{
   279  													Destination: destination,
   280  												},
   281  											},
   282  										},
   283  									},
   284  								},
   285  							},
   286  						},
   287  					},
   288  				},
   289  			},
   290  			Result: xdr.TransactionResultPair{
   291  				TransactionHash: hardCodedTransactionHash,
   292  				Result: xdr.TransactionResult{
   293  					FeeCharged: 300,
   294  					Result: xdr.TransactionResultResult{
   295  						Code: xdr.TransactionResultCodeTxFeeBumpInnerSuccess,
   296  						InnerResultPair: &xdr.InnerTransactionResultPair{
   297  							TransactionHash: hardCodedTransactionHash,
   298  							Result: xdr.InnerTransactionResult{
   299  								FeeCharged: 100,
   300  								Result: xdr.InnerTransactionResultResult{
   301  									Code: xdr.TransactionResultCodeTxSuccess,
   302  									Results: &[]xdr.OperationResult{
   303  										xdr.OperationResult{
   304  											Tr: &xdr.OperationResultTr{
   305  												CreateAccountResult: &xdr.CreateAccountResult{},
   306  											},
   307  										},
   308  									},
   309  								},
   310  							},
   311  						},
   312  						Results: &[]xdr.OperationResult{
   313  							xdr.OperationResult{},
   314  						},
   315  					},
   316  				},
   317  			},
   318  		},
   319  		ingest.LedgerTransaction{
   320  			Index:      1,
   321  			UnsafeMeta: hardCodedMeta,
   322  			Envelope: xdr.TransactionEnvelope{
   323  				Type: xdr.EnvelopeTypeEnvelopeTypeTx,
   324  				V1: &xdr.TransactionV1Envelope{
   325  					Tx: xdr.Transaction{
   326  						SourceAccount: testAccount2,
   327  						SeqNum:        118426953012574851,
   328  						Memo: xdr.Memo{
   329  							Type: xdr.MemoTypeMemoText,
   330  							Text: &hardCodedMemoText,
   331  						},
   332  						Fee: 100,
   333  						Cond: xdr.Preconditions{
   334  							Type: xdr.PreconditionTypePrecondV2,
   335  							V2: &xdr.PreconditionsV2{
   336  								TimeBounds: &xdr.TimeBounds{
   337  									MinTime: 0,
   338  									MaxTime: 1594272628,
   339  								},
   340  								LedgerBounds: &xdr.LedgerBounds{
   341  									MinLedger: 5,
   342  									MaxLedger: 10,
   343  								},
   344  								ExtraSigners: []xdr.SignerKey{signerKey},
   345  							},
   346  						},
   347  						Operations: []xdr.Operation{
   348  							xdr.Operation{
   349  								SourceAccount: &testAccount4,
   350  								Body: xdr.OperationBody{
   351  									Type: xdr.OperationTypePathPaymentStrictReceive,
   352  									PathPaymentStrictReceiveOp: &xdr.PathPaymentStrictReceiveOp{
   353  										Destination: destination,
   354  									},
   355  								},
   356  							},
   357  						},
   358  					},
   359  				},
   360  			},
   361  			Result: xdr.TransactionResultPair{
   362  				TransactionHash: hardCodedTransactionHash,
   363  				Result: xdr.TransactionResult{
   364  					FeeCharged: 100,
   365  					Result: xdr.TransactionResultResult{
   366  						Code:    xdr.TransactionResultCodeTxInsufficientBalance,
   367  						Results: genericResultResults,
   368  					},
   369  				},
   370  			},
   371  		},
   372  	}
   373  	historyHeader = []xdr.LedgerHeaderHistoryEntry{
   374  		xdr.LedgerHeaderHistoryEntry{
   375  			Header: xdr.LedgerHeader{
   376  				LedgerSeq: 30521816,
   377  				ScpValue:  xdr.StellarValue{CloseTime: 1594272522},
   378  			},
   379  		},
   380  		xdr.LedgerHeaderHistoryEntry{
   381  			Header: xdr.LedgerHeader{
   382  				LedgerSeq: 30521817,
   383  				ScpValue:  xdr.StellarValue{CloseTime: 1594272522},
   384  			},
   385  		},
   386  		xdr.LedgerHeaderHistoryEntry{
   387  			Header: xdr.LedgerHeader{
   388  				LedgerSeq: 30521818,
   389  				ScpValue:  xdr.StellarValue{CloseTime: 1594272522},
   390  			},
   391  		},
   392  	}
   393  	return
   394  }