diff --git a/iwf/communication.go b/iwf/communication.go index e917316..8e2f7c5 100644 --- a/iwf/communication.go +++ b/iwf/communication.go @@ -7,5 +7,9 @@ type Communication interface { PublishInterstateChannel(channelName string, value interface{}) // below is for internal implementation - getToPublishInterStateChannel() map[string][]iwfidl.EncodedObject + communicationInternal } + +type communicationInternal interface { + GetToPublishInterStateChannel() map[string][]iwfidl.EncodedObject +} \ No newline at end of file diff --git a/iwf/communication_impl.go b/iwf/communication_impl.go index 1d22f3f..f7473f6 100644 --- a/iwf/communication_impl.go +++ b/iwf/communication_impl.go @@ -8,7 +8,7 @@ type communicationImpl struct { encoder ObjectEncoder } -func (c *communicationImpl) getToPublishInterStateChannel() map[string][]iwfidl.EncodedObject { +func (c *communicationImpl) GetToPublishInterStateChannel() map[string][]iwfidl.EncodedObject { return c.toPublishInterStateChannel } diff --git a/iwf/persistence.go b/iwf/persistence.go index ef22da6..bea199b 100644 --- a/iwf/persistence.go +++ b/iwf/persistence.go @@ -48,11 +48,14 @@ type Persistence interface { RecordEvent(key string, value interface{}) // below is for internal implementation - getToReturn() ( + persistenceInternal +} + +type persistenceInternal interface { + GetToReturn() ( dataObjectsToReturn []iwfidl.KeyValue, stateLocalToReturn []iwfidl.KeyValue, recordEvents []iwfidl.KeyValue, searchAttributes []iwfidl.SearchAttribute, ) } - diff --git a/iwf/persistence_impl.go b/iwf/persistence_impl.go index 7342407..47a71a4 100644 --- a/iwf/persistence_impl.go +++ b/iwf/persistence_impl.go @@ -249,7 +249,7 @@ func (p *persistenceImpl) RecordEvent(key string, value interface{}) { p.recordedEvents[key] = *v } -func (p *persistenceImpl) getToReturn() ( +func (p *persistenceImpl) GetToReturn() ( dataObjectsToReturn []iwfidl.KeyValue, stateLocalToReturn []iwfidl.KeyValue, recordEvents []iwfidl.KeyValue, diff --git a/iwf/worker_service_impl.go b/iwf/worker_service_impl.go index 53d6e78..25c6d00 100644 --- a/iwf/worker_service_impl.go +++ b/iwf/worker_service_impl.go @@ -31,7 +31,7 @@ func (w *workerServiceImpl) HandleWorkflowStateStart(ctx context.Context, reques return nil, err } - err = canNotRequestAndPublishTheSameInterStateChannel(comm.getToPublishInterStateChannel(), commandRequest) + err = canNotRequestAndPublishTheSameInterStateChannel(comm.GetToPublishInterStateChannel(), commandRequest) if err != nil { return nil, err } @@ -40,14 +40,14 @@ func (w *workerServiceImpl) HandleWorkflowStateStart(ctx context.Context, reques if err != nil { return nil, err } - publishings := toPublishing(comm.getToPublishInterStateChannel()) + publishings := toPublishing(comm.GetToPublishInterStateChannel()) resp = &iwfidl.WorkflowStateStartResponse{ CommandRequest: idlCommandRequest, } if len(publishings) > 0 { resp.PublishToInterStateChannel = publishings } - dataObjectsToReturn, stateLocalToReturn, recordedEvents, upsertSearchAttributes := pers.getToReturn() + dataObjectsToReturn, stateLocalToReturn, recordedEvents, upsertSearchAttributes := pers.GetToReturn() if len(dataObjectsToReturn) > 0 { resp.UpsertDataObjects = dataObjectsToReturn } @@ -119,11 +119,11 @@ func (w *workerServiceImpl) HandleWorkflowStateDecide(ctx context.Context, reque resp = &iwfidl.WorkflowStateDecideResponse{ StateDecision: idlDecision, } - publishings := toPublishing(comm.getToPublishInterStateChannel()) + publishings := toPublishing(comm.GetToPublishInterStateChannel()) if len(publishings) > 0 { resp.PublishToInterStateChannel = publishings } - dataObjectsToReturn, stateLocalToReturn, recordedEvents, upsertSearchAttributes := pers.getToReturn() + dataObjectsToReturn, stateLocalToReturn, recordedEvents, upsertSearchAttributes := pers.GetToReturn() if len(dataObjectsToReturn) > 0 { resp.UpsertDataObjects = dataObjectsToReturn } diff --git a/iwftest/README.md b/iwftest/README.md new file mode 100644 index 0000000..125c0a5 --- /dev/null +++ b/iwftest/README.md @@ -0,0 +1,70 @@ +## Unit tests APIs for iWF + +The APIs are generated by the below commands: +```shell + mockgen -source=iwf/persistence.go -package=iwftest -destination=iwftest/persistence.go + mockgen -source=iwf/communication.go -package=iwftest -destination=iwftest/communication.go + mockgen -source=iwf/workflow_context.go -package=iwftest -destination=iwftest/workflow_context.go +``` + +## Usage + +See the [samples](https://github.com/indeedeng/iwf-golang-samples) for more details: + +```go +package subscription + +import ( + "github.com/golang/mock/gomock" + "github.com/indeedeng/iwf-golang-sdk/iwf" + "github.com/indeedeng/iwf-golang-sdk/iwftest" + "github.com/stretchr/testify/assert" + "testing" + "time" +) + +var mockWfCtx *iwftest.MockWorkflowContext +var mockPersistence *iwftest.MockPersistence +var mockCommunication *iwftest.MockCommunication +var emptyCmdResults = iwf.CommandResults{} +var emptyObj = iwftest.NewTestObject(nil) +var mockSvc *MockMyService + +func beforeEach(t *testing.T) { + ctrl := gomock.NewController(t) + + mockSvc = NewMockMyService(ctrl) + mockWfCtx = iwftest.NewMockWorkflowContext(ctrl) + mockPersistence = iwftest.NewMockPersistence(ctrl) + mockCommunication = iwftest.NewMockCommunication(ctrl) +} + + +func TestInitState_Start(t *testing.T) { + beforeEach(t) + + state := NewInitState() + + mockPersistence.EXPECT().SetDataObject(keyCustomer, testCustomer) + cmdReq, err := state.Start(mockWfCtx, testCustomerObj, mockPersistence, mockCommunication) + assert.Nil(t, err) + assert.Equal(t, iwf.EmptyCommandRequest(), cmdReq) +} + + +func TestTrialState_Start(t *testing.T) { + beforeEach(t) + + state := NewTrialState(mockSvc) + + mockSvc.EXPECT().sendEmail(testCustomer.Email, gomock.Any(), gomock.Any()) + mockPersistence.EXPECT().GetDataObject(keyCustomer, gomock.Any()).SetArg(1, testCustomer) + cmdReq, err := state.Start(mockWfCtx, emptyObj, mockPersistence, mockCommunication) + assert.Nil(t, err) + firingTime := cmdReq.Commands[0].TimerCommand.FiringUnixTimestampSeconds + assert.Equal(t, iwf.AllCommandsCompletedRequest( + iwf.NewTimerCommand("", time.Unix(firingTime, 0)), + ), cmdReq) +} + +``` diff --git a/iwftest/communication.go b/iwftest/communication.go index afaee0a..563cc8e 100644 --- a/iwftest/communication.go +++ b/iwftest/communication.go @@ -34,6 +34,20 @@ func (m *MockCommunication) EXPECT() *MockCommunicationMockRecorder { return m.recorder } +// GetToPublishInterStateChannel mocks base method. +func (m *MockCommunication) GetToPublishInterStateChannel() map[string][]iwfidl.EncodedObject { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetToPublishInterStateChannel") + ret0, _ := ret[0].(map[string][]iwfidl.EncodedObject) + return ret0 +} + +// GetToPublishInterStateChannel indicates an expected call of GetToPublishInterStateChannel. +func (mr *MockCommunicationMockRecorder) GetToPublishInterStateChannel() *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetToPublishInterStateChannel", reflect.TypeOf((*MockCommunication)(nil).GetToPublishInterStateChannel)) +} + // PublishInterstateChannel mocks base method. func (m *MockCommunication) PublishInterstateChannel(channelName string, value interface{}) { m.ctrl.T.Helper() @@ -46,16 +60,39 @@ func (mr *MockCommunicationMockRecorder) PublishInterstateChannel(channelName, v return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "PublishInterstateChannel", reflect.TypeOf((*MockCommunication)(nil).PublishInterstateChannel), channelName, value) } -// getToPublishInterStateChannel mocks base method. -func (m *MockCommunication) getToPublishInterStateChannel() map[string][]iwfidl.EncodedObject { +// MockcommunicationInternal is a mock of communicationInternal interface. +type MockcommunicationInternal struct { + ctrl *gomock.Controller + recorder *MockcommunicationInternalMockRecorder +} + +// MockcommunicationInternalMockRecorder is the mock recorder for MockcommunicationInternal. +type MockcommunicationInternalMockRecorder struct { + mock *MockcommunicationInternal +} + +// NewMockcommunicationInternal creates a new mock instance. +func NewMockcommunicationInternal(ctrl *gomock.Controller) *MockcommunicationInternal { + mock := &MockcommunicationInternal{ctrl: ctrl} + mock.recorder = &MockcommunicationInternalMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockcommunicationInternal) EXPECT() *MockcommunicationInternalMockRecorder { + return m.recorder +} + +// GetToPublishInterStateChannel mocks base method. +func (m *MockcommunicationInternal) GetToPublishInterStateChannel() map[string][]iwfidl.EncodedObject { m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "getToPublishInterStateChannel") + ret := m.ctrl.Call(m, "GetToPublishInterStateChannel") ret0, _ := ret[0].(map[string][]iwfidl.EncodedObject) return ret0 } -// getToPublishInterStateChannel indicates an expected call of getToPublishInterStateChannel. -func (mr *MockCommunicationMockRecorder) getToPublishInterStateChannel() *gomock.Call { +// GetToPublishInterStateChannel indicates an expected call of GetToPublishInterStateChannel. +func (mr *MockcommunicationInternalMockRecorder) GetToPublishInterStateChannel() *gomock.Call { mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "getToPublishInterStateChannel", reflect.TypeOf((*MockCommunication)(nil).getToPublishInterStateChannel)) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetToPublishInterStateChannel", reflect.TypeOf((*MockcommunicationInternal)(nil).GetToPublishInterStateChannel)) } diff --git a/iwftest/persistence.go b/iwftest/persistence.go index 1904d49..f4ba1e6 100644 --- a/iwftest/persistence.go +++ b/iwftest/persistence.go @@ -157,6 +157,23 @@ func (mr *MockPersistenceMockRecorder) GetStateLocal(key, valuePtr interface{}) return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetStateLocal", reflect.TypeOf((*MockPersistence)(nil).GetStateLocal), key, valuePtr) } +// GetToReturn mocks base method. +func (m *MockPersistence) GetToReturn() ([]iwfidl.KeyValue, []iwfidl.KeyValue, []iwfidl.KeyValue, []iwfidl.SearchAttribute) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetToReturn") + ret0, _ := ret[0].([]iwfidl.KeyValue) + ret1, _ := ret[1].([]iwfidl.KeyValue) + ret2, _ := ret[2].([]iwfidl.KeyValue) + ret3, _ := ret[3].([]iwfidl.SearchAttribute) + return ret0, ret1, ret2, ret3 +} + +// GetToReturn indicates an expected call of GetToReturn. +func (mr *MockPersistenceMockRecorder) GetToReturn() *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetToReturn", reflect.TypeOf((*MockPersistence)(nil).GetToReturn)) +} + // RecordEvent mocks base method. func (m *MockPersistence) RecordEvent(key string, value interface{}) { m.ctrl.T.Helper() @@ -277,10 +294,33 @@ func (mr *MockPersistenceMockRecorder) SetStateLocal(key, value interface{}) *go return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "SetStateLocal", reflect.TypeOf((*MockPersistence)(nil).SetStateLocal), key, value) } -// getToReturn mocks base method. -func (m *MockPersistence) getToReturn() ([]iwfidl.KeyValue, []iwfidl.KeyValue, []iwfidl.KeyValue, []iwfidl.SearchAttribute) { +// MockpersistenceInternal is a mock of persistenceInternal interface. +type MockpersistenceInternal struct { + ctrl *gomock.Controller + recorder *MockpersistenceInternalMockRecorder +} + +// MockpersistenceInternalMockRecorder is the mock recorder for MockpersistenceInternal. +type MockpersistenceInternalMockRecorder struct { + mock *MockpersistenceInternal +} + +// NewMockpersistenceInternal creates a new mock instance. +func NewMockpersistenceInternal(ctrl *gomock.Controller) *MockpersistenceInternal { + mock := &MockpersistenceInternal{ctrl: ctrl} + mock.recorder = &MockpersistenceInternalMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockpersistenceInternal) EXPECT() *MockpersistenceInternalMockRecorder { + return m.recorder +} + +// GetToReturn mocks base method. +func (m *MockpersistenceInternal) GetToReturn() ([]iwfidl.KeyValue, []iwfidl.KeyValue, []iwfidl.KeyValue, []iwfidl.SearchAttribute) { m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "getToReturn") + ret := m.ctrl.Call(m, "GetToReturn") ret0, _ := ret[0].([]iwfidl.KeyValue) ret1, _ := ret[1].([]iwfidl.KeyValue) ret2, _ := ret[2].([]iwfidl.KeyValue) @@ -288,8 +328,8 @@ func (m *MockPersistence) getToReturn() ([]iwfidl.KeyValue, []iwfidl.KeyValue, [ return ret0, ret1, ret2, ret3 } -// getToReturn indicates an expected call of getToReturn. -func (mr *MockPersistenceMockRecorder) getToReturn() *gomock.Call { +// GetToReturn indicates an expected call of GetToReturn. +func (mr *MockpersistenceInternalMockRecorder) GetToReturn() *gomock.Call { mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "getToReturn", reflect.TypeOf((*MockPersistence)(nil).getToReturn)) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetToReturn", reflect.TypeOf((*MockpersistenceInternal)(nil).GetToReturn)) }