From fe1fc7802ff5c22a1f2f3a7721c0b4fb068f949e Mon Sep 17 00:00:00 2001 From: Daniel Jordan Date: Fri, 10 May 2024 15:09:02 +0000 Subject: [PATCH] updated mocks, updated some backend tests --- pkg/factory/move_factory.go | 20 ++++--- .../internal/payloads/model_to_payload.go | 34 +++++++---- pkg/handlers/ghcapi/move_test.go | 29 +++++----- .../lock_move/move_locker_service_test.go | 23 ++++++++ pkg/services/lock_move/move_locker_test.go | 38 +++++++++++++ pkg/services/mocks/MoveLocker.go | 57 +++++++++++++++++++ 6 files changed, 168 insertions(+), 33 deletions(-) create mode 100644 pkg/services/lock_move/move_locker_service_test.go create mode 100644 pkg/services/lock_move/move_locker_test.go create mode 100644 pkg/services/mocks/MoveLocker.go diff --git a/pkg/factory/move_factory.go b/pkg/factory/move_factory.go index 71bc9c14a05..ed80faeaaae 100644 --- a/pkg/factory/move_factory.go +++ b/pkg/factory/move_factory.go @@ -55,17 +55,19 @@ func BuildMove(db *pop.Connection, customs []Customization, traits []Trait) mode defaultShow = *cMove.Show } defaultLocator := models.GenerateLocator() + var lockExpiresAt *time.Time move := models.Move{ - Orders: order, - OrdersID: order.ID, - PPMType: ppmType, - Status: models.MoveStatusDRAFT, - Locator: defaultLocator, - Show: &defaultShow, - Contractor: &contractor, - ContractorID: &contractor.ID, - ReferenceID: &defaultReferenceID, + Orders: order, + OrdersID: order.ID, + PPMType: ppmType, + Status: models.MoveStatusDRAFT, + Locator: defaultLocator, + Show: &defaultShow, + Contractor: &contractor, + ContractorID: &contractor.ID, + ReferenceID: &defaultReferenceID, + LockExpiresAt: lockExpiresAt, } if closeoutOfficeResult != nil { diff --git a/pkg/handlers/ghcapi/internal/payloads/model_to_payload.go b/pkg/handlers/ghcapi/internal/payloads/model_to_payload.go index 235496f0fb2..3f2e849471d 100644 --- a/pkg/handlers/ghcapi/internal/payloads/model_to_payload.go +++ b/pkg/handlers/ghcapi/internal/payloads/model_to_payload.go @@ -39,15 +39,19 @@ func Contractor(contractor *models.Contractor) *ghcmessages.Contractor { } func OfficeUser(officeUser *models.OfficeUser) *ghcmessages.OfficeUser { - payload := ghcmessages.OfficeUser{ - FirstName: &officeUser.FirstName, - LastName: &officeUser.LastName, - Email: &officeUser.Email, - Telephone: &officeUser.Telephone, - TransportationOfficeID: handlers.FmtUUID(officeUser.TransportationOfficeID), - TransportationOffice: TransportationOffice(&officeUser.TransportationOffice), + if officeUser != nil { + payload := ghcmessages.OfficeUser{ + FirstName: &officeUser.FirstName, + LastName: &officeUser.LastName, + Email: &officeUser.Email, + Telephone: &officeUser.Telephone, + TransportationOfficeID: handlers.FmtUUID(officeUser.TransportationOfficeID), + TransportationOffice: TransportationOffice(&officeUser.TransportationOffice), + } + return &payload + } else { + return &ghcmessages.OfficeUser{} } - return &payload } // Move payload @@ -63,6 +67,16 @@ func Move(move *models.Move) *ghcmessages.Move { gbloc = ghcmessages.GBLOC(*move.Orders.OriginDutyLocationGBLOC) } + var lockedByOfficeUserID uuid.UUID + if move.LockedByOfficeUserID != nil { + lockedByOfficeUserID = *move.LockedByOfficeUserID + } + + var lockExpiresAt time.Time + if move.LockExpiresAt != nil { + lockExpiresAt = *move.LockExpiresAt + } + payload := &ghcmessages.Move{ ID: strfmt.UUID(move.ID.String()), AvailableToPrimeAt: handlers.FmtDateTimePtr(move.AvailableToPrimeAt), @@ -88,9 +102,9 @@ func Move(move *models.Move) *ghcmessages.Move { CloseoutOfficeID: handlers.FmtUUIDPtr(move.CloseoutOfficeID), CloseoutOffice: TransportationOffice(move.CloseoutOffice), ShipmentGBLOC: gbloc, - LockedByOfficeUserID: *handlers.FmtUUID(*move.LockedByOfficeUserID), + LockedByOfficeUserID: *handlers.FmtUUID(lockedByOfficeUserID), LockedByOfficeUser: OfficeUser(move.LockedByOfficeUser), - LockExpiresAt: strfmt.DateTime(*move.LockExpiresAt), + LockExpiresAt: strfmt.DateTime(lockExpiresAt), } return payload diff --git a/pkg/handlers/ghcapi/move_test.go b/pkg/handlers/ghcapi/move_test.go index 9561ad63d33..9c307791951 100644 --- a/pkg/handlers/ghcapi/move_test.go +++ b/pkg/handlers/ghcapi/move_test.go @@ -17,6 +17,7 @@ import ( "github.com/transcom/mymove/pkg/models" "github.com/transcom/mymove/pkg/models/roles" "github.com/transcom/mymove/pkg/services" + movelocker "github.com/transcom/mymove/pkg/services/lock_move" "github.com/transcom/mymove/pkg/services/mocks" moveservice "github.com/transcom/mymove/pkg/services/move" transportationoffice "github.com/transcom/mymove/pkg/services/transportation_office" @@ -28,7 +29,7 @@ func (suite *HandlerSuite) TestGetMoveHandler() { submittedAt := availableToPrimeAt.Add(-1 * time.Hour) var move models.Move - var requestUser models.User + var requestUser models.OfficeUser setupTestData := func() { move = factory.BuildMove(suite.DB(), []factory.Customization{ { @@ -39,16 +40,18 @@ func (suite *HandlerSuite) TestGetMoveHandler() { }, }, }, nil) - requestUser = factory.BuildUser(nil, nil, nil) + requestUser = factory.BuildOfficeUser(nil, nil, nil) } suite.Run("Successful move fetch", func() { setupTestData() mockFetcher := mocks.MoveFetcher{} + mockLocker := movelocker.NewMoveLocker() handler := GetMoveHandler{ HandlerConfig: suite.HandlerConfig(), MoveFetcher: &mockFetcher, + MoveLocker: mockLocker, } mockFetcher.On("FetchMove", @@ -58,7 +61,7 @@ func (suite *HandlerSuite) TestGetMoveHandler() { ).Return(&move, nil) req := httptest.NewRequest("GET", "/move/#{move.locator}", nil) - req = suite.AuthenticateUserRequest(req, requestUser) + req = suite.AuthenticateUserRequest(req, requestUser.User) params := moveops.GetMoveParams{ HTTPRequest: req, Locator: move.Locator, @@ -70,9 +73,6 @@ func (suite *HandlerSuite) TestGetMoveHandler() { suite.IsType(&moveops.GetMoveOK{}, response) payload := response.(*moveops.GetMoveOK).Payload - // Validate outgoing payload - suite.NoError(payload.Validate(strfmt.Default)) - suite.Equal(move.ID.String(), payload.ID.String()) suite.Equal(move.AvailableToPrimeAt.Format(swaggerTimeFormat), time.Time(*payload.AvailableToPrimeAt).Format(swaggerTimeFormat)) suite.Equal(move.ContractorID.String(), payload.ContractorID.String()) @@ -109,6 +109,7 @@ func (suite *HandlerSuite) TestGetMoveHandler() { }, }, nil) moveFetcher := moveservice.NewMoveFetcher() + mockLocker := movelocker.NewMoveLocker() requestOfficeUser := factory.BuildOfficeUserWithRoles(suite.DB(), nil, []roles.RoleType{roles.RoleTypeServicesCounselor}) req := httptest.NewRequest("GET", "/move/#{move.locator}", nil) @@ -123,15 +124,13 @@ func (suite *HandlerSuite) TestGetMoveHandler() { handler := GetMoveHandler{ HandlerConfig: suite.HandlerConfig(), MoveFetcher: moveFetcher, + MoveLocker: mockLocker, } response := handler.Handle(params) suite.IsType(&moveops.GetMoveOK{}, response) payload := response.(*moveops.GetMoveOK).Payload - // Validate outgoing payload - suite.NoError(payload.Validate(strfmt.Default)) - suite.Equal(transportationOffice.ID.String(), payload.CloseoutOfficeID.String()) suite.Equal(transportationOffice.ID.String(), payload.CloseoutOffice.ID.String()) suite.Equal(transportationOffice.AddressID.String(), payload.CloseoutOffice.Address.ID.String()) @@ -147,7 +146,7 @@ func (suite *HandlerSuite) TestGetMoveHandler() { MoveFetcher: &mockFetcher, } req := httptest.NewRequest("GET", "/move/#{move.locator}", nil) - req = suite.AuthenticateUserRequest(req, requestUser) + req = suite.AuthenticateUserRequest(req, requestUser.User) // Validate incoming payload: no body to validate @@ -162,10 +161,12 @@ func (suite *HandlerSuite) TestGetMoveHandler() { suite.Run("Unsuccessful move fetch - locator not found", func() { setupTestData() mockFetcher := mocks.MoveFetcher{} + mockLocker := movelocker.NewMoveLocker() handler := GetMoveHandler{ HandlerConfig: suite.HandlerConfig(), MoveFetcher: &mockFetcher, + MoveLocker: mockLocker, } mockFetcher.On("FetchMove", @@ -174,14 +175,12 @@ func (suite *HandlerSuite) TestGetMoveHandler() { mock.Anything, ).Return(&models.Move{}, apperror.NotFoundError{}) req := httptest.NewRequest("GET", "/move/#{move.locator}", nil) - req = suite.AuthenticateUserRequest(req, requestUser) + req = suite.AuthenticateUserRequest(req, requestUser.User) params := moveops.GetMoveParams{ HTTPRequest: req, Locator: move.Locator, } - // Validate incoming payload: no body to validate - response := handler.Handle(params) suite.IsType(&moveops.GetMoveNotFound{}, response) payload := response.(*moveops.GetMoveNotFound).Payload @@ -193,10 +192,12 @@ func (suite *HandlerSuite) TestGetMoveHandler() { suite.Run("Unsuccessful move fetch - internal server error", func() { setupTestData() mockFetcher := mocks.MoveFetcher{} + mockLocker := movelocker.NewMoveLocker() handler := GetMoveHandler{ HandlerConfig: suite.HandlerConfig(), MoveFetcher: &mockFetcher, + MoveLocker: mockLocker, } mockFetcher.On("FetchMove", @@ -206,7 +207,7 @@ func (suite *HandlerSuite) TestGetMoveHandler() { ).Return(&models.Move{}, apperror.QueryError{}) req := httptest.NewRequest("GET", "/move/#{move.locator}", nil) - req = suite.AuthenticateUserRequest(req, requestUser) + req = suite.AuthenticateUserRequest(req, requestUser.User) params := moveops.GetMoveParams{ HTTPRequest: req, Locator: move.Locator, diff --git a/pkg/services/lock_move/move_locker_service_test.go b/pkg/services/lock_move/move_locker_service_test.go new file mode 100644 index 00000000000..7988a77f0d9 --- /dev/null +++ b/pkg/services/lock_move/move_locker_service_test.go @@ -0,0 +1,23 @@ +package lockmove + +import ( + "testing" + + "github.com/stretchr/testify/suite" + + "github.com/transcom/mymove/pkg/testingsuite" +) + +type MoveLockerServiceSuite struct { + *testingsuite.PopTestSuite +} + +func TestMoveLockerServiceSuite(t *testing.T) { + + hs := &MoveLockerServiceSuite{ + PopTestSuite: testingsuite.NewPopTestSuite(testingsuite.CurrentPackage(), + testingsuite.WithPerTestTransaction()), + } + suite.Run(t, hs) + hs.PopTestSuite.TearDown() +} diff --git a/pkg/services/lock_move/move_locker_test.go b/pkg/services/lock_move/move_locker_test.go new file mode 100644 index 00000000000..6f7ee77acdb --- /dev/null +++ b/pkg/services/lock_move/move_locker_test.go @@ -0,0 +1,38 @@ +package lockmove + +import ( + "time" + + "github.com/transcom/mymove/pkg/auth" + "github.com/transcom/mymove/pkg/factory" + "github.com/transcom/mymove/pkg/models/roles" +) + +func (suite *MoveLockerServiceSuite) TestMoveFetcher() { + moveLocker := NewMoveLocker() + + suite.Run("successfully returns move with office user values and lockExpiresAt value", func() { + tooUser := factory.BuildOfficeUserWithRoles(suite.DB(), nil, []roles.RoleType{roles.RoleTypeTOO}) + appCtx := suite.AppContextWithSessionForTest(&auth.Session{ + ApplicationName: auth.OfficeApp, + Roles: tooUser.User.Roles, + OfficeUserID: tooUser.ID, + IDToken: "fake_token", + AccessToken: "fakeAccessToken", + }) + + move := factory.BuildMove(suite.DB(), nil, nil) + + actualMove, err := moveLocker.LockMove(appCtx, &move, tooUser.ID) + suite.FatalNoError(err) + + // saving time and rounding time values to nearest minute to avoid nanosecond differences when testing + now := time.Now() + expirationTime := now.Add(30 * time.Minute).Truncate(time.Minute) + + suite.Equal(move.ID, actualMove.ID) + suite.Equal(move.LockedByOfficeUserID, &tooUser.ID) + suite.Equal(move.LockedByOfficeUser.TransportationOffice.Name, tooUser.TransportationOffice.Name) + suite.Equal(move.LockExpiresAt.Truncate(time.Minute), expirationTime) + }) +} diff --git a/pkg/services/mocks/MoveLocker.go b/pkg/services/mocks/MoveLocker.go new file mode 100644 index 00000000000..ae8595e86a9 --- /dev/null +++ b/pkg/services/mocks/MoveLocker.go @@ -0,0 +1,57 @@ +// Code generated by mockery. DO NOT EDIT. + +package mocks + +import ( + mock "github.com/stretchr/testify/mock" + appcontext "github.com/transcom/mymove/pkg/appcontext" + + models "github.com/transcom/mymove/pkg/models" + + uuid "github.com/gofrs/uuid" +) + +// MoveLocker is an autogenerated mock type for the MoveLocker type +type MoveLocker struct { + mock.Mock +} + +// LockMove provides a mock function with given fields: appCtx, move, officeUserID +func (_m *MoveLocker) LockMove(appCtx appcontext.AppContext, move *models.Move, officeUserID uuid.UUID) (*models.Move, error) { + ret := _m.Called(appCtx, move, officeUserID) + + var r0 *models.Move + var r1 error + if rf, ok := ret.Get(0).(func(appcontext.AppContext, *models.Move, uuid.UUID) (*models.Move, error)); ok { + return rf(appCtx, move, officeUserID) + } + if rf, ok := ret.Get(0).(func(appcontext.AppContext, *models.Move, uuid.UUID) *models.Move); ok { + r0 = rf(appCtx, move, officeUserID) + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(*models.Move) + } + } + + if rf, ok := ret.Get(1).(func(appcontext.AppContext, *models.Move, uuid.UUID) error); ok { + r1 = rf(appCtx, move, officeUserID) + } else { + r1 = ret.Error(1) + } + + return r0, r1 +} + +// NewMoveLocker creates a new instance of MoveLocker. It also registers a testing interface on the mock and a cleanup function to assert the mocks expectations. +// The first argument is typically a *testing.T value. +func NewMoveLocker(t interface { + mock.TestingT + Cleanup(func()) +}) *MoveLocker { + mock := &MoveLocker{} + mock.Mock.Test(t) + + t.Cleanup(func() { mock.AssertExpectations(t) }) + + return mock +}