diff --git a/cmd/integration_tests.go b/cmd/integration_tests.go index 92d7e98a4..0d8446bec 100644 --- a/cmd/integration_tests.go +++ b/cmd/integration_tests.go @@ -33,7 +33,7 @@ func (c *IntegrationTestsCommand) Command() *cobra.Command { Usage: "Issuer if the asset to be disbursed", OptType: types.String, ConfigKey: &integrationTestsOpts.DisbursetAssetIssuer, - Required: true, + Required: false, }, { Name: "disbursement-name", diff --git a/internal/integrationtests/docker/docker-compose-e2e-tests.yml b/internal/integrationtests/docker/docker-compose-e2e-tests.yml index 1c2f9e592..4d5b0d712 100644 --- a/internal/integrationtests/docker/docker-compose-e2e-tests.yml +++ b/internal/integrationtests/docker/docker-compose-e2e-tests.yml @@ -221,6 +221,21 @@ services: "max_amount": 10000 }, "withdraw": {"enabled": false} + }, + { + "sep24_enabled": true, + "schema": "stellar", + "code": "XLM", + "distribution_account": "${DISTRIBUTION_PUBLIC_KEY}", + "significant_decimals": 7, + "deposit": { + "enabled": true, + "fee_minimum": 0, + "fee_percent": 0, + "min_amount": 1, + "max_amount": 10000 + }, + "withdraw": {"enabled": false} } ] } diff --git a/internal/integrationtests/utils.go b/internal/integrationtests/utils.go index e5c748148..8bae5b8b8 100644 --- a/internal/integrationtests/utils.go +++ b/internal/integrationtests/utils.go @@ -2,7 +2,6 @@ package integrationtests import ( "context" - "encoding/json" "fmt" "io" "io/fs" @@ -10,6 +9,7 @@ import ( "github.com/gocarina/gocsv" "github.com/stellar/go/clients/horizonclient" + "github.com/stellar/go/protocols/horizon/operations" "github.com/stellar/go/support/log" "github.com/stellar/stellar-disbursement-platform-backend/internal/data" @@ -46,28 +46,20 @@ func readDisbursementCSV(disbursementFilePath string, disbursementFileName strin return instructions, nil } -type PaymentHorizon struct { - ReceiverAccount string `json:"to"` - Amount string `json:"amount"` - AssetCode string `json:"asset_code"` - AssetIssuer string `json:"asset_issuer"` - TransactionSuccessful bool `json:"transaction_successful"` -} - -func getTransactionOnHorizon(client horizonclient.ClientInterface, transactionID string) (*PaymentHorizon, error) { - ph := &PaymentHorizon{} +func getTransactionOnHorizon(client horizonclient.ClientInterface, transactionID string) (*operations.Payment, error) { records, err := client.Payments(horizonclient.OperationRequest{ForTransaction: transactionID}) if err != nil { - return nil, fmt.Errorf("error checking payment in horizon: %w", err) + return nil, fmt.Errorf("checking payment in horizon: %w", err) } - paymentRecord, err := json.Marshal(records.Embedded.Records[0]) - if err != nil { - return nil, fmt.Errorf("error marshaling payment record: %w", err) + + if len(records.Embedded.Records) == 0 { + return nil, fmt.Errorf("no payment records found in horizon for transaction %s", transactionID) } - err = json.Unmarshal(paymentRecord, ph) - if err != nil { - return nil, fmt.Errorf("error unmarshling payment record: %w", err) + + hPayment, ok := records.Embedded.Records[0].(operations.Payment) + if !ok { + return nil, fmt.Errorf("casting payment record to operations.Payment") } - return ph, nil + return &hPayment, nil } diff --git a/internal/integrationtests/utils_test.go b/internal/integrationtests/utils_test.go index 784f046ac..f938c1cd7 100644 --- a/internal/integrationtests/utils_test.go +++ b/internal/integrationtests/utils_test.go @@ -83,7 +83,7 @@ func Test_getTransactionInHorizon(t *testing.T) { Once() ph, err := getTransactionOnHorizon(mockHorizonClient, mockTransactionID) - require.EqualError(t, err, "error checking payment in horizon: horizon error: \"Resource Missing\" - check horizon.Error.Problem for more information") + require.EqualError(t, err, "checking payment in horizon: horizon error: \"Resource Missing\" - check horizon.Error.Problem for more information") assert.Empty(t, ph) mockHorizonClient.AssertExpectations(t) @@ -142,9 +142,10 @@ func Test_getTransactionInHorizon(t *testing.T) { ph, err := getTransactionOnHorizon(mockHorizonClient, mockTransactionID) require.NoError(t, err) - assert.Equal(t, "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", ph.ReceiverAccount) - assert.Equal(t, "USDC", ph.AssetCode) - assert.Equal(t, "GBZF7AS3TBASAL5RQ7ECJODFWFLBDCKJK5SMPUCO5R36CJUIZRWQJTGB", ph.AssetIssuer) + assert.Equal(t, "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", ph.To) + assert.Equal(t, "USDC", ph.Asset.Code) + assert.Equal(t, "GBZF7AS3TBASAL5RQ7ECJODFWFLBDCKJK5SMPUCO5R36CJUIZRWQJTGB", ph.Asset.Issuer) + assert.Equal(t, "credit_alphanum4", ph.Asset.Type) assert.Equal(t, "100.0000000", ph.Amount) assert.Equal(t, true, ph.TransactionSuccessful) diff --git a/internal/integrationtests/validations.go b/internal/integrationtests/validations.go index ff376bfbf..f363bb3e8 100644 --- a/internal/integrationtests/validations.go +++ b/internal/integrationtests/validations.go @@ -4,6 +4,9 @@ import ( "context" "fmt" + "github.com/stellar/go/protocols/horizon/operations" + "github.com/stellar/go/support/log" + "github.com/stellar/stellar-disbursement-platform-backend/db" "github.com/stellar/stellar-disbursement-platform-backend/internal/data" ) @@ -67,7 +70,6 @@ func validateExpectationsAfterStartDisbursement(ctx context.Context, disbursemen } for _, receiver := range receivers { - // Validate receiver_wallet status expectedStatusByRegistrationContactType := map[data.RegistrationContactType]data.ReceiversWalletStatus{ data.RegistrationContactTypePhone: data.ReadyReceiversWalletStatus, @@ -101,20 +103,26 @@ func validateExpectationsAfterReceiverRegistration(ctx context.Context, models * return nil } -func validateStellarTransaction(paymentHorizon *PaymentHorizon, receiverAccount, disbursedAssetCode, disbursedAssetIssuer, amount string) error { - if !paymentHorizon.TransactionSuccessful { +func validateStellarTransaction(hPayment *operations.Payment, receiverAccount, disbursedAssetCode, disbursedAssetIssuer, amount string) error { + if !hPayment.TransactionSuccessful { return fmt.Errorf("transaction was not successful on horizon network") } - if paymentHorizon.ReceiverAccount != receiverAccount { + if hPayment.To != receiverAccount { return fmt.Errorf("transaction sent to wrong receiver account") } - if paymentHorizon.Amount != amount { + if hPayment.Amount != amount { return fmt.Errorf("transaction with wrong amount") } - if paymentHorizon.AssetCode != disbursedAssetCode || paymentHorizon.AssetIssuer != disbursedAssetIssuer { + dataAsset := data.Asset{ + Code: disbursedAssetCode, + Issuer: disbursedAssetIssuer, + } + if !dataAsset.EqualsHorizonAsset(hPayment.Asset) { + log.Errorf("disbursed.asset: %s:%s", disbursedAssetCode, disbursedAssetIssuer) + log.Errorf("hAsset: %+v", hPayment.Asset) return fmt.Errorf("transaction with wrong disbursed asset") } diff --git a/internal/integrationtests/validations_test.go b/internal/integrationtests/validations_test.go index 39d141503..fcc788ced 100644 --- a/internal/integrationtests/validations_test.go +++ b/internal/integrationtests/validations_test.go @@ -4,6 +4,8 @@ import ( "context" "testing" + "github.com/stellar/go/protocols/horizon/base" + "github.com/stellar/go/protocols/horizon/operations" "github.com/stretchr/testify/require" "github.com/stellar/stellar-disbursement-platform-backend/db" @@ -266,58 +268,67 @@ func Test_validateStellarTransaction(t *testing.T) { mockAmount := "0.1" t.Run("error transaction not successful", func(t *testing.T) { - err := validateStellarTransaction(&PaymentHorizon{ - TransactionSuccessful: false, + err := validateStellarTransaction(&operations.Payment{ + Base: operations.Base{TransactionSuccessful: false}, }, mockReceiverAccount, mockassetCode, mockassetIssuer, mockAmount) require.EqualError(t, err, "transaction was not successful on horizon network") }) t.Run("error wrong receiver account", func(t *testing.T) { - err := validateStellarTransaction(&PaymentHorizon{ - TransactionSuccessful: true, - ReceiverAccount: "invalidReceiver", + err := validateStellarTransaction(&operations.Payment{ + Base: operations.Base{TransactionSuccessful: true}, + To: "invalidReceiver", }, mockReceiverAccount, mockassetCode, mockassetIssuer, mockAmount) require.EqualError(t, err, "transaction sent to wrong receiver account") }) t.Run("error wrong amount", func(t *testing.T) { - err := validateStellarTransaction(&PaymentHorizon{ - TransactionSuccessful: true, - ReceiverAccount: "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", - Amount: "20", + err := validateStellarTransaction(&operations.Payment{ + Base: operations.Base{TransactionSuccessful: true}, + To: "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", + Amount: "20", }, mockReceiverAccount, mockassetCode, mockassetIssuer, mockAmount) require.EqualError(t, err, "transaction with wrong amount") }) t.Run("error wrong asset code", func(t *testing.T) { - err := validateStellarTransaction(&PaymentHorizon{ - TransactionSuccessful: true, - ReceiverAccount: "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", - Amount: "0.1", - AssetCode: "invalidCode", - AssetIssuer: "GBZF7AS3TBASAL5RQ7ECJODFWFLBDCKJK5SMPUCO5R36CJUIZRWQJTGB", + err := validateStellarTransaction(&operations.Payment{ + Base: operations.Base{TransactionSuccessful: true}, + To: "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", + Amount: "0.1", + Asset: base.Asset{ + Type: "credit_alphanum12", + Code: "invalidCode", + Issuer: "GBZF7AS3TBASAL5RQ7ECJODFWFLBDCKJK5SMPUCO5R36CJUIZRWQJTGB", + }, }, mockReceiverAccount, mockassetCode, mockassetIssuer, mockAmount) require.EqualError(t, err, "transaction with wrong disbursed asset") }) t.Run("error wrong asset issuer", func(t *testing.T) { - err := validateStellarTransaction(&PaymentHorizon{ - TransactionSuccessful: true, - ReceiverAccount: "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", - Amount: "0.1", - AssetCode: "USDC", - AssetIssuer: "invalidIssuer", + err := validateStellarTransaction(&operations.Payment{ + Base: operations.Base{TransactionSuccessful: true}, + To: "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", + Amount: "0.1", + Asset: base.Asset{ + Type: "credit_alphanum4", + Code: "USDC", + Issuer: "invalidIssuer", + }, }, mockReceiverAccount, mockassetCode, mockassetIssuer, mockAmount) require.EqualError(t, err, "transaction with wrong disbursed asset") }) t.Run("successful validation", func(t *testing.T) { - err := validateStellarTransaction(&PaymentHorizon{ - TransactionSuccessful: true, - ReceiverAccount: "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", - Amount: "0.1", - AssetCode: "USDC", - AssetIssuer: "GBZF7AS3TBASAL5RQ7ECJODFWFLBDCKJK5SMPUCO5R36CJUIZRWQJTGB", + err := validateStellarTransaction(&operations.Payment{ + Base: operations.Base{TransactionSuccessful: true}, + To: "GD44L3Q6NYRFPVOX4CJUUV63QEOOU3R5JNQJBLR6WWXFWYHEGK2YVBQ7", + Amount: "0.1", + Asset: base.Asset{ + Type: "credit_alphanum4", + Code: "USDC", + Issuer: "GBZF7AS3TBASAL5RQ7ECJODFWFLBDCKJK5SMPUCO5R36CJUIZRWQJTGB", + }, }, mockReceiverAccount, mockassetCode, mockassetIssuer, mockAmount) require.NoError(t, err) })