From 6f872c8ac7e0dbefdc293e9bf2a9fad966a96979 Mon Sep 17 00:00:00 2001 From: Crimson Thompson Date: Mon, 25 Nov 2024 17:56:36 +0100 Subject: [PATCH 1/6] fix: run e2e tests on CI by default --- Earthfile | 24 +- go.mod | 3 + go.sum | 1 + pkg/testserver/server.go | 2 + test/e2e/api_bank_accounts_test.go | 435 +++++++++++++++-------------- 5 files changed, 245 insertions(+), 220 deletions(-) diff --git a/Earthfile b/Earthfile index 3ca155ed..8d33e254 100644 --- a/Earthfile +++ b/Earthfile @@ -5,6 +5,9 @@ IMPORT github.com/formancehq/earthly:tags/v0.16.2 AS core FROM core+base-image +postgres: + FROM postgres:15-alpine + sources: WORKDIR src WORKDIR /src @@ -60,11 +63,25 @@ build-image: DO core+SAVE_IMAGE --COMPONENT=payments --REPOSITORY=${REPOSITORY} --TAG=$tag tests: - FROM core+builder-image + FROM +tidy COPY (+sources/*) /src WORKDIR /src - WITH DOCKER --pull=postgres:15-alpine - DO --pass-args core+GO_TESTS + ARG includeIntegrationTests="true" + + ENV CGO_ENABLED=1 # required for -race + + LET goFlags="-race" + IF [ "$includeIntegrationTests" = "true" ] + COPY (+compile-configs/configs.json) /src/internal/connectors/plugins/configs.json + COPY (+compile-plugins/list.go) /src/internal/connectors/plugins/public/list.go + SET goFlags="$goFlags -tags it" + WITH DOCKER --load=postgres:15-alpine=+postgres + RUN go test $goFlags ./... + END + ELSE + WITH DOCKER --pull=postgres:15-alpine + DO --pass-args +GO_TESTS + END END deploy: @@ -104,6 +121,7 @@ tidy: FROM core+builder-image COPY --pass-args (+sources/src) /src WORKDIR /src + COPY --dir test . DO --pass-args core+GO_TIDY generate: diff --git a/go.mod b/go.mod index 4cb2465c..3fc02269 100644 --- a/go.mod +++ b/go.mod @@ -147,11 +147,14 @@ require ( github.com/mailru/easyjson v0.7.7 // indirect github.com/mattn/go-colorable v0.1.13 // indirect github.com/mattn/go-isatty v0.0.20 // indirect + github.com/minio/highwayhash v1.0.3 // indirect github.com/mitchellh/mapstructure v1.5.0 // indirect github.com/moby/docker-image-spec v1.3.1 // indirect github.com/moby/term v0.5.0 // indirect github.com/muhlemmer/gu v0.3.1 // indirect github.com/muhlemmer/httpforwarded v0.1.0 // indirect + github.com/nats-io/jwt/v2 v2.7.0 // indirect + github.com/nats-io/nats-server/v2 v2.10.22 // indirect github.com/nats-io/nkeys v0.4.7 // indirect github.com/nats-io/nuid v1.0.1 // indirect github.com/nexus-rpc/sdk-go v0.0.11 // indirect diff --git a/go.sum b/go.sum index 77cabab8..8bc9e18e 100644 --- a/go.sum +++ b/go.sum @@ -1598,6 +1598,7 @@ golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.7.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.11.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.21.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.27.0 h1:wBqf8DvsY9Y/2P8gAfPDEYNuS30J4lPHJxXSb/nJZ+s= golang.org/x/sys v0.27.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= diff --git a/pkg/testserver/server.go b/pkg/testserver/server.go index 1901da6c..2d297df9 100644 --- a/pkg/testserver/server.go +++ b/pkg/testserver/server.go @@ -11,6 +11,8 @@ import ( "github.com/nats-io/nats.go" + _ "github.com/formancehq/payments/internal/connectors/plugins/public" + "github.com/formancehq/go-libs/v2/otlp" "github.com/formancehq/go-libs/v2/otlp/otlpmetrics" "github.com/formancehq/go-libs/v2/publish" diff --git a/test/e2e/api_bank_accounts_test.go b/test/e2e/api_bank_accounts_test.go index 3601cf2a..961be090 100644 --- a/test/e2e/api_bank_accounts_test.go +++ b/test/e2e/api_bank_accounts_test.go @@ -13,236 +13,237 @@ import ( "github.com/google/uuid" "github.com/formancehq/payments/pkg/testserver" - . "github.com/formancehq/payments/pkg/testserver" . "github.com/onsi/ginkgo/v2" . "github.com/onsi/gomega" ) -var _ = Context("Payments API Bank Accounts", func() { - var ( - db = UseTemplatedDatabase() - ctx = logging.TestingContext() - - accountNumber = "123456789" - iban = "DE89370400440532013000" - createRequest v3.BankAccountsCreateRequest - v2createRequest v2.BankAccountsCreateRequest - - app *utils.Deferred[*testserver.Server] - ) - - app = testserver.NewTestServer(func() Configuration { - return Configuration{ - Stack: stack, - PostgresConfiguration: db.GetValue().ConnectionOptions(), - TemporalNamespace: temporalServer.GetValue().DefaultNamespace(), - TemporalAddress: temporalServer.GetValue().Address(), - Output: GinkgoWriter, - } - }) - - createRequest = v3.BankAccountsCreateRequest{ - Name: "foo", - AccountNumber: &accountNumber, - IBAN: &iban, - } - v2createRequest = v2.BankAccountsCreateRequest{ - Name: "foo", - AccountNumber: &accountNumber, - IBAN: &iban, - } - - When("creating a new bank account with v3", func() { +var _ = Describe("Payments API Bank Accounts", func() { + Context("API requests", func() { var ( - ver int - createResponse struct{ Data string } - getResponse struct{ Data models.BankAccount } - err error - ) - JustBeforeEach(func() { - ver = 3 - err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createResponse) - }) - It("should be ok", func() { - Expect(err).To(BeNil()) - id, err := uuid.Parse(createResponse.Data) - Expect(err).To(BeNil()) - err = GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) - Expect(err).To(BeNil()) - Expect(getResponse.Data.ID.String()).To(Equal(id.String())) - }) - }) + postgres = UseTemplatedDatabase() + ctx = logging.TestingContext() - When("creating a new bank account with v2", func() { - var ( - ver int - createResponse struct{ Data v2.BankAccountResponse } - getResponse struct{ Data models.BankAccount } - err error - ) - JustBeforeEach(func() { - ver = 2 - err = CreateBankAccount(ctx, app.GetValue(), ver, v2createRequest, &createResponse) - }) - It("should be ok", func() { - Expect(err).To(BeNil()) - id, err := uuid.Parse(createResponse.Data.ID) - Expect(err).To(BeNil()) - err = GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) - Expect(err).To(BeNil()) - Expect(getResponse.Data.ID.String()).To(Equal(id.String())) - }) - }) + accountNumber = "123456789" + iban = "DE89370400440532013000" + createRequest v3.BankAccountsCreateRequest + v2createRequest v2.BankAccountsCreateRequest - When("forwarding a bank account to a connector with v3", func() { - var ( - ver int - createRes struct{ Data string } - forwardReq v3.BankAccountsForwardToConnectorRequest - connectorRes struct{ Data string } - res struct{ Data models.Task } - err error - id uuid.UUID + app *utils.Deferred[*testserver.Server] ) - JustBeforeEach(func() { - ver = 3 - err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) - Expect(err).To(BeNil()) - id, err = uuid.Parse(createRes.Data) - Expect(err).To(BeNil()) - - connectorConf := ConnectorConf{ - Name: fmt.Sprintf("connector-%s", id.String()), - PollingPeriod: "2m", - PageSize: 30, - APIKey: "key", - Endpoint: "http://example.com", - } - err := InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) - Expect(err).To(BeNil()) - }) - - It("should fail when connector ID is invalid", func() { - forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} - err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("400")) - }) - It("should be ok when connector is installed", func() { - forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} - err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) - Expect(err).To(BeNil()) - Expect(res.Data.ID.Reference).To(ContainSubstring(id.String())) - Expect(res.Data.ID.Reference).To(ContainSubstring(connectorRes.Data)) - Expect(res.Data.ConnectorID.String()).To(ContainSubstring(connectorRes.Data)) - }) - }) - When("forwarding a bank account to a connector with v2", func() { - var ( - ver int - createRes struct{ Data v2.BankAccountResponse } - forwardReq v2.BankAccountsForwardToConnectorRequest - connectorRes struct{ Data string } - res struct{ Data v2.BankAccountResponse } - err error - id uuid.UUID - ) - JustBeforeEach(func() { - ver = 2 - err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) - Expect(err).To(BeNil()) - id, err = uuid.Parse(createRes.Data.ID) - Expect(err).To(BeNil()) - connectorConf := ConnectorConf{ - Name: fmt.Sprintf("connector-%s", id.String()), - PollingPeriod: "2m", - PageSize: 30, - APIKey: "key", - Endpoint: "http://example.com", + app = testserver.NewTestServer(func() testserver.Configuration { + return testserver.Configuration{ + Stack: stack, + PostgresConfiguration: postgres.GetValue().ConnectionOptions(), + TemporalNamespace: temporalServer.GetValue().DefaultNamespace(), + TemporalAddress: temporalServer.GetValue().Address(), + Output: GinkgoWriter, } - err := InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) - Expect(err).To(BeNil()) - }) - It("should fail when connector ID is invalid", func() { - forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} - err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("400")) - }) - It("should fail immediately with error because method is unimplemented on plugin", func() { - forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} - err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("UNIMPLEMENTED")) - }) - }) - - When("updating bank account metadata with v3", func() { - var ( - ver int - createRes struct{ Data string } - res struct{ Data models.BankAccount } - req v3.BankAccountsUpdateMetadataRequest - err error - id uuid.UUID - ) - JustBeforeEach(func() { - ver = 3 - err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) - Expect(err).To(BeNil()) - id, err = uuid.Parse(createRes.Data) - Expect(err).To(BeNil()) }) - It("should fail when metadata is invalid", func() { - req = v3.BankAccountsUpdateMetadataRequest{} - err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("400")) - }) - It("should be ok when metadata is valid", func() { - req = v3.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} - err = UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) - Expect(err).To(BeNil()) - err = GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) - Expect(err).To(BeNil()) - Expect(res.Data.ID.String()).To(Equal(id.String())) - Expect(res.Data.Metadata).To(Equal(req.Metadata)) - }) - }) - - When("updating bank account metadata with v2", func() { - var ( - ver int - createRes struct{ Data v2.BankAccountResponse } - res struct{ Data models.BankAccount } - req v2.BankAccountsUpdateMetadataRequest - err error - id uuid.UUID - ) - JustBeforeEach(func() { - ver = 2 - err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) - Expect(err).To(BeNil()) - id, err = uuid.Parse(createRes.Data.ID) - Expect(err).To(BeNil()) - }) + createRequest = v3.BankAccountsCreateRequest{ + Name: "foo", + AccountNumber: &accountNumber, + IBAN: &iban, + } + v2createRequest = v2.BankAccountsCreateRequest{ + Name: "foo", + AccountNumber: &accountNumber, + IBAN: &iban, + } - It("should fail when metadata is invalid", func() { - req = v2.BankAccountsUpdateMetadataRequest{} - err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("400")) - }) - It("should be ok when metadata is valid", func() { - req = v2.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} - err = UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) - Expect(err).To(BeNil()) - err = GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) - Expect(err).To(BeNil()) - Expect(res.Data.ID.String()).To(Equal(id.String())) - Expect(res.Data.Metadata).To(Equal(req.Metadata)) + When("creating a new bank account with v3", func() { + var ( + ver int + createResponse struct{ Data string } + getResponse struct{ Data models.BankAccount } + err error + ) + JustBeforeEach(func() { + ver = 3 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createResponse) + }) + It("should be ok", func() { + Expect(err).To(BeNil()) + id, err := uuid.Parse(createResponse.Data) + Expect(err).To(BeNil()) + err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) + Expect(err).To(BeNil()) + Expect(getResponse.Data.ID.String()).To(Equal(id.String())) + }) + }) + + When("creating a new bank account with v2", func() { + var ( + ver int + createResponse struct{ Data v2.BankAccountResponse } + getResponse struct{ Data models.BankAccount } + err error + ) + JustBeforeEach(func() { + ver = 2 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, v2createRequest, &createResponse) + }) + It("should be ok", func() { + Expect(err).To(BeNil()) + id, err := uuid.Parse(createResponse.Data.ID) + Expect(err).To(BeNil()) + err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) + Expect(err).To(BeNil()) + Expect(getResponse.Data.ID.String()).To(Equal(id.String())) + }) + }) + + When("forwarding a bank account to a connector with v3", func() { + var ( + ver int + createRes struct{ Data string } + forwardReq v3.BankAccountsForwardToConnectorRequest + connectorRes struct{ Data string } + res struct{ Data models.Task } + err error + id uuid.UUID + ) + JustBeforeEach(func() { + ver = 3 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + Expect(err).To(BeNil()) + id, err = uuid.Parse(createRes.Data) + Expect(err).To(BeNil()) + + connectorConf := ConnectorConf{ + Name: fmt.Sprintf("connector-%s", id.String()), + PollingPeriod: "2m", + PageSize: 30, + APIKey: "key", + Endpoint: "http://example.com", + } + err := testserver.InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) + Expect(err).To(BeNil()) + }) + + It("should fail when connector ID is invalid", func() { + forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("400")) + }) + It("should be ok when connector is installed", func() { + forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + Expect(err).To(BeNil()) + Expect(res.Data.ID.Reference).To(ContainSubstring(id.String())) + Expect(res.Data.ID.Reference).To(ContainSubstring(connectorRes.Data)) + Expect(res.Data.ConnectorID.String()).To(ContainSubstring(connectorRes.Data)) + }) + }) + + When("forwarding a bank account to a connector with v2", func() { + var ( + ver int + createRes struct{ Data v2.BankAccountResponse } + forwardReq v2.BankAccountsForwardToConnectorRequest + connectorRes struct{ Data string } + res struct{ Data v2.BankAccountResponse } + err error + id uuid.UUID + ) + JustBeforeEach(func() { + ver = 2 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + Expect(err).To(BeNil()) + id, err = uuid.Parse(createRes.Data.ID) + Expect(err).To(BeNil()) + connectorConf := ConnectorConf{ + Name: fmt.Sprintf("connector-%s", id.String()), + PollingPeriod: "2m", + PageSize: 30, + APIKey: "key", + Endpoint: "http://example.com", + } + err := testserver.InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) + Expect(err).To(BeNil()) + }) + It("should fail when connector ID is invalid", func() { + forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("400")) + }) + It("should fail immediately with error because method is unimplemented on plugin", func() { + forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("UNIMPLEMENTED")) + }) + }) + + When("updating bank account metadata with v3", func() { + var ( + ver int + createRes struct{ Data string } + res struct{ Data models.BankAccount } + req v3.BankAccountsUpdateMetadataRequest + err error + id uuid.UUID + ) + JustBeforeEach(func() { + ver = 3 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + Expect(err).To(BeNil()) + id, err = uuid.Parse(createRes.Data) + Expect(err).To(BeNil()) + }) + + It("should fail when metadata is invalid", func() { + req = v3.BankAccountsUpdateMetadataRequest{} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("400")) + }) + It("should be ok when metadata is valid", func() { + req = v3.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} + err = testserver.UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) + Expect(err).To(BeNil()) + err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) + Expect(err).To(BeNil()) + Expect(res.Data.ID.String()).To(Equal(id.String())) + Expect(res.Data.Metadata).To(Equal(req.Metadata)) + }) + }) + + When("updating bank account metadata with v2", func() { + var ( + ver int + createRes struct{ Data v2.BankAccountResponse } + res struct{ Data models.BankAccount } + req v2.BankAccountsUpdateMetadataRequest + err error + id uuid.UUID + ) + JustBeforeEach(func() { + ver = 2 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + Expect(err).To(BeNil()) + id, err = uuid.Parse(createRes.Data.ID) + Expect(err).To(BeNil()) + }) + + It("should fail when metadata is invalid", func() { + req = v2.BankAccountsUpdateMetadataRequest{} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("400")) + }) + It("should be ok when metadata is valid", func() { + req = v2.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} + err = testserver.UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) + Expect(err).To(BeNil()) + err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) + Expect(err).To(BeNil()) + Expect(res.Data.ID.String()).To(Equal(id.String())) + Expect(res.Data.Metadata).To(Equal(req.Metadata)) + }) }) }) }) From 7387e9b917774dd618747a9596852bfa5c33fb10 Mon Sep 17 00:00:00 2001 From: Crimson Thompson Date: Tue, 26 Nov 2024 10:00:00 +0100 Subject: [PATCH 2/6] fix --- test/e2e/api_bank_accounts_test.go | 434 ++++++++++++++--------------- 1 file changed, 216 insertions(+), 218 deletions(-) diff --git a/test/e2e/api_bank_accounts_test.go b/test/e2e/api_bank_accounts_test.go index 961be090..c7ed9609 100644 --- a/test/e2e/api_bank_accounts_test.go +++ b/test/e2e/api_bank_accounts_test.go @@ -17,233 +17,231 @@ import ( . "github.com/onsi/gomega" ) -var _ = Describe("Payments API Bank Accounts", func() { - Context("API requests", func() { +var _ = Context("Payments API Bank Accounts", func() { + var ( + postgres = UseTemplatedDatabase() + ctx = logging.TestingContext() + + accountNumber = "123456789" + iban = "DE89370400440532013000" + createRequest v3.BankAccountsCreateRequest + v2createRequest v2.BankAccountsCreateRequest + + app *utils.Deferred[*testserver.Server] + ) + + app = testserver.NewTestServer(func() testserver.Configuration { + return testserver.Configuration{ + Stack: stack, + PostgresConfiguration: postgres.GetValue().ConnectionOptions(), + TemporalNamespace: temporalServer.GetValue().DefaultNamespace(), + TemporalAddress: temporalServer.GetValue().Address(), + Output: GinkgoWriter, + } + }) + + createRequest = v3.BankAccountsCreateRequest{ + Name: "foo", + AccountNumber: &accountNumber, + IBAN: &iban, + } + v2createRequest = v2.BankAccountsCreateRequest{ + Name: "foo", + AccountNumber: &accountNumber, + IBAN: &iban, + } + + When("creating a new bank account with v3", func() { var ( - postgres = UseTemplatedDatabase() - ctx = logging.TestingContext() + ver int + createResponse struct{ Data string } + getResponse struct{ Data models.BankAccount } + err error + ) + JustBeforeEach(func() { + ver = 3 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createResponse) + }) + It("should be ok", func() { + Expect(err).To(BeNil()) + id, err := uuid.Parse(createResponse.Data) + Expect(err).To(BeNil()) + err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) + Expect(err).To(BeNil()) + Expect(getResponse.Data.ID.String()).To(Equal(id.String())) + }) + }) - accountNumber = "123456789" - iban = "DE89370400440532013000" - createRequest v3.BankAccountsCreateRequest - v2createRequest v2.BankAccountsCreateRequest + When("creating a new bank account with v2", func() { + var ( + ver int + createResponse struct{ Data v2.BankAccountResponse } + getResponse struct{ Data models.BankAccount } + err error + ) + JustBeforeEach(func() { + ver = 2 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, v2createRequest, &createResponse) + }) + It("should be ok", func() { + Expect(err).To(BeNil()) + id, err := uuid.Parse(createResponse.Data.ID) + Expect(err).To(BeNil()) + err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) + Expect(err).To(BeNil()) + Expect(getResponse.Data.ID.String()).To(Equal(id.String())) + }) + }) - app *utils.Deferred[*testserver.Server] + When("forwarding a bank account to a connector with v3", func() { + var ( + ver int + createRes struct{ Data string } + forwardReq v3.BankAccountsForwardToConnectorRequest + connectorRes struct{ Data string } + res struct{ Data models.Task } + err error + id uuid.UUID ) + JustBeforeEach(func() { + ver = 3 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + Expect(err).To(BeNil()) + id, err = uuid.Parse(createRes.Data) + Expect(err).To(BeNil()) + + connectorConf := ConnectorConf{ + Name: fmt.Sprintf("connector-%s", id.String()), + PollingPeriod: "2m", + PageSize: 30, + APIKey: "key", + Endpoint: "http://example.com", + } + err := testserver.InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) + Expect(err).To(BeNil()) + }) + + It("should fail when connector ID is invalid", func() { + forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("400")) + }) + It("should be ok when connector is installed", func() { + forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + Expect(err).To(BeNil()) + Expect(res.Data.ID.Reference).To(ContainSubstring(id.String())) + Expect(res.Data.ID.Reference).To(ContainSubstring(connectorRes.Data)) + Expect(res.Data.ConnectorID.String()).To(ContainSubstring(connectorRes.Data)) + }) + }) - app = testserver.NewTestServer(func() testserver.Configuration { - return testserver.Configuration{ - Stack: stack, - PostgresConfiguration: postgres.GetValue().ConnectionOptions(), - TemporalNamespace: temporalServer.GetValue().DefaultNamespace(), - TemporalAddress: temporalServer.GetValue().Address(), - Output: GinkgoWriter, + When("forwarding a bank account to a connector with v2", func() { + var ( + ver int + createRes struct{ Data v2.BankAccountResponse } + forwardReq v2.BankAccountsForwardToConnectorRequest + connectorRes struct{ Data string } + res struct{ Data v2.BankAccountResponse } + err error + id uuid.UUID + ) + JustBeforeEach(func() { + ver = 2 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + Expect(err).To(BeNil()) + id, err = uuid.Parse(createRes.Data.ID) + Expect(err).To(BeNil()) + connectorConf := ConnectorConf{ + Name: fmt.Sprintf("connector-%s", id.String()), + PollingPeriod: "2m", + PageSize: 30, + APIKey: "key", + Endpoint: "http://example.com", } + err := testserver.InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) + Expect(err).To(BeNil()) + }) + It("should fail when connector ID is invalid", func() { + forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("400")) }) + It("should fail immediately with error because method is unimplemented on plugin", func() { + forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("UNIMPLEMENTED")) + }) + }) - createRequest = v3.BankAccountsCreateRequest{ - Name: "foo", - AccountNumber: &accountNumber, - IBAN: &iban, - } - v2createRequest = v2.BankAccountsCreateRequest{ - Name: "foo", - AccountNumber: &accountNumber, - IBAN: &iban, - } + When("updating bank account metadata with v3", func() { + var ( + ver int + createRes struct{ Data string } + res struct{ Data models.BankAccount } + req v3.BankAccountsUpdateMetadataRequest + err error + id uuid.UUID + ) + JustBeforeEach(func() { + ver = 3 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + Expect(err).To(BeNil()) + id, err = uuid.Parse(createRes.Data) + Expect(err).To(BeNil()) + }) - When("creating a new bank account with v3", func() { - var ( - ver int - createResponse struct{ Data string } - getResponse struct{ Data models.BankAccount } - err error - ) - JustBeforeEach(func() { - ver = 3 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createResponse) - }) - It("should be ok", func() { - Expect(err).To(BeNil()) - id, err := uuid.Parse(createResponse.Data) - Expect(err).To(BeNil()) - err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) - Expect(err).To(BeNil()) - Expect(getResponse.Data.ID.String()).To(Equal(id.String())) - }) - }) - - When("creating a new bank account with v2", func() { - var ( - ver int - createResponse struct{ Data v2.BankAccountResponse } - getResponse struct{ Data models.BankAccount } - err error - ) - JustBeforeEach(func() { - ver = 2 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, v2createRequest, &createResponse) - }) - It("should be ok", func() { - Expect(err).To(BeNil()) - id, err := uuid.Parse(createResponse.Data.ID) - Expect(err).To(BeNil()) - err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) - Expect(err).To(BeNil()) - Expect(getResponse.Data.ID.String()).To(Equal(id.String())) - }) - }) - - When("forwarding a bank account to a connector with v3", func() { - var ( - ver int - createRes struct{ Data string } - forwardReq v3.BankAccountsForwardToConnectorRequest - connectorRes struct{ Data string } - res struct{ Data models.Task } - err error - id uuid.UUID - ) - JustBeforeEach(func() { - ver = 3 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) - Expect(err).To(BeNil()) - id, err = uuid.Parse(createRes.Data) - Expect(err).To(BeNil()) - - connectorConf := ConnectorConf{ - Name: fmt.Sprintf("connector-%s", id.String()), - PollingPeriod: "2m", - PageSize: 30, - APIKey: "key", - Endpoint: "http://example.com", - } - err := testserver.InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) - Expect(err).To(BeNil()) - }) - - It("should fail when connector ID is invalid", func() { - forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("400")) - }) - It("should be ok when connector is installed", func() { - forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) - Expect(err).To(BeNil()) - Expect(res.Data.ID.Reference).To(ContainSubstring(id.String())) - Expect(res.Data.ID.Reference).To(ContainSubstring(connectorRes.Data)) - Expect(res.Data.ConnectorID.String()).To(ContainSubstring(connectorRes.Data)) - }) - }) - - When("forwarding a bank account to a connector with v2", func() { - var ( - ver int - createRes struct{ Data v2.BankAccountResponse } - forwardReq v2.BankAccountsForwardToConnectorRequest - connectorRes struct{ Data string } - res struct{ Data v2.BankAccountResponse } - err error - id uuid.UUID - ) - JustBeforeEach(func() { - ver = 2 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) - Expect(err).To(BeNil()) - id, err = uuid.Parse(createRes.Data.ID) - Expect(err).To(BeNil()) - connectorConf := ConnectorConf{ - Name: fmt.Sprintf("connector-%s", id.String()), - PollingPeriod: "2m", - PageSize: 30, - APIKey: "key", - Endpoint: "http://example.com", - } - err := testserver.InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) - Expect(err).To(BeNil()) - }) - It("should fail when connector ID is invalid", func() { - forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("400")) - }) - It("should fail immediately with error because method is unimplemented on plugin", func() { - forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("UNIMPLEMENTED")) - }) - }) - - When("updating bank account metadata with v3", func() { - var ( - ver int - createRes struct{ Data string } - res struct{ Data models.BankAccount } - req v3.BankAccountsUpdateMetadataRequest - err error - id uuid.UUID - ) - JustBeforeEach(func() { - ver = 3 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) - Expect(err).To(BeNil()) - id, err = uuid.Parse(createRes.Data) - Expect(err).To(BeNil()) - }) - - It("should fail when metadata is invalid", func() { - req = v3.BankAccountsUpdateMetadataRequest{} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("400")) - }) - It("should be ok when metadata is valid", func() { - req = v3.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} - err = testserver.UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) - Expect(err).To(BeNil()) - err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) - Expect(err).To(BeNil()) - Expect(res.Data.ID.String()).To(Equal(id.String())) - Expect(res.Data.Metadata).To(Equal(req.Metadata)) - }) - }) - - When("updating bank account metadata with v2", func() { - var ( - ver int - createRes struct{ Data v2.BankAccountResponse } - res struct{ Data models.BankAccount } - req v2.BankAccountsUpdateMetadataRequest - err error - id uuid.UUID - ) - JustBeforeEach(func() { - ver = 2 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) - Expect(err).To(BeNil()) - id, err = uuid.Parse(createRes.Data.ID) - Expect(err).To(BeNil()) - }) - - It("should fail when metadata is invalid", func() { - req = v2.BankAccountsUpdateMetadataRequest{} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) - Expect(err).NotTo(BeNil()) - Expect(err.Error()).To(ContainSubstring("400")) - }) - It("should be ok when metadata is valid", func() { - req = v2.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} - err = testserver.UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) - Expect(err).To(BeNil()) - err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) - Expect(err).To(BeNil()) - Expect(res.Data.ID.String()).To(Equal(id.String())) - Expect(res.Data.Metadata).To(Equal(req.Metadata)) - }) + It("should fail when metadata is invalid", func() { + req = v3.BankAccountsUpdateMetadataRequest{} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("400")) + }) + It("should be ok when metadata is valid", func() { + req = v3.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} + err = testserver.UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) + Expect(err).To(BeNil()) + err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) + Expect(err).To(BeNil()) + Expect(res.Data.ID.String()).To(Equal(id.String())) + Expect(res.Data.Metadata).To(Equal(req.Metadata)) + }) + }) + + When("updating bank account metadata with v2", func() { + var ( + ver int + createRes struct{ Data v2.BankAccountResponse } + res struct{ Data models.BankAccount } + req v2.BankAccountsUpdateMetadataRequest + err error + id uuid.UUID + ) + JustBeforeEach(func() { + ver = 2 + err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + Expect(err).To(BeNil()) + id, err = uuid.Parse(createRes.Data.ID) + Expect(err).To(BeNil()) + }) + + It("should fail when metadata is invalid", func() { + req = v2.BankAccountsUpdateMetadataRequest{} + err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) + Expect(err).NotTo(BeNil()) + Expect(err.Error()).To(ContainSubstring("400")) + }) + It("should be ok when metadata is valid", func() { + req = v2.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} + err = testserver.UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) + Expect(err).To(BeNil()) + err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) + Expect(err).To(BeNil()) + Expect(res.Data.ID.String()).To(Equal(id.String())) + Expect(res.Data.Metadata).To(Equal(req.Metadata)) }) }) }) From 4f22a6e31b82009183bdb14ab48b8bdecf989271 Mon Sep 17 00:00:00 2001 From: Crimson Thompson Date: Tue, 26 Nov 2024 10:04:47 +0100 Subject: [PATCH 3/6] fix --- test/e2e/api_bank_accounts_test.go | 54 +++++++++++++++--------------- 1 file changed, 27 insertions(+), 27 deletions(-) diff --git a/test/e2e/api_bank_accounts_test.go b/test/e2e/api_bank_accounts_test.go index c7ed9609..fb67bb32 100644 --- a/test/e2e/api_bank_accounts_test.go +++ b/test/e2e/api_bank_accounts_test.go @@ -12,28 +12,28 @@ import ( "github.com/formancehq/payments/internal/models" "github.com/google/uuid" - "github.com/formancehq/payments/pkg/testserver" + . "github.com/formancehq/payments/pkg/testserver" . "github.com/onsi/ginkgo/v2" . "github.com/onsi/gomega" ) var _ = Context("Payments API Bank Accounts", func() { var ( - postgres = UseTemplatedDatabase() - ctx = logging.TestingContext() + db = UseTemplatedDatabase() + ctx = logging.TestingContext() accountNumber = "123456789" iban = "DE89370400440532013000" createRequest v3.BankAccountsCreateRequest v2createRequest v2.BankAccountsCreateRequest - app *utils.Deferred[*testserver.Server] + app *utils.Deferred[*Server] ) - app = testserver.NewTestServer(func() testserver.Configuration { - return testserver.Configuration{ + app = NewTestServer(func() Configuration { + return Configuration{ Stack: stack, - PostgresConfiguration: postgres.GetValue().ConnectionOptions(), + PostgresConfiguration: db.GetValue().ConnectionOptions(), TemporalNamespace: temporalServer.GetValue().DefaultNamespace(), TemporalAddress: temporalServer.GetValue().Address(), Output: GinkgoWriter, @@ -60,13 +60,13 @@ var _ = Context("Payments API Bank Accounts", func() { ) JustBeforeEach(func() { ver = 3 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createResponse) + err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createResponse) }) It("should be ok", func() { Expect(err).To(BeNil()) id, err := uuid.Parse(createResponse.Data) Expect(err).To(BeNil()) - err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) + err = GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) Expect(err).To(BeNil()) Expect(getResponse.Data.ID.String()).To(Equal(id.String())) }) @@ -81,13 +81,13 @@ var _ = Context("Payments API Bank Accounts", func() { ) JustBeforeEach(func() { ver = 2 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, v2createRequest, &createResponse) + err = CreateBankAccount(ctx, app.GetValue(), ver, v2createRequest, &createResponse) }) It("should be ok", func() { Expect(err).To(BeNil()) id, err := uuid.Parse(createResponse.Data.ID) Expect(err).To(BeNil()) - err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) + err = GetBankAccount(ctx, app.GetValue(), ver, id.String(), &getResponse) Expect(err).To(BeNil()) Expect(getResponse.Data.ID.String()).To(Equal(id.String())) }) @@ -105,7 +105,7 @@ var _ = Context("Payments API Bank Accounts", func() { ) JustBeforeEach(func() { ver = 3 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) Expect(err).To(BeNil()) id, err = uuid.Parse(createRes.Data) Expect(err).To(BeNil()) @@ -117,19 +117,19 @@ var _ = Context("Payments API Bank Accounts", func() { APIKey: "key", Endpoint: "http://example.com", } - err := testserver.InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) + err := InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) Expect(err).To(BeNil()) }) It("should fail when connector ID is invalid", func() { forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) Expect(err).NotTo(BeNil()) Expect(err.Error()).To(ContainSubstring("400")) }) It("should be ok when connector is installed", func() { forwardReq = v3.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) Expect(err).To(BeNil()) Expect(res.Data.ID.Reference).To(ContainSubstring(id.String())) Expect(res.Data.ID.Reference).To(ContainSubstring(connectorRes.Data)) @@ -149,7 +149,7 @@ var _ = Context("Payments API Bank Accounts", func() { ) JustBeforeEach(func() { ver = 2 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) Expect(err).To(BeNil()) id, err = uuid.Parse(createRes.Data.ID) Expect(err).To(BeNil()) @@ -160,18 +160,18 @@ var _ = Context("Payments API Bank Accounts", func() { APIKey: "key", Endpoint: "http://example.com", } - err := testserver.InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) + err := InstallConnector(ctx, app.GetValue(), ver, connectorConf, &connectorRes) Expect(err).To(BeNil()) }) It("should fail when connector ID is invalid", func() { forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: "invalid"} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) Expect(err).NotTo(BeNil()) Expect(err.Error()).To(ContainSubstring("400")) }) It("should fail immediately with error because method is unimplemented on plugin", func() { forwardReq = v2.BankAccountsForwardToConnectorRequest{ConnectorID: connectorRes.Data} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) + err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &forwardReq, &res) Expect(err).NotTo(BeNil()) Expect(err.Error()).To(ContainSubstring("UNIMPLEMENTED")) }) @@ -188,7 +188,7 @@ var _ = Context("Payments API Bank Accounts", func() { ) JustBeforeEach(func() { ver = 3 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) Expect(err).To(BeNil()) id, err = uuid.Parse(createRes.Data) Expect(err).To(BeNil()) @@ -196,15 +196,15 @@ var _ = Context("Payments API Bank Accounts", func() { It("should fail when metadata is invalid", func() { req = v3.BankAccountsUpdateMetadataRequest{} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) + err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) Expect(err).NotTo(BeNil()) Expect(err.Error()).To(ContainSubstring("400")) }) It("should be ok when metadata is valid", func() { req = v3.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} - err = testserver.UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) + err = UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) Expect(err).To(BeNil()) - err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) + err = GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) Expect(err).To(BeNil()) Expect(res.Data.ID.String()).To(Equal(id.String())) Expect(res.Data.Metadata).To(Equal(req.Metadata)) @@ -222,7 +222,7 @@ var _ = Context("Payments API Bank Accounts", func() { ) JustBeforeEach(func() { ver = 2 - err = testserver.CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) + err = CreateBankAccount(ctx, app.GetValue(), ver, createRequest, &createRes) Expect(err).To(BeNil()) id, err = uuid.Parse(createRes.Data.ID) Expect(err).To(BeNil()) @@ -230,15 +230,15 @@ var _ = Context("Payments API Bank Accounts", func() { It("should fail when metadata is invalid", func() { req = v2.BankAccountsUpdateMetadataRequest{} - err = testserver.ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) + err = ForwardBankAccount(ctx, app.GetValue(), ver, id.String(), &req, &res) Expect(err).NotTo(BeNil()) Expect(err.Error()).To(ContainSubstring("400")) }) It("should be ok when metadata is valid", func() { req = v2.BankAccountsUpdateMetadataRequest{Metadata: map[string]string{"key": "val"}} - err = testserver.UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) + err = UpdateBankAccountMetadata(ctx, app.GetValue(), ver, id.String(), &req, nil) Expect(err).To(BeNil()) - err = testserver.GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) + err = GetBankAccount(ctx, app.GetValue(), ver, id.String(), &res) Expect(err).To(BeNil()) Expect(res.Data.ID.String()).To(Equal(id.String())) Expect(res.Data.Metadata).To(Equal(req.Metadata)) From 0ef0ec08d98cea435354ec56409c57427d7b8c62 Mon Sep 17 00:00:00 2001 From: Paul Nicolas Date: Tue, 26 Nov 2024 13:44:49 +0100 Subject: [PATCH 4/6] close conn when closing store --- internal/storage/connectors.go | 3 +++ internal/storage/storage.go | 13 ++++++++++++- 2 files changed, 15 insertions(+), 1 deletion(-) diff --git a/internal/storage/connectors.go b/internal/storage/connectors.go index f2006226..b45ddf1e 100644 --- a/internal/storage/connectors.go +++ b/internal/storage/connectors.go @@ -51,6 +51,9 @@ func (s *store) ListenConnectorsChanges(ctx context.Context, handlers HandlerCon if err != nil { return errors.Wrap(err, "cannot get connection") } + + s.conns = append(s.conns, conn) + if err := conn.Raw(func(driverConn any) error { listener := pgxlisten.Listener{ Connect: func(ctx context.Context) (*pgx.Conn, error) { diff --git a/internal/storage/storage.go b/internal/storage/storage.go index 39411afe..3f96f5f1 100644 --- a/internal/storage/storage.go +++ b/internal/storage/storage.go @@ -129,6 +129,7 @@ const encryptionOptions = "compress-algo=1, cipher-algo=aes256" type store struct { logger logging.Logger db *bun.DB + conns []bun.Conn configEncryptionKey string } @@ -141,5 +142,15 @@ func newStorage(logger logging.Logger, db *bun.DB, configEncryptionKey string) S } func (s *store) Close() error { - return s.db.Close() + if err := s.db.Close(); err != nil { + return err + } + + for _, conn := range s.conns { + if err := conn.Close(); err != nil { + return err + } + } + + return nil } From 494020791940f821d8f9f3765afee34b8906f2b7 Mon Sep 17 00:00:00 2001 From: Paul Nicolas Date: Tue, 26 Nov 2024 13:46:07 +0100 Subject: [PATCH 5/6] add mutex --- internal/storage/connectors.go | 2 ++ internal/storage/storage.go | 8 +++++++- 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/internal/storage/connectors.go b/internal/storage/connectors.go index b45ddf1e..e0715295 100644 --- a/internal/storage/connectors.go +++ b/internal/storage/connectors.go @@ -52,7 +52,9 @@ func (s *store) ListenConnectorsChanges(ctx context.Context, handlers HandlerCon return errors.Wrap(err, "cannot get connection") } + s.rwMutex.Lock() s.conns = append(s.conns, conn) + s.rwMutex.Unlock() if err := conn.Raw(func(driverConn any) error { listener := pgxlisten.Listener{ diff --git a/internal/storage/storage.go b/internal/storage/storage.go index 3f96f5f1..8effaa85 100644 --- a/internal/storage/storage.go +++ b/internal/storage/storage.go @@ -2,6 +2,7 @@ package storage import ( "context" + "sync" "time" "github.com/formancehq/go-libs/v2/bun/bunpaginate" @@ -129,8 +130,10 @@ const encryptionOptions = "compress-algo=1, cipher-algo=aes256" type store struct { logger logging.Logger db *bun.DB - conns []bun.Conn configEncryptionKey string + + conns []bun.Conn + rwMutex sync.RWMutex } func newStorage(logger logging.Logger, db *bun.DB, configEncryptionKey string) Storage { @@ -142,6 +145,9 @@ func newStorage(logger logging.Logger, db *bun.DB, configEncryptionKey string) S } func (s *store) Close() error { + s.rwMutex.Lock() + defer s.rwMutex.Unlock() + if err := s.db.Close(); err != nil { return err } From b4527e0d852b64438caf606c5aa2db76219ea0b5 Mon Sep 17 00:00:00 2001 From: Paul Nicolas Date: Tue, 26 Nov 2024 14:00:33 +0100 Subject: [PATCH 6/6] call close when service is cut --- internal/storage/module.go | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/internal/storage/module.go b/internal/storage/module.go index 8db90ce3..4fd5063a 100644 --- a/internal/storage/module.go +++ b/internal/storage/module.go @@ -1,6 +1,8 @@ package storage import ( + "context" + "github.com/formancehq/go-libs/v2/bun/bunconnect" "github.com/formancehq/go-libs/v2/logging" "github.com/formancehq/go-libs/v2/service" @@ -15,5 +17,12 @@ func Module(cmd *cobra.Command, connectionOptions bunconnect.ConnectionOptions, fx.Provide(func(logger logging.Logger, db *bun.DB) Storage { return newStorage(logger, db, configEncryptionKey) }), + fx.Invoke(func(s Storage, lc fx.Lifecycle) { + lc.Append(fx.Hook{ + OnStop: func(ctx context.Context) error { + return s.Close() + }, + }) + }), ) }