From db0380732b248c2343c95cdd56b33a50b3383d66 Mon Sep 17 00:00:00 2001 From: Irina Date: Sun, 21 Jun 2020 13:09:56 +0300 Subject: [PATCH] RIC-475 - E2M publish sdl event RedButton and Shutdown Change-Id: Iaa0255f25f7dc126181550a1aa16389661687b59 Signed-off-by: Irina --- Automation/Tests/Resource/scripts_variables.robot | 2 +- E2Manager/app/main.go | 4 +- E2Manager/container-tag.yaml | 2 +- E2Manager/controllers/e2t_controller_test.go | 7 +- E2Manager/controllers/nodeb_controller_test.go | 2 +- .../httpmsghandlers/delete_all_request_handler.go | 48 ++-- .../delete_all_request_handler_test.go | 271 ++++++++++++++------- .../set_general_configuration_handler.go | 5 + .../e2_setup_request_notification_handler.go | 2 + E2Manager/managers/e2t_shutdown_manager.go | 38 +-- E2Manager/managers/e2t_shutdown_manager_test.go | 249 ++++++++++--------- .../incoming_request_handler_provider.go | 16 +- .../incoming_request_handler_provider_test.go | 2 +- E2Manager/services/rnib_data_service.go | 6 - 14 files changed, 378 insertions(+), 276 deletions(-) diff --git a/Automation/Tests/Resource/scripts_variables.robot b/Automation/Tests/Resource/scripts_variables.robot index 99c2944..13b044a 100644 --- a/Automation/Tests/Resource/scripts_variables.robot +++ b/Automation/Tests/Resource/scripts_variables.robot @@ -32,4 +32,4 @@ ${first_retry_to_retrieve_from_db} RnibDataService.retry - retrying 1 GetNo ${third_retry_to_retrieve_from_db} RnibDataService.retry - after 3 attempts of GetNodeb ${RIC_RES_STATUS_REQ_message_type_successfully_sent} Message type: 10090 - Successfully sent RMR message ${E2_TERM_KEEP_ALIVE_REQ_message_type_successfully_sent} Message type: 1101 - Successfully sent RMR message -${save_general_configuration} RnibDataService.SaveGeneralConfiguration - configuration: {EnableRic:false} \ No newline at end of file +${save_general_configuration} SetGeneralConfigurationHandler.Handle - save general configuration to rnib: {EnableRic:false} \ No newline at end of file diff --git a/E2Manager/app/main.go b/E2Manager/app/main.go index 5dd1922..97ce5ab 100644 --- a/E2Manager/app/main.go +++ b/E2Manager/app/main.go @@ -65,7 +65,7 @@ func main() { ranAlarmService := services.NewRanAlarmService(logger, config) ranConnectStatusChangeManager := managers.NewRanConnectStatusChangeManager(logger, rnibDataService,ranListManager, ranAlarmService) e2tAssociationManager := managers.NewE2TAssociationManager(logger, rnibDataService, e2tInstancesManager, routingManagerClient, ranConnectStatusChangeManager) - e2tShutdownManager := managers.NewE2TShutdownManager(logger, config, rnibDataService, e2tInstancesManager, e2tAssociationManager, kubernetes) + e2tShutdownManager := managers.NewE2TShutdownManager(logger, config, rnibDataService, e2tInstancesManager, e2tAssociationManager, kubernetes, ranConnectStatusChangeManager) e2tKeepAliveWorker := managers.NewE2TKeepAliveWorker(logger, rmrSender, e2tInstancesManager, e2tShutdownManager, config) rmrNotificationHandlerProvider := rmrmsghandlerprovider.NewNotificationHandlerProvider() rmrNotificationHandlerProvider.Init(logger, config, rnibDataService, rmrSender, e2tInstancesManager, routingManagerClient, e2tAssociationManager, ranConnectStatusChangeManager) @@ -80,7 +80,7 @@ func main() { go rmrReceiver.ListenAndHandle() go e2tKeepAliveWorker.Execute() - httpMsgHandlerProvider := httpmsghandlerprovider.NewIncomingRequestHandlerProvider(logger, rmrSender, config, rnibDataService, ranSetupManager, e2tInstancesManager, e2tAssociationManager, routingManagerClient) + httpMsgHandlerProvider := httpmsghandlerprovider.NewIncomingRequestHandlerProvider(logger, rmrSender, config, rnibDataService, ranSetupManager, e2tInstancesManager, e2tAssociationManager, routingManagerClient, ranConnectStatusChangeManager) rootController := controllers.NewRootController(rnibDataService) nodebController := controllers.NewNodebController(logger, httpMsgHandlerProvider) e2tController := controllers.NewE2TController(logger, httpMsgHandlerProvider) diff --git a/E2Manager/container-tag.yaml b/E2Manager/container-tag.yaml index 6eeabcf..c403cbe 100644 --- a/E2Manager/container-tag.yaml +++ b/E2Manager/container-tag.yaml @@ -1,4 +1,4 @@ # The Jenkins job requires a tag to build the Docker image. # Global-JJB script assumes this file is in the repo root. --- -tag: 5.2.3 +tag: 5.2.4 diff --git a/E2Manager/controllers/e2t_controller_test.go b/E2Manager/controllers/e2t_controller_test.go index 943b138..17abc4e 100644 --- a/E2Manager/controllers/e2t_controller_test.go +++ b/E2Manager/controllers/e2t_controller_test.go @@ -54,7 +54,12 @@ func setupE2TControllerTest(t *testing.T) (*E2TController, *mocks.RnibReaderMock rnibDataService := services.NewRnibDataService(log, config, readerMock, nil) e2tInstancesManager := managers.NewE2TInstancesManager(rnibDataService, log) - handlerProvider := httpmsghandlerprovider.NewIncomingRequestHandlerProvider(log, nil, config, rnibDataService, nil, e2tInstancesManager, &managers.E2TAssociationManager{}, nil) + + ranListManager := managers.NewRanListManager(log) + ranAlarmService := services.NewRanAlarmService(log, config) + ranConnectStatusChangeManager := managers.NewRanConnectStatusChangeManager(log, rnibDataService,ranListManager, ranAlarmService) + + handlerProvider := httpmsghandlerprovider.NewIncomingRequestHandlerProvider(log, nil, config, rnibDataService, nil, e2tInstancesManager, &managers.E2TAssociationManager{}, nil, ranConnectStatusChangeManager) controller := NewE2TController(log, handlerProvider) return controller, readerMock } diff --git a/E2Manager/controllers/nodeb_controller_test.go b/E2Manager/controllers/nodeb_controller_test.go index d68ac51..4bcc708 100644 --- a/E2Manager/controllers/nodeb_controller_test.go +++ b/E2Manager/controllers/nodeb_controller_test.go @@ -181,7 +181,7 @@ func setupControllerTest(t *testing.T) (*NodebController, *mocks.RnibReaderMock, ranConnectStatusChangeManager := managers.NewRanConnectStatusChangeManager(log, rnibDataService, ranListManager, ranAlarmService) e2tAssociationManager := managers.NewE2TAssociationManager(log, rnibDataService, e2tInstancesManager, rmClient, ranConnectStatusChangeManager) - handlerProvider := httpmsghandlerprovider.NewIncomingRequestHandlerProvider(log, rmrSender, config, rnibDataService, ranSetupManager, e2tInstancesManager, e2tAssociationManager, rmClient) + handlerProvider := httpmsghandlerprovider.NewIncomingRequestHandlerProvider(log, rmrSender, config, rnibDataService, ranSetupManager, e2tInstancesManager, e2tAssociationManager, rmClient, ranConnectStatusChangeManager) controller := NewNodebController(log, handlerProvider) return controller, readerMock, writerMock, rmrMessengerMock, e2tInstancesManager } diff --git a/E2Manager/handlers/httpmsghandlers/delete_all_request_handler.go b/E2Manager/handlers/httpmsghandlers/delete_all_request_handler.go index 975640a..4e4142e 100644 --- a/E2Manager/handlers/httpmsghandlers/delete_all_request_handler.go +++ b/E2Manager/handlers/httpmsghandlers/delete_all_request_handler.go @@ -36,24 +36,26 @@ import ( ) type DeleteAllRequestHandler struct { - rnibDataService services.RNibDataService - rmrSender *rmrsender.RmrSender - config *configuration.Configuration - logger *logger.Logger - e2tInstancesManager managers.IE2TInstancesManager - rmClient clients.IRoutingManagerClient + rnibDataService services.RNibDataService + rmrSender *rmrsender.RmrSender + config *configuration.Configuration + logger *logger.Logger + e2tInstancesManager managers.IE2TInstancesManager + rmClient clients.IRoutingManagerClient + ranConnectStatusChangeManager managers.IRanConnectStatusChangeManager } const PartialSuccessDueToRmErrorMessage = "Operation succeeded except for routing manager outbound call" -func NewDeleteAllRequestHandler(logger *logger.Logger, rmrSender *rmrsender.RmrSender, config *configuration.Configuration, rnibDataService services.RNibDataService, e2tInstancesManager managers.IE2TInstancesManager, rmClient clients.IRoutingManagerClient) *DeleteAllRequestHandler { +func NewDeleteAllRequestHandler(logger *logger.Logger, rmrSender *rmrsender.RmrSender, config *configuration.Configuration, rnibDataService services.RNibDataService, e2tInstancesManager managers.IE2TInstancesManager, rmClient clients.IRoutingManagerClient, ranConnectStatusChangeManager managers.IRanConnectStatusChangeManager) *DeleteAllRequestHandler { return &DeleteAllRequestHandler{ - logger: logger, - rnibDataService: rnibDataService, - rmrSender: rmrSender, - config: config, - e2tInstancesManager: e2tInstancesManager, - rmClient: rmClient, + logger: logger, + rnibDataService: rnibDataService, + rmrSender: rmrSender, + config: config, + e2tInstancesManager: e2tInstancesManager, + rmClient: rmClient, + ranConnectStatusChangeManager: ranConnectStatusChangeManager, } } @@ -195,7 +197,7 @@ func (h *DeleteAllRequestHandler) updateNodebInfoShutDown(node *entities.NodebIn return nil, false } - err := h.updateNodebInfo(node, entities.ConnectionStatus_SHUT_DOWN, false) + err := h.updateNodebInfo(node, entities.ConnectionStatus_SHUT_DOWN, false) if err != nil { return err, false @@ -205,19 +207,21 @@ func (h *DeleteAllRequestHandler) updateNodebInfoShutDown(node *entities.NodebIn } func (h *DeleteAllRequestHandler) updateNodebInfo(node *entities.NodebInfo, connectionStatus entities.ConnectionStatus, resetAssociatedE2TAddress bool) error { - node.ConnectionStatus = connectionStatus - - if resetAssociatedE2TAddress { - node.AssociatedE2TInstanceAddress = "" - } - - err := h.rnibDataService.UpdateNodebInfo(node) + err := h.ranConnectStatusChangeManager.ChangeStatus(node, connectionStatus) if err != nil { - h.logger.Errorf("#DeleteAllRequestHandler.updateNodebInfo - RAN name: %s - failed updating nodeB entity in rNib. error: %s", node.RanName, err) return e2managererrors.NewRnibDbError() } + if resetAssociatedE2TAddress { + node.AssociatedE2TInstanceAddress = "" + + err = h.rnibDataService.UpdateNodebInfo(node) + if err != nil { + h.logger.Errorf("#DeleteAllRequestHandler.updateNodebInfo - RAN name: %s - failed updating nodeB entity in rNib. error: %s", node.RanName, err) + return e2managererrors.NewRnibDbError() + } + } h.logger.Infof("#DeleteAllRequestHandler.updateNodebInfo - RAN name: %s, connection status: %s", node.RanName, connectionStatus) return nil diff --git a/E2Manager/handlers/httpmsghandlers/delete_all_request_handler_test.go b/E2Manager/handlers/httpmsghandlers/delete_all_request_handler_test.go index e7f8686..9cdcf04 100644 --- a/E2Manager/handlers/httpmsghandlers/delete_all_request_handler_test.go +++ b/E2Manager/handlers/httpmsghandlers/delete_all_request_handler_test.go @@ -47,7 +47,7 @@ const BaseRMUrl = "http://10.10.2.15:12020/routingmanager" func setupDeleteAllRequestHandlerTest(t *testing.T) (*DeleteAllRequestHandler, *mocks.RnibReaderMock, *mocks.RnibWriterMock, *mocks.RmrMessengerMock, *mocks.HttpClientMock) { log := initLog(t) - config := configuration.ParseConfiguration() + config := &configuration.Configuration{StateChangeMessageChannel: "RAN_CONNECTION_STATUS_CHANGE"} config.BigRedButtonTimeoutSec = 1 config.RoutingManager.BaseUrl = BaseRMUrl @@ -61,7 +61,12 @@ func setupDeleteAllRequestHandlerTest(t *testing.T) (*DeleteAllRequestHandler, * e2tInstancesManager := managers.NewE2TInstancesManager(rnibDataService, log) httpClientMock := &mocks.HttpClientMock{} rmClient := clients.NewRoutingManagerClient(log, config, httpClientMock) - handler := NewDeleteAllRequestHandler(log, rmrSender, config, rnibDataService, e2tInstancesManager, rmClient) + + ranListManager := managers.NewRanListManager(log) + ranAlarmService := services.NewRanAlarmService(log, config) + ranConnectStatusChangeManager := managers.NewRanConnectStatusChangeManager(log, rnibDataService,ranListManager, ranAlarmService) + + handler := NewDeleteAllRequestHandler(log, rmrSender, config, rnibDataService, e2tInstancesManager, rmClient, ranConnectStatusChangeManager) return handler, readerMock, writerMock, rmrMessengerMock, httpClientMock } @@ -121,13 +126,40 @@ func TestTwoRansGetE2TAddressesEmptyListOneGetNodebFailure(t *testing.T) { readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_DISCONNECTED,} readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) - updatedNb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUT_DOWN,} - writerMock.On("UpdateNodebInfo", updatedNb1).Return(nil) + + updatedNb1 := *nb1 + updatedNb1.ConnectionStatus = entities.ConnectionStatus_SHUT_DOWN + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNb1, "RAN_CONNECTION_STATUS_CHANGE", "RanName_1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUT_DOWN} + writerMock.On("UpdateNodebInfo", nodeb1NotAssociated).Return(nil) + var nb2 *entities.NodebInfo readerMock.On("GetNodeb", "RanName_2").Return(nb2, common.NewInternalError(errors.New("error"))) _, err := h.Handle(nil) assert.IsType(t,&e2managererrors.RnibDbError{}, err) - writerMock.AssertNumberOfCalls(t, "UpdateNodebInfo", 1) + writerMock.AssertNumberOfCalls(t, "UpdateNodebInfo", 2) + writerMock.AssertNumberOfCalls(t, "UpdateNodebInfoOnConnectionStatusInversion", 0) + readerMock.AssertExpectations(t) +} + +func TestUpdateNodebInfoOnConnectionStatusInversionFailure(t *testing.T) { + h, readerMock, writerMock, _, _ := setupDeleteAllRequestHandlerTest(t) + readerMock.On("GetE2TAddresses").Return([]string{}, nil) + nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}, {InventoryName: "RanName_2"}} + readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) + nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED} + readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) + + updatedNb1 := *nb1 + updatedNb1.ConnectionStatus = entities.ConnectionStatus_SHUT_DOWN + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNb1, "RAN_CONNECTION_STATUS_CHANGE", "RanName_1_DISCONNECTED").Return(common.NewInternalError(errors.New("error"))) + + _, err := h.Handle(nil) + + assert.IsType(t,&e2managererrors.RnibDbError{}, err) + writerMock.AssertNumberOfCalls(t, "UpdateNodebInfo", 0) + writerMock.AssertNumberOfCalls(t, "UpdateNodebInfoOnConnectionStatusInversion", 1) readerMock.AssertExpectations(t) } @@ -179,6 +211,59 @@ func TestOneRanDissociateFailsTryShuttingDownFailure(t *testing.T) { writerMock.AssertExpectations(t) } +func TestOneRanWithStateShutDown(t *testing.T) { + h, readerMock, writerMock, rmrMessengerMock, httpClientMock := setupDeleteAllRequestHandlerTest(t) + e2tAddresses := []string{E2TAddress} + readerMock.On("GetE2TAddresses").Return(e2tAddresses, nil) + mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses, true) + nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}} + readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) + + nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUT_DOWN} + readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) + readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) + + e2tInstance := entities.E2TInstance{Address: E2TAddress, AssociatedRanList: []string{"RanName_1"}} + readerMock.On("GetE2TInstances", []string{E2TAddress}).Return([]*entities.E2TInstance{&e2tInstance}, nil) + updatedE2tInstance := e2tInstance + updatedE2tInstance.AssociatedRanList = []string{} + writerMock.On("SaveE2TInstance", &updatedE2tInstance).Return(nil) + + rmrMessage := models.RmrMessage{MsgType: rmrCgo.RIC_SCTP_CLEAR_ALL} + mbuf := rmrCgo.NewMBuf(rmrMessage.MsgType, len(rmrMessage.Payload), rmrMessage.RanName, &rmrMessage.Payload, &rmrMessage.XAction, rmrMessage.GetMsgSrc()) + rmrMessengerMock.On("SendMsg", mbuf, true).Return(mbuf, nil) + + _, err := h.Handle(nil) + + assert.Nil(t, err) + rmrMessengerMock.AssertCalled(t, "SendMsg", mbuf, true) + readerMock.AssertExpectations(t) + writerMock.AssertExpectations(t) +} + +func TestOneRanShutDown(t *testing.T) { + h, readerMock, writerMock, _, httpClientMock := setupDeleteAllRequestHandlerTest(t) + e2tAddresses := []string{} + readerMock.On("GetE2TAddresses").Return(e2tAddresses, nil) + mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses, true) + nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}} + readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) + + nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN} + readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) + + nodeb1NotAssociated := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUT_DOWN,} + writerMock.On("UpdateNodebInfo", nodeb1NotAssociated).Return(nil) + + readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) + + _, err := h.Handle(nil) + + assert.Nil(t, err) + readerMock.AssertExpectations(t) + writerMock.AssertExpectations(t) +} + func TestOneRanTryShuttingDownSucceedsClearFails(t *testing.T) { h, readerMock, writerMock, _, httpClientMock := setupDeleteAllRequestHandlerTest(t) e2tAddresses := []string{E2TAddress} @@ -186,10 +271,17 @@ func TestOneRanTryShuttingDownSucceedsClearFails(t *testing.T) { mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses, true) nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}} readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) + nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) - updatedNb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} - writerMock.On("UpdateNodebInfo", updatedNb1).Return(nil) + + updatedNb1 := *nb1 + updatedNb1.ConnectionStatus = entities.ConnectionStatus_SHUTTING_DOWN + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNb1, "RAN_CONNECTION_STATUS_CHANGE", "RanName_1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} + writerMock.On("UpdateNodebInfo", nodeb1NotAssociated).Return(nil) + readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) readerMock.On("GetE2TInstances", []string{E2TAddress}).Return([]*entities.E2TInstance{}, common.NewInternalError(errors.New("error"))) _, err := h.Handle(nil) @@ -198,6 +290,31 @@ func TestOneRanTryShuttingDownSucceedsClearFails(t *testing.T) { writerMock.AssertExpectations(t) } +func TestOneRanTryShuttingDownUpdateNodebError(t *testing.T) { + h, readerMock, writerMock, _, httpClientMock := setupDeleteAllRequestHandlerTest(t) + e2tAddresses := []string{E2TAddress} + readerMock.On("GetE2TAddresses").Return(e2tAddresses, nil) + mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses, true) + nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}} + readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) + + nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} + readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) + + updatedNb1 := *nb1 + updatedNb1.ConnectionStatus = entities.ConnectionStatus_SHUTTING_DOWN + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNb1, "RAN_CONNECTION_STATUS_CHANGE", "RanName_1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} + writerMock.On("UpdateNodebInfo", nodeb1NotAssociated).Return(common.NewInternalError(errors.New("error"))) + + _, err := h.Handle(nil) + + assert.IsType(t, &e2managererrors.RnibDbError{}, err) + readerMock.AssertExpectations(t) + writerMock.AssertExpectations(t) +} + func TestOneRanTryShuttingDownSucceedsClearSucceedsRmrSendFails(t *testing.T) { h, readerMock, writerMock, rmrMessengerMock, httpClientMock := setupDeleteAllRequestHandlerTest(t) e2tAddresses := []string{E2TAddress} @@ -207,8 +324,14 @@ func TestOneRanTryShuttingDownSucceedsClearSucceedsRmrSendFails(t *testing.T) { readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) - updatedNb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} - writerMock.On("UpdateNodebInfo", updatedNb1).Return(nil) + + updatedNb1 := *nb1 + updatedNb1.ConnectionStatus = entities.ConnectionStatus_SHUTTING_DOWN + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNb1, "RAN_CONNECTION_STATUS_CHANGE", "RanName_1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} + writerMock.On("UpdateNodebInfo", nodeb1NotAssociated).Return(nil) + readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) e2tInstance := entities.E2TInstance{Address: E2TAddress, AssociatedRanList: []string{"RanName_1"}} readerMock.On("GetE2TInstances", []string{E2TAddress}).Return([]*entities.E2TInstance{&e2tInstance}, nil) @@ -269,73 +392,51 @@ func TestTwoRansTryShuttingDownSucceedsClearSucceedsRmrSucceedsAllRansAreShutdow testTwoRansTryShuttingDownSucceedsClearSucceedsRmrSucceedsAllRansAreShutdown(t, true) } -//func TestOneRanTryShuttingDownSucceedsClearSucceedsRmrSucceedsRanStatusIsAlreadyShutdown(t *testing.T) { -// h, readerMock, writerMock, rmrMessengerMock, httpClientMock := setupDeleteAllRequestHandlerTest(t) -// e2tAddresses := []string{E2TAddress} - -// readerMock.On("GetE2TAddresses").Return(e2tAddresses , nil) -// mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses ,true) -// nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}} -// readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) -// nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} -// readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) -// updatedNb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} -// writerMock.On("UpdateNodebInfo", updatedNb1).Return(nil) -// readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) -// e2tInstance := entities.E2TInstance{Address: E2TAddress, AssociatedRanList: []string{"RanName_1"}} -// readerMock.On("GetE2TInstances", []string{E2TAddress}).Return([]*entities.E2TInstance{&e2tInstance }, nil) -// updatedE2tInstance := e2tInstance -// updatedE2tInstance.AssociatedRanList = []string{} -// writerMock.On("SaveE2TInstance", &updatedE2tInstance).Return(nil) -// -// rmrMessage := models.RmrMessage{MsgType: rmrCgo.RIC_SCTP_CLEAR_ALL} -// mbuf := rmrCgo.NewMBuf(rmrMessage.MsgType, len(rmrMessage.Payload), rmrMessage.RanName, &rmrMessage.Payload, &rmrMessage.XAction) -// rmrMessengerMock.On("SendMsg", mbuf, true).Return(mbuf, nil) -// -// readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) -// nbAfterTimer := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUT_DOWN,} -// readerMock.On("GetNodeb", /*"RanName_1"*/mock.Anything).Return(nbAfterTimer , nil) // Since this is a second call with same arguments we send mock.Anything due to mock limitations -// _, err := h.Handle(nil) -// assert.Nil(t, err) -// rmrMessengerMock.AssertCalled(t, "SendMsg",mbuf, true) -// readerMock.AssertExpectations(t) -// writerMock.AssertExpectations(t) -// writerMock.AssertNumberOfCalls(t, "UpdateNodebInfo", 1) -//} - -//func TestOneRanTryShuttingDownSucceedsClearSucceedsRmrSucceedsRanStatusIsShuttingDownUpdateFailure(t *testing.T) { -// h, readerMock, writerMock, rmrMessengerMock, httpClientMock := setupDeleteAllRequestHandlerTest(t) -// e2tAddresses := []string{E2TAddress} -// readerMock.On("GetE2TAddresses").Return(e2tAddresses, nil) -// mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses, true) -// nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}} -// readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) -// //nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} -// //readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) -// updatedNb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} -// writerMock.On("UpdateNodebInfo", updatedNb1).Return(nil) -// readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) -// e2tInstance := entities.E2TInstance{Address: E2TAddress, AssociatedRanList: []string{"RanName_1"}} -// readerMock.On("GetE2TInstances", []string{E2TAddress}).Return([]*entities.E2TInstance{&e2tInstance}, nil) -// updatedE2tInstance := e2tInstance -// updatedE2tInstance.AssociatedRanList = []string{} -// writerMock.On("SaveE2TInstance", &updatedE2tInstance).Return(nil) -// -// rmrMessage := models.RmrMessage{MsgType: rmrCgo.RIC_SCTP_CLEAR_ALL} -// mbuf := rmrCgo.NewMBuf(rmrMessage.MsgType, len(rmrMessage.Payload), rmrMessage.RanName, &rmrMessage.Payload, &rmrMessage.XAction) -// rmrMessengerMock.On("SendMsg", mbuf, true).Return(mbuf, nil) -// -// readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) -// readerMock.On("GetNodeb", "RanName_1").Return(updatedNb1, nil) -// updatedNb2 := *updatedNb1 -// updatedNb2.ConnectionStatus = entities.ConnectionStatus_SHUT_DOWN -// writerMock.On("UpdateNodebInfo", &updatedNb2).Return(common.NewInternalError(errors.New("error"))) -// _, err := h.Handle(nil) -// assert.IsType(t,&e2managererrors.RnibDbError{}, err) -// rmrMessengerMock.AssertCalled(t, "SendMsg", mbuf, true) -// readerMock.AssertExpectations(t) -// writerMock.AssertExpectations(t) -//} +func TestOneRanTryShuttingDownSucceedsClearSucceedsRmrSucceedsRanStatusIsShuttingDownUpdateFailure(t *testing.T) { + h, readerMock, writerMock, rmrMessengerMock, httpClientMock := setupDeleteAllRequestHandlerTest(t) + e2tAddresses := []string{E2TAddress} + readerMock.On("GetE2TAddresses").Return(e2tAddresses, nil) + mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses, true) + nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}} + readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) + + nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN, AssociatedE2TInstanceAddress: E2TAddress} + readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) + + updatedNb1 := *nb1 //&entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN, AssociatedE2TInstanceAddress: E2TAddress} + writerMock.On("UpdateNodebInfo", &updatedNb1).Return(nil) + + nodeb1NotAssociated := *nb1 + nodeb1NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb1NotAssociated.ConnectionStatus = entities.ConnectionStatus_SHUTTING_DOWN + writerMock.On("UpdateNodebInfo", &nodeb1NotAssociated).Return(nil) + + readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) + e2tInstance := entities.E2TInstance{Address: E2TAddress, AssociatedRanList: []string{"RanName_1"}} + readerMock.On("GetE2TInstances", []string{E2TAddress}).Return([]*entities.E2TInstance{&e2tInstance}, nil) + updatedE2tInstance := e2tInstance + updatedE2tInstance.AssociatedRanList = []string{} + writerMock.On("SaveE2TInstance", &updatedE2tInstance).Return(nil) + + rmrMessage := models.RmrMessage{MsgType: rmrCgo.RIC_SCTP_CLEAR_ALL} + mbuf := rmrCgo.NewMBuf(rmrMessage.MsgType, len(rmrMessage.Payload), rmrMessage.RanName, &rmrMessage.Payload, &rmrMessage.XAction, rmrMessage.GetMsgSrc()) + rmrMessengerMock.On("SendMsg", mbuf, true).Return(mbuf, nil) + + readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) + readerMock.On("GetNodeb", "RanName_1").Return(updatedNb1, nil) + + updatedNb2 := *nb1//&entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUT_DOWN,} + updatedNb2.ConnectionStatus = entities.ConnectionStatus_SHUT_DOWN + updatedNb2.AssociatedE2TInstanceAddress = "" + writerMock.On("UpdateNodebInfo", &updatedNb2).Return(common.NewInternalError(errors.New("error"))) + + _, err := h.Handle(nil) + + assert.IsType(t, &e2managererrors.RnibDbError{}, err) + rmrMessengerMock.AssertCalled(t, "SendMsg", mbuf, true) + readerMock.AssertExpectations(t) + writerMock.AssertExpectations(t) +} func testOneRanTryShuttingDownSucceedsClearSucceedsRmrSucceedsRanStatusIsShuttingDown(t *testing.T, partial bool) { h, readerMock, writerMock, rmrMessengerMock, httpClientMock := setupDeleteAllRequestHandlerTest(t) @@ -344,8 +445,6 @@ func testOneRanTryShuttingDownSucceedsClearSucceedsRmrSucceedsRanStatusIsShuttin mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses, !partial) nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}} readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) - //nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} - //readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) updatedNb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} writerMock.On("UpdateNodebInfo", updatedNb1).Return(nil) readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) @@ -368,7 +467,7 @@ func testOneRanTryShuttingDownSucceedsClearSucceedsRmrSucceedsRanStatusIsShuttin rmrMessengerMock.AssertCalled(t, "SendMsg", mbuf, true) readerMock.AssertExpectations(t) writerMock.AssertExpectations(t) - writerMock.AssertNumberOfCalls(t, "UpdateNodebInfo", 2) + writerMock.AssertNumberOfCalls(t, "UpdateNodebInfo", 3) } func TestOneRanTryShuttingDownSucceedsClearSucceedsRmrSucceedsRanStatusIsShuttingDownSuccess (t *testing.T) { @@ -386,18 +485,6 @@ func TestSuccessTwoE2TInstancesSixRans(t *testing.T) { mockHttpClientDissociateAllRans(httpClientMock, e2tAddresses, true) nbIdentityList := []*entities.NbIdentity{{InventoryName: "RanName_1"}, {InventoryName: "RanName_2"}, {InventoryName: "RanName_3"}, {InventoryName: "RanName_4"}, {InventoryName: "RanName_5"}, {InventoryName: "RanName_6"}} readerMock.On("GetListNodebIds").Return(nbIdentityList, nil) - //nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} - //readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil) - //nb2 := &entities.NodebInfo{RanName: "RanName_2", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} - //readerMock.On("GetNodeb", "RanName_2").Return(nb2, nil) - //nb3 := &entities.NodebInfo{RanName: "RanName_3", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress} - //readerMock.On("GetNodeb", "RanName_3").Return(nb3, nil) - //nb4 := &entities.NodebInfo{RanName: "RanName_4", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress2} - //readerMock.On("GetNodeb", "RanName_4").Return(nb4, nil) - //nb5 := &entities.NodebInfo{RanName: "RanName_5", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress2} - //readerMock.On("GetNodeb", "RanName_5").Return(nb5, nil) - //nb6 := &entities.NodebInfo{RanName: "RanName_6", ConnectionStatus: entities.ConnectionStatus_CONNECTED, AssociatedE2TInstanceAddress: E2TAddress2} - //readerMock.On("GetNodeb", "RanName_6").Return(nb6, nil) updatedNb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN,} writerMock.On("UpdateNodebInfo", updatedNb1).Return(nil) @@ -458,7 +545,7 @@ func TestSuccessTwoE2TInstancesSixRans(t *testing.T) { rmrMessengerMock.AssertCalled(t, "SendMsg", mbuf, true) readerMock.AssertExpectations(t) writerMock.AssertExpectations(t) - writerMock.AssertNumberOfCalls(t, "UpdateNodebInfo", 12) + writerMock.AssertNumberOfCalls(t, "UpdateNodebInfo", 18) } func initLog(t *testing.T) *logger.Logger { diff --git a/E2Manager/handlers/httpmsghandlers/set_general_configuration_handler.go b/E2Manager/handlers/httpmsghandlers/set_general_configuration_handler.go index 851dab1..2b2f074 100644 --- a/E2Manager/handlers/httpmsghandlers/set_general_configuration_handler.go +++ b/E2Manager/handlers/httpmsghandlers/set_general_configuration_handler.go @@ -51,9 +51,14 @@ func (h *SetGeneralConfigurationHandler) Handle(request models.Request) (models. return nil, e2managererrors.NewRnibDbError() } + h.logger.Infof("#SetGeneralConfigurationHandler.Handle - got general configuration from rnib - enableRic: %t", existingConfig.EnableRic) + if existingConfig.EnableRic != configuration.EnableRic { existingConfig.EnableRic = configuration.EnableRic + + h.logger.Infof("#SetGeneralConfigurationHandler.Handle - save general configuration to rnib: %+v", *existingConfig) + err := h.rnibDataService.SaveGeneralConfiguration(existingConfig) if err != nil { diff --git a/E2Manager/handlers/rmrmsghandlers/e2_setup_request_notification_handler.go b/E2Manager/handlers/rmrmsghandlers/e2_setup_request_notification_handler.go index b2f9898..d229e8c 100644 --- a/E2Manager/handlers/rmrmsghandlers/e2_setup_request_notification_handler.go +++ b/E2Manager/handlers/rmrmsghandlers/e2_setup_request_notification_handler.go @@ -76,6 +76,8 @@ func (h *E2SetupRequestNotificationHandler) Handle(request *models.NotificationR return } + h.logger.Infof("#E2SetupRequestNotificationHandler.Handle - got general configuration from rnib - enableRic: %t", generalConfiguration.EnableRic) + if !generalConfiguration.EnableRic { cause := models.Cause{Misc: &models.CauseMisc{OmIntervention: &struct{}{}}} h.handleUnsuccessfulResponse(ranName, request, cause) diff --git a/E2Manager/managers/e2t_shutdown_manager.go b/E2Manager/managers/e2t_shutdown_manager.go index 6287547..2b82d3a 100644 --- a/E2Manager/managers/e2t_shutdown_manager.go +++ b/E2Manager/managers/e2t_shutdown_manager.go @@ -34,22 +34,24 @@ type IE2TShutdownManager interface { } type E2TShutdownManager struct { - logger *logger.Logger - config *configuration.Configuration - rnibDataService services.RNibDataService - e2TInstancesManager IE2TInstancesManager - e2tAssociationManager *E2TAssociationManager - kubernetesManager *KubernetesManager + logger *logger.Logger + config *configuration.Configuration + rnibDataService services.RNibDataService + e2TInstancesManager IE2TInstancesManager + e2tAssociationManager *E2TAssociationManager + kubernetesManager *KubernetesManager + ranConnectStatusChangeManager IRanConnectStatusChangeManager } -func NewE2TShutdownManager(logger *logger.Logger, config *configuration.Configuration, rnibDataService services.RNibDataService, e2TInstancesManager IE2TInstancesManager, e2tAssociationManager *E2TAssociationManager, kubernetes *KubernetesManager) *E2TShutdownManager { +func NewE2TShutdownManager(logger *logger.Logger, config *configuration.Configuration, rnibDataService services.RNibDataService, e2TInstancesManager IE2TInstancesManager, e2tAssociationManager *E2TAssociationManager, kubernetes *KubernetesManager, ranConnectStatusChangeManager IRanConnectStatusChangeManager) *E2TShutdownManager { return &E2TShutdownManager{ - logger: logger, - config: config, - rnibDataService: rnibDataService, - e2TInstancesManager: e2TInstancesManager, - e2tAssociationManager: e2tAssociationManager, - kubernetesManager: kubernetes, + logger: logger, + config: config, + rnibDataService: rnibDataService, + e2TInstancesManager: e2TInstancesManager, + e2tAssociationManager: e2tAssociationManager, + kubernetesManager: kubernetes, + ranConnectStatusChangeManager: ranConnectStatusChangeManager, } } @@ -97,12 +99,16 @@ func (m E2TShutdownManager) clearNodebsAssociation(ranNamesToBeDissociated []str } return err } - nodeb.AssociatedE2TInstanceAddress = "" - nodeb.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + err = m.ranConnectStatusChangeManager.ChangeStatus(nodeb, entities.ConnectionStatus_DISCONNECTED) + if err != nil { + return err + } + + nodeb.AssociatedE2TInstanceAddress = "" err = m.rnibDataService.UpdateNodebInfo(nodeb) if err != nil { - m.logger.Errorf("#E2TShutdownManager.associateAndSetupNodebs - Failed to save nodeb %s from db.", ranName) + m.logger.Errorf("#E2TShutdownManager.clearNodebsAssociation - Failed to save nodeb %s to db.", ranName) return err } } diff --git a/E2Manager/managers/e2t_shutdown_manager_test.go b/E2Manager/managers/e2t_shutdown_manager_test.go index eaceeb5..af3f2a0 100644 --- a/E2Manager/managers/e2t_shutdown_manager_test.go +++ b/E2Manager/managers/e2t_shutdown_manager_test.go @@ -46,7 +46,7 @@ const E2TAddress3 = "10.10.2.17:9800" func initE2TShutdownManagerTest(t *testing.T) (*E2TShutdownManager, *mocks.RnibReaderMock, *mocks.RnibWriterMock, *mocks.HttpClientMock, *KubernetesManager) { log := initLog(t) - config := &configuration.Configuration{RnibRetryIntervalMs: 10, MaxRnibConnectionAttempts: 3, E2TInstanceDeletionTimeoutMs: 15000} + config := &configuration.Configuration{RnibRetryIntervalMs: 10, MaxRnibConnectionAttempts: 3, E2TInstanceDeletionTimeoutMs: 15000, StateChangeMessageChannel: "RAN_CONNECTION_STATUS_CHANGE"} readerMock := &mocks.RnibReaderMock{} writerMock := &mocks.RnibWriterMock{} @@ -65,7 +65,7 @@ func initE2TShutdownManagerTest(t *testing.T) (*E2TShutdownManager, *mocks.RnibR /*shutdownManager := NewE2TShutdownManager(log, config, rnibDataService, e2tInstancesManager, associationManager, kubernetesManager) return shutdownManager, readerMock, writerMock, httpClientMock, kubernetesManager*/ - shutdownManager := NewE2TShutdownManager(log, config, rnibDataService, e2tInstancesManager, associationManager, nil) + shutdownManager := NewE2TShutdownManager(log, config, rnibDataService, e2tInstancesManager, associationManager, nil, ranConnectStatusChangeManager) return shutdownManager, readerMock, writerMock, httpClientMock, nil } @@ -103,18 +103,35 @@ func TestShutdownSuccess1OutOf3Instances(t *testing.T) { writerMock.On("RemoveE2TInstance", E2TAddress).Return(nil) writerMock.On("SaveE2TAddresses", []string{E2TAddress2,E2TAddress3}).Return(nil) + /*** nodeb 1 ***/ nodeb1connected := *nodeb1 - nodeb1connected.AssociatedE2TInstanceAddress = "" nodeb1connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb1connected).Return(nil) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb1connected, "RAN_CONNECTION_STATUS_CHANGE", "test1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := *nodeb1 + nodeb1NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb1NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb1NotAssociated).Return(nil) + + /*** nodeb 2 ***/ nodeb2connected := *nodeb2 - nodeb2connected.AssociatedE2TInstanceAddress = "" nodeb2connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED writerMock.On("UpdateNodebInfo", &nodeb2connected).Return(nil) + + nodeb2NotAssociated := *nodeb2 + nodeb2NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb2NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb2NotAssociated).Return(nil) + + /*** nodeb 5 ***/ nodeb5connected := *nodeb5 - nodeb5connected.AssociatedE2TInstanceAddress = "" nodeb5connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb5connected).Return(nil) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb5connected, "RAN_CONNECTION_STATUS_CHANGE", "test5_DISCONNECTED").Return(nil) + + nodeb5NotAssociated := *nodeb5 + nodeb5NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb5NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb5NotAssociated).Return(nil) err := shutdownManager.Shutdown(e2tInstance1) @@ -173,22 +190,32 @@ func TestShutdownSuccess1Instance2Rans(t *testing.T) { readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) writerMock.On("SaveE2TAddresses", []string{}).Return(nil) + /*** nodeb 1 connected ***/ nodeb1new := *nodeb1 - nodeb1new.AssociatedE2TInstanceAddress = "" nodeb1new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb1new).Return(nil) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb1new, "RAN_CONNECTION_STATUS_CHANGE", "test1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := *nodeb1 + nodeb1NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb1NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb1NotAssociated).Return(nil) + + /*** nodeb 2 disconnected ***/ nodeb2new := *nodeb2 - nodeb2new.AssociatedE2TInstanceAddress = "" nodeb2new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED writerMock.On("UpdateNodebInfo", &nodeb2new).Return(nil) + nodeb2NotAssociated := *nodeb2 + nodeb2NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb2NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb2NotAssociated).Return(nil) + err := shutdownManager.Shutdown(e2tInstance1) assert.Nil(t, err) readerMock.AssertExpectations(t) writerMock.AssertExpectations(t) httpClientMock.AssertExpectations(t) - } func TestShutdownE2tInstanceAlreadyBeingDeleted(t *testing.T) { @@ -205,7 +232,6 @@ func TestShutdownE2tInstanceAlreadyBeingDeleted(t *testing.T) { readerMock.AssertExpectations(t) writerMock.AssertExpectations(t) httpClientMock.AssertExpectations(t) - } func TestShutdownFailureMarkInstanceAsToBeDeleted(t *testing.T) { @@ -222,7 +248,6 @@ func TestShutdownFailureMarkInstanceAsToBeDeleted(t *testing.T) { readerMock.AssertExpectations(t) writerMock.AssertExpectations(t) httpClientMock.AssertExpectations(t) - } func TestShutdownFailureRoutingManagerError(t *testing.T) { @@ -258,18 +283,35 @@ func TestShutdownFailureRoutingManagerError(t *testing.T) { writerMock.On("RemoveE2TInstance", E2TAddress).Return(nil) writerMock.On("SaveE2TAddresses", []string{E2TAddress2,E2TAddress3}).Return(nil) + /*** nodeb 1 connected ***/ nodeb1connected := *nodeb1 - nodeb1connected.AssociatedE2TInstanceAddress = "" nodeb1connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb1connected).Return(nil) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb1connected, "RAN_CONNECTION_STATUS_CHANGE", "test1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := *nodeb1 + nodeb1NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb1NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb1NotAssociated).Return(nil) + + /*** nodeb 2 shutting down ***/ nodeb2connected := *nodeb2 - nodeb2connected.AssociatedE2TInstanceAddress = "" nodeb2connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED writerMock.On("UpdateNodebInfo", &nodeb2connected).Return(nil) + + nodeb2NotAssociated := *nodeb2 + nodeb2NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb2NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb2NotAssociated).Return(nil) + + /*** nodeb 5 connected ***/ nodeb5connected := *nodeb5 - nodeb5connected.AssociatedE2TInstanceAddress = "" nodeb5connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb5connected).Return(nil) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb5connected, "RAN_CONNECTION_STATUS_CHANGE", "test5_DISCONNECTED").Return(nil) + + nodeb5NotAssociated := *nodeb5 + nodeb5NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb5NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb5NotAssociated).Return(nil) err := shutdownManager.Shutdown(e2tInstance1) @@ -277,7 +319,6 @@ func TestShutdownFailureRoutingManagerError(t *testing.T) { readerMock.AssertExpectations(t) writerMock.AssertExpectations(t) httpClientMock.AssertExpectations(t) - } func TestShutdownFailureInClearNodebsAssociation(t *testing.T) { @@ -292,9 +333,36 @@ func TestShutdownFailureInClearNodebsAssociation(t *testing.T) { readerMock.On("GetNodeb", "test1").Return(nodeb1, nil) nodeb1new := *nodeb1 - nodeb1new.AssociatedE2TInstanceAddress = "" nodeb1new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb1new).Return(common.NewInternalError(fmt.Errorf("for tests"))) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb1new, "RAN_CONNECTION_STATUS_CHANGE", "test1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := *nodeb1 + nodeb1NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb1NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb1NotAssociated).Return(common.NewInternalError(fmt.Errorf("for tests"))) + + err := shutdownManager.Shutdown(e2tInstance1) + + assert.NotNil(t, err) + readerMock.AssertExpectations(t) + writerMock.AssertExpectations(t) + httpClientMock.AssertExpectations(t) +} + +func TestShutdownFailureInClearNodebsAssociation_UpdateConnectionStatus(t *testing.T) { + shutdownManager, readerMock, writerMock, httpClientMock,_ := initE2TShutdownManagerTest(t) + + e2tInstance1 := entities.NewE2TInstance(E2TAddress, PodName) + e2tInstance1.State = entities.Active + e2tInstance1.AssociatedRanList = []string{"test1", "test2"} + writerMock.On("SaveE2TInstance", mock.MatchedBy(func(e2tInstance *entities.E2TInstance) bool { return e2tInstance.Address == E2TAddress && e2tInstance.State == entities.ToBeDeleted })).Return(nil) + + nodeb1 := &entities.NodebInfo{RanName:"test1", AssociatedE2TInstanceAddress:E2TAddress, ConnectionStatus:entities.ConnectionStatus_CONNECTED, E2ApplicationProtocol:entities.E2ApplicationProtocol_X2_SETUP_REQUEST} + readerMock.On("GetNodeb", "test1").Return(nodeb1, nil) + + nodeb1new := *nodeb1 + nodeb1new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb1new, "RAN_CONNECTION_STATUS_CHANGE", "test1_DISCONNECTED").Return(common.NewInternalError(fmt.Errorf("for tests"))) err := shutdownManager.Shutdown(e2tInstance1) @@ -318,9 +386,13 @@ func TestShutdownResourceNotFoundErrorInGetNodeb(t *testing.T) { readerMock.On("GetNodeb", "test2").Return(nodeb2, common.NewResourceNotFoundError("for testing")) nodeb1new := *nodeb1 - nodeb1new.AssociatedE2TInstanceAddress = "" nodeb1new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb1new).Return(nil) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb1new, "RAN_CONNECTION_STATUS_CHANGE", "test1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := *nodeb1 + nodeb1NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb1NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb1NotAssociated).Return(nil) err := shutdownManager.Shutdown(e2tInstance1) @@ -354,10 +426,14 @@ func TestShutdownResourceGeneralErrorInGetNodeb(t *testing.T) { writerMock.On("SaveE2TAddresses", []string{}).Return(nil) nodeb2new := *nodeb2 - nodeb2new.AssociatedE2TInstanceAddress = "" nodeb2new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED writerMock.On("UpdateNodebInfo", &nodeb2new).Return(nil) + nodeb2NotAssociated := *nodeb2 + nodeb2NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb2NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb2NotAssociated).Return(nil) + err := shutdownManager.Shutdown(e2tInstance1) assert.Nil(t, err) @@ -396,18 +472,35 @@ func TestShutdownFailureInRemoveE2TInstance(t *testing.T) { writerMock.On("RemoveE2TInstance", E2TAddress).Return(common.NewInternalError(fmt.Errorf("for tests"))) + /*** nodeb 1 connected ***/ nodeb1connected := *nodeb1 - nodeb1connected.AssociatedE2TInstanceAddress = "" nodeb1connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb1connected).Return(nil) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb1connected, "RAN_CONNECTION_STATUS_CHANGE", "test1_DISCONNECTED").Return(nil) + + nodeb1NotAssociated := *nodeb1 + nodeb1NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb1NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb1NotAssociated).Return(nil) + + /*** nodeb 2 shutting down ***/ nodeb2connected := *nodeb2 - nodeb2connected.AssociatedE2TInstanceAddress = "" nodeb2connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED writerMock.On("UpdateNodebInfo", &nodeb2connected).Return(nil) + + nodeb2NotAssociated := *nodeb2 + nodeb2NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb2NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb2NotAssociated).Return(nil) + + /*** nodeb 5 connected ***/ nodeb5connected := *nodeb5 - nodeb5connected.AssociatedE2TInstanceAddress = "" nodeb5connected.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb5connected).Return(nil) + writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &nodeb5connected, "RAN_CONNECTION_STATUS_CHANGE", "test5_DISCONNECTED").Return(nil) + + nodeb5NotAssociated := *nodeb5 + nodeb5NotAssociated.AssociatedE2TInstanceAddress = "" + nodeb5NotAssociated.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED + writerMock.On("UpdateNodebInfo", &nodeb5NotAssociated).Return(nil) err := shutdownManager.Shutdown(e2tInstance1) @@ -415,100 +508,4 @@ func TestShutdownFailureInRemoveE2TInstance(t *testing.T) { readerMock.AssertExpectations(t) writerMock.AssertExpectations(t) httpClientMock.AssertExpectations(t) -} -/* -func TestShutdownSuccess2Instance2Rans(t *testing.T) { - shutdownManager, readerMock, writerMock, httpClientMock,kubernetesManager := initE2TShutdownManagerTest(t) - - e2tInstance1 := entities.NewE2TInstance(E2TAddress, PodName) - e2tInstance1.State = entities.Active - e2tInstance1.AssociatedRanList = []string{"test2"} - writerMock.On("SaveE2TInstance", mock.MatchedBy(func(e2tInstance *entities.E2TInstance) bool { return e2tInstance.Address == E2TAddress && e2tInstance.State == entities.ToBeDeleted })).Return(nil) - - nodeb1 := &entities.NodebInfo{RanName:"test1", AssociatedE2TInstanceAddress:E2TAddress2, ConnectionStatus:entities.ConnectionStatus_CONNECTED, E2ApplicationProtocol:entities.E2ApplicationProtocol_X2_SETUP_REQUEST} - nodeb2 := &entities.NodebInfo{RanName:"test2", AssociatedE2TInstanceAddress:E2TAddress, ConnectionStatus:entities.ConnectionStatus_DISCONNECTED, E2ApplicationProtocol:entities.E2ApplicationProtocol_X2_SETUP_REQUEST} - readerMock.On("GetNodeb", "test2").Return(nodeb2, nil) - - data := models.NewRoutingManagerDeleteRequestModel(E2TAddress, []string{"test2"}, nil) - marshaled, _ := json.Marshal(data) - body := bytes.NewBuffer(marshaled) - respBody := ioutil.NopCloser(bytes.NewBufferString("")) - httpClientMock.On("Delete", "e2t", "application/json", body).Return(&http.Response{StatusCode: http.StatusCreated, Body: respBody}, nil) - - writerMock.On("RemoveE2TInstance", E2TAddress).Return(nil) - readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) - writerMock.On("SaveE2TAddresses", []string{}).Return(nil) - - nodeb1new := *nodeb1 - nodeb1new.AssociatedE2TInstanceAddress = "" - nodeb1new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - nodeb2new := *nodeb2 - nodeb2new.AssociatedE2TInstanceAddress = "" - nodeb2new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb2new).Return(nil) - - test := TestStruct{ - description: "namespace, 2 pods in Oran", - namespace: "oran", - objs: []runtime.Object{pod("oran", PodName), pod("oran", "e2t_2"), pod("some-namespace", "POD_Test_1")}, - } - - t.Run(test.description, func(t *testing.T) { - kubernetesManager.ClientSet = fake.NewSimpleClientset(test.objs...) - - err := shutdownManager.Shutdown(e2tInstance1) - - assert.Nil(t, err) - readerMock.AssertExpectations(t) - writerMock.AssertExpectations(t) - httpClientMock.AssertExpectations(t) - }) -} - -func TestShutdownSuccess2Instance2RansNoPod(t *testing.T) { - shutdownManager, readerMock, writerMock, httpClientMock,kubernetesManager := initE2TShutdownManagerTest(t) - - e2tInstance1 := entities.NewE2TInstance(E2TAddress, PodName) - e2tInstance1.State = entities.Active - e2tInstance1.AssociatedRanList = []string{"test2"} - writerMock.On("SaveE2TInstance", mock.MatchedBy(func(e2tInstance *entities.E2TInstance) bool { return e2tInstance.Address == E2TAddress && e2tInstance.State == entities.ToBeDeleted })).Return(nil) - - nodeb1 := &entities.NodebInfo{RanName:"test1", AssociatedE2TInstanceAddress:E2TAddress2, ConnectionStatus:entities.ConnectionStatus_CONNECTED, E2ApplicationProtocol:entities.E2ApplicationProtocol_X2_SETUP_REQUEST} - nodeb2 := &entities.NodebInfo{RanName:"test2", AssociatedE2TInstanceAddress:E2TAddress, ConnectionStatus:entities.ConnectionStatus_DISCONNECTED, E2ApplicationProtocol:entities.E2ApplicationProtocol_X2_SETUP_REQUEST} - readerMock.On("GetNodeb", "test2").Return(nodeb2, nil) - - data := models.NewRoutingManagerDeleteRequestModel(E2TAddress, []string{"test2"}, nil) - marshaled, _ := json.Marshal(data) - body := bytes.NewBuffer(marshaled) - respBody := ioutil.NopCloser(bytes.NewBufferString("")) - httpClientMock.On("Delete", "e2t", "application/json", body).Return(&http.Response{StatusCode: http.StatusCreated, Body: respBody}, nil) - - writerMock.On("RemoveE2TInstance", E2TAddress).Return(nil) - readerMock.On("GetE2TAddresses").Return([]string{E2TAddress}, nil) - writerMock.On("SaveE2TAddresses", []string{}).Return(nil) - - nodeb1new := *nodeb1 - nodeb1new.AssociatedE2TInstanceAddress = "" - nodeb1new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - nodeb2new := *nodeb2 - nodeb2new.AssociatedE2TInstanceAddress = "" - nodeb2new.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED - writerMock.On("UpdateNodebInfo", &nodeb2new).Return(nil) - - test := TestStruct{ - description: "namespace, 2 pods in Oran", - namespace: "oran", - objs: []runtime.Object{pod("oran", "e2t_2"), pod("some-namespace", "POD_Test_1")}, - } - - t.Run(test.description, func(t *testing.T) { - kubernetesManager.ClientSet = fake.NewSimpleClientset(test.objs...) - - err := shutdownManager.Shutdown(e2tInstance1) - - assert.Nil(t, err) - readerMock.AssertExpectations(t) - writerMock.AssertExpectations(t) - httpClientMock.AssertExpectations(t) - }) -}*/ \ No newline at end of file +} \ No newline at end of file diff --git a/E2Manager/providers/httpmsghandlerprovider/incoming_request_handler_provider.go b/E2Manager/providers/httpmsghandlerprovider/incoming_request_handler_provider.go index 3cd151f..cb4ed18 100644 --- a/E2Manager/providers/httpmsghandlerprovider/incoming_request_handler_provider.go +++ b/E2Manager/providers/httpmsghandlerprovider/incoming_request_handler_provider.go @@ -43,22 +43,24 @@ const ( ) type IncomingRequestHandlerProvider struct { - requestMap map[IncomingRequest]httpmsghandlers.RequestHandler - logger *logger.Logger + requestMap map[IncomingRequest]httpmsghandlers.RequestHandler + logger *logger.Logger + ranConnectStatusChangeManager managers.IRanConnectStatusChangeManager } -func NewIncomingRequestHandlerProvider(logger *logger.Logger, rmrSender *rmrsender.RmrSender, config *configuration.Configuration, rNibDataService services.RNibDataService, ranSetupManager *managers.RanSetupManager, e2tInstancesManager managers.IE2TInstancesManager, e2tAssociationManager *managers.E2TAssociationManager, rmClient clients.IRoutingManagerClient) *IncomingRequestHandlerProvider { +func NewIncomingRequestHandlerProvider(logger *logger.Logger, rmrSender *rmrsender.RmrSender, config *configuration.Configuration, rNibDataService services.RNibDataService, ranSetupManager *managers.RanSetupManager, e2tInstancesManager managers.IE2TInstancesManager, e2tAssociationManager *managers.E2TAssociationManager, rmClient clients.IRoutingManagerClient, ranConnectStatusChangeManager managers.IRanConnectStatusChangeManager) *IncomingRequestHandlerProvider { return &IncomingRequestHandlerProvider{ - requestMap: initRequestHandlerMap(logger, rmrSender, config, rNibDataService, e2tInstancesManager, rmClient), - logger: logger, + requestMap: initRequestHandlerMap(logger, rmrSender, config, rNibDataService, e2tInstancesManager, rmClient, ranConnectStatusChangeManager), + logger: logger, + ranConnectStatusChangeManager: ranConnectStatusChangeManager, } } -func initRequestHandlerMap(logger *logger.Logger, rmrSender *rmrsender.RmrSender, config *configuration.Configuration, rNibDataService services.RNibDataService, e2tInstancesManager managers.IE2TInstancesManager, rmClient clients.IRoutingManagerClient) map[IncomingRequest]httpmsghandlers.RequestHandler { +func initRequestHandlerMap(logger *logger.Logger, rmrSender *rmrsender.RmrSender, config *configuration.Configuration, rNibDataService services.RNibDataService, e2tInstancesManager managers.IE2TInstancesManager, rmClient clients.IRoutingManagerClient, ranConnectStatusChangeManager managers.IRanConnectStatusChangeManager) map[IncomingRequest]httpmsghandlers.RequestHandler { return map[IncomingRequest]httpmsghandlers.RequestHandler{ - ShutdownRequest: httpmsghandlers.NewDeleteAllRequestHandler(logger, rmrSender, config, rNibDataService, e2tInstancesManager, rmClient), + ShutdownRequest: httpmsghandlers.NewDeleteAllRequestHandler(logger, rmrSender, config, rNibDataService, e2tInstancesManager, rmClient, ranConnectStatusChangeManager), ResetRequest: httpmsghandlers.NewX2ResetRequestHandler(logger, rmrSender, rNibDataService), SetGeneralConfigurationRequest: httpmsghandlers.NewSetGeneralConfigurationHandler(logger, rNibDataService), GetNodebRequest: httpmsghandlers.NewGetNodebRequestHandler(logger, rNibDataService), diff --git a/E2Manager/providers/httpmsghandlerprovider/incoming_request_handler_provider_test.go b/E2Manager/providers/httpmsghandlerprovider/incoming_request_handler_provider_test.go index f359788..4be6e4f 100644 --- a/E2Manager/providers/httpmsghandlerprovider/incoming_request_handler_provider_test.go +++ b/E2Manager/providers/httpmsghandlerprovider/incoming_request_handler_provider_test.go @@ -60,7 +60,7 @@ func setupTest(t *testing.T) *IncomingRequestHandlerProvider { ranAlarmService := services.NewRanAlarmService(log, config) ranConnectStatusChangeManager := managers.NewRanConnectStatusChangeManager(log, rnibDataService,ranListManager, ranAlarmService) e2tAssociationManager := managers.NewE2TAssociationManager(log, rnibDataService, e2tInstancesManager, rmClient, ranConnectStatusChangeManager) - return NewIncomingRequestHandlerProvider(log, rmrSender, configuration.ParseConfiguration(), rnibDataService, ranSetupManager, e2tInstancesManager, e2tAssociationManager, rmClient) + return NewIncomingRequestHandlerProvider(log, rmrSender, configuration.ParseConfiguration(), rnibDataService, ranSetupManager, e2tInstancesManager, e2tAssociationManager, rmClient, ranConnectStatusChangeManager) } func TestNewIncomingRequestHandlerProvider(t *testing.T) { diff --git a/E2Manager/services/rnib_data_service.go b/E2Manager/services/rnib_data_service.go index dbc9e29..e96ba48 100644 --- a/E2Manager/services/rnib_data_service.go +++ b/E2Manager/services/rnib_data_service.go @@ -282,16 +282,10 @@ func (w *rNibDataService) GetGeneralConfiguration() (*entities.GeneralConfigurat return }) - if err == nil { - w.logger.Infof("#RnibDataService.GetGeneralConfiguration - enableRic: %t", generalConfiguration.EnableRic) - } - return generalConfiguration, err } func (w *rNibDataService) SaveGeneralConfiguration(config *entities.GeneralConfiguration) error { - w.logger.Infof("#RnibDataService.SaveGeneralConfiguration - configuration: %+v", *config) - err := w.retry("SaveGeneralConfiguration", func() (err error) { err = w.rnibWriter.SaveGeneralConfiguration(config) return -- 2.16.6