From d39280d4e5f3b26c12be2f4ab3d829771c55fa7d Mon Sep 17 00:00:00 2001 From: "naman.gupta" Date: Wed, 22 Mar 2023 19:58:15 +0530 Subject: [PATCH] E2 reset Response. E2 Reset Response from e2mgr after the timer for handling the reset times out. Signed-off-by: naman.gupta Change-Id: I28bcdd771c5cbd48cb96e978ee5a58a0fa024833 --- .../rmrmsghandlers/e2_reset_request_handler.go | 54 +++++++++++++++++++++- .../e2_reset_request_handler_test.go | 49 ++++++++++++++++++-- .../notification_handler_provider.go | 2 +- .../notification_handler_provider_test.go | 2 +- E2Manager/rmrCgo/rmrCgoTypes.go | 1 + 5 files changed, 100 insertions(+), 8 deletions(-) diff --git a/E2Manager/handlers/rmrmsghandlers/e2_reset_request_handler.go b/E2Manager/handlers/rmrmsghandlers/e2_reset_request_handler.go index 76a0b1a..5fb36c8 100644 --- a/E2Manager/handlers/rmrmsghandlers/e2_reset_request_handler.go +++ b/E2Manager/handlers/rmrmsghandlers/e2_reset_request_handler.go @@ -22,8 +22,11 @@ import ( "e2mgr/configuration" "e2mgr/logger" "e2mgr/models" + "e2mgr/rmrCgo" "e2mgr/services" + "e2mgr/services/rmrsender" "e2mgr/utils" + "encoding/xml" "time" "gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities" @@ -31,17 +34,23 @@ import ( const E2ResetRequestLogInfoElapsedTime = "#E2ResetRequestNotificationHandler.Handle - Summary: elapsed time for receiving and handling reset request message from E2 terminator: %f ms" +var ( + resetRequestEmptyTagsToReplaceToSelfClosingTags = []string{"reject", "ignore", "protocolIEs", "procedureCode", "ResetResponse", "ResetResponseIEs", "id", "criticality", "TransactionID"} +) + type E2ResetRequestNotificationHandler struct { logger *logger.Logger rnibDataService services.RNibDataService config *configuration.Configuration + rmrSender *rmrsender.RmrSender } -func NewE2ResetRequestNotificationHandler(logger *logger.Logger, rnibDataService services.RNibDataService, config *configuration.Configuration) *E2ResetRequestNotificationHandler { +func NewE2ResetRequestNotificationHandler(logger *logger.Logger, rnibDataService services.RNibDataService, config *configuration.Configuration, rmrSender *rmrsender.RmrSender) *E2ResetRequestNotificationHandler { return &E2ResetRequestNotificationHandler{ logger: logger, rnibDataService: rnibDataService, config: config, + rmrSender: rmrSender, } } @@ -74,6 +83,15 @@ func (e *E2ResetRequestNotificationHandler) Handle(request *models.NotificationR e.waitfortimertimeout(request) + ranName := request.RanName + resetRequest, err := e.parseE2ResetMessage(request.Payload) + if err != nil { + e.logger.Errorf(err.Error()) + return + } + e.logger.Infof("#E2ResetRequestNotificationHandler.Handle - RIC_RESET_REQUEST has been parsed successfully %+v", resetRequest) + e.handleSuccessfulResponse(ranName, request, resetRequest) + nodebInfo.ConnectionStatus = entities.ConnectionStatus_CONNECTED err = e.rnibDataService.UpdateNodebInfoAndPublish(nodebInfo) @@ -107,3 +125,37 @@ func (e *E2ResetRequestNotificationHandler) waitfortimertimeout(request *models. time.Sleep(time.Duration(timeout/100) * time.Millisecond) } } + +func (e *E2ResetRequestNotificationHandler) parseE2ResetMessage(payload []byte) (*models.E2ResetRequestMessage, error) { + e2resetMessage := models.E2ResetRequestMessage{} + err := xml.Unmarshal(utils.NormalizeXml(payload), &(e2resetMessage.E2APPDU)) + + if err != nil { + e.logger.Errorf("#E2ResetRequestNotificationHandler.Handle - error in parsing request message: %+v", err) + return nil, err + } + e.logger.Debugf("#E2ResetRequestNotificationHandler.Handle - Unmarshalling is successful %v", e2resetMessage.E2APPDU.InitiatingMessage.ProcedureCode) + return &e2resetMessage, nil +} + +func (h *E2ResetRequestNotificationHandler) handleSuccessfulResponse(ranName string, req *models.NotificationRequest, resetRequest *models.E2ResetRequestMessage) { + + successResponse := models.NewE2ResetResponseMessage(resetRequest) + h.logger.Debugf("#E2ResetRequestNotificationHandler.handleSuccessfulResponse - E2_RESET_RESPONSE has been built successfully %+v", successResponse) + + responsePayload, err := xml.Marshal(&successResponse.E2ApPdu) + if err != nil { + h.logger.Warnf("#E2ResetRequestNotificationHandler.handleSuccessfulResponse - RAN name: %s - Error marshalling RIC_E2_RESET_RESP. Payload: %s", ranName, responsePayload) + } + + responsePayload = utils.ReplaceEmptyTagsWithSelfClosing(responsePayload, resetRequestEmptyTagsToReplaceToSelfClosingTags) + + h.logger.Infof("#E2ResetRequestNotificationHandler.handleSuccessfulResponse - payload: %s", responsePayload) + + msg := models.NewRmrMessage(rmrCgo.RIC_E2_RESET_RESP, ranName, responsePayload, req.TransactionId, req.GetMsgSrc()) + h.logger.Infof("#E2ResetRequestNotificationHandler.handleSuccessfulResponse - RAN name: %s - RIC_E2_RESET_RESP message has been built successfully. Message: %x", ranName, msg) + err = h.rmrSender.Send(msg) + if err != nil { + h.logger.Errorf("#E2ResetRequestNotificationHandler.handleSuccessfulResponse - RAN name: %s - Error sending e2 success response %+v", ranName, msg) + } +} diff --git a/E2Manager/handlers/rmrmsghandlers/e2_reset_request_handler_test.go b/E2Manager/handlers/rmrmsghandlers/e2_reset_request_handler_test.go index c5d8747..56efae9 100644 --- a/E2Manager/handlers/rmrmsghandlers/e2_reset_request_handler_test.go +++ b/E2Manager/handlers/rmrmsghandlers/e2_reset_request_handler_test.go @@ -22,12 +22,16 @@ import ( "e2mgr/configuration" "e2mgr/mocks" "e2mgr/models" + "e2mgr/rmrCgo" + + // "e2mgr/rmrCgo" "e2mgr/services" "e2mgr/tests" "e2mgr/utils" "testing" "gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities" + // "github.com/stretchr/testify/assert" "github.com/stretchr/testify/mock" ) @@ -35,24 +39,27 @@ const ( E2ResetXmlPath = "../../tests/resources/reset/reset-request.xml" ) -func initE2ResetMocks(t *testing.T) (*E2ResetRequestNotificationHandler, *mocks.RnibReaderMock, *mocks.RnibWriterMock) { +func initE2ResetMocks(t *testing.T) (*E2ResetRequestNotificationHandler, *mocks.RnibReaderMock, *mocks.RnibWriterMock, *mocks.RmrMessengerMock) { logger := tests.InitLog(t) config := &configuration.Configuration{ RnibRetryIntervalMs: 10, MaxRnibConnectionAttempts: 3, + E2ResetTimeOutSec: 10, RnibWriter: configuration.RnibWriterConfig{ StateChangeMessageChannel: StateChangeMessageChannel, }} + rmrMessengerMock := &mocks.RmrMessengerMock{} + rmrSender := tests.InitRmrSender(rmrMessengerMock, logger) readerMock := &mocks.RnibReaderMock{} writerMock := &mocks.RnibWriterMock{} rnibDataService := services.NewRnibDataService(logger, config, readerMock, writerMock) - handler := NewE2ResetRequestNotificationHandler(logger, rnibDataService, config) - return handler, readerMock, writerMock + handler := NewE2ResetRequestNotificationHandler(logger, rnibDataService, config, rmrSender) + return handler, readerMock, writerMock, rmrMessengerMock } -func TestE2ResetRequestHandler(t *testing.T) { +func TestE2ResettNotificationHandler(t *testing.T) { e2ResetXml := utils.ReadXmlFile(t, E2ResetXmlPath) - handler, readerMock, writerMock := initE2ResetMocks(t) + handler, readerMock, writerMock, rmrMessengerMock := initE2ResetMocks(t) var nodebInfo = &entities.NodebInfo{ RanName: gnbNodebRanName, AssociatedE2TInstanceAddress: e2tInstanceFullAddress, @@ -64,8 +71,40 @@ func TestE2ResetRequestHandler(t *testing.T) { } readerMock.On("GetNodeb", gnbNodebRanName).Return(nodebInfo, nil) writerMock.On("UpdateNodebInfoAndPublish", mock.Anything).Return(nil) + var errEmpty error + rmrMessage := &rmrCgo.MBuf{} + rmrMessengerMock.On("SendMsg", mock.Anything, mock.Anything).Return(rmrMessage, errEmpty) notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(""), e2ResetXml...)} handler.Handle(notificationRequest) readerMock.AssertExpectations(t) writerMock.AssertExpectations(t) + rmrMessengerMock.AssertNotCalled(t, "SendMsg") +} + +func TestE2ResettNotificationHandler_UpdateStatus_Connected(t *testing.T) { + e2ResetXml := utils.ReadXmlFile(t, E2ResetXmlPath) + handler, readerMock, writerMock, rmrMessengerMock := initE2ResetMocks(t) + var nodebInfo = &entities.NodebInfo{ + RanName: gnbNodebRanName, + AssociatedE2TInstanceAddress: e2tInstanceFullAddress, + ConnectionStatus: entities.ConnectionStatus_DISCONNECTED, + NodeType: entities.Node_GNB, + Configuration: &entities.NodebInfo_Gnb{ + Gnb: &entities.Gnb{}, + }, + } + readerMock.On("GetNodeb", gnbNodebRanName).Return(nodebInfo, nil) + writerMock.On("UpdateNodebInfoAndPublish", mock.Anything).Return(nil) + nodebInfo.ConnectionStatus = entities.ConnectionStatus_CONNECTED + readerMock.On("GetNodeb", gnbNodebRanName).Return(nodebInfo, nil) + + var errEmpty error + rmrMessage := &rmrCgo.MBuf{} + rmrMessengerMock.On("SendMsg", mock.Anything, mock.Anything).Return(rmrMessage, errEmpty) + notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(""), e2ResetXml...)} + handler.Handle(notificationRequest) + readerMock.AssertCalled(t, "GetNodeb", mock.Anything) + writerMock.AssertCalled(t, "UpdateNodebInfoAndPublish", mock.Anything) + readerMock.AssertCalled(t, "GetNodeb", mock.Anything) + rmrMessengerMock.AssertNotCalled(t, "SendMsg") } diff --git a/E2Manager/providers/rmrmsghandlerprovider/notification_handler_provider.go b/E2Manager/providers/rmrmsghandlerprovider/notification_handler_provider.go index 3d13a30..92f7e09 100644 --- a/E2Manager/providers/rmrmsghandlerprovider/notification_handler_provider.go +++ b/E2Manager/providers/rmrmsghandlerprovider/notification_handler_provider.go @@ -95,7 +95,7 @@ func (provider *NotificationHandlerProvider) Init(logger *logger.Logger, config e2SetupRequestNotificationHandler := rmrmsghandlers.NewE2SetupRequestNotificationHandler(logger, config, e2tInstancesManager, rmrSender, rnibDataService, e2tAssociationManager, ranConnectStatusChangeManager, ranListManager) ricServiceUpdateHandler := rmrmsghandlers.NewRicServiceUpdateHandler(logger, rmrSender, rnibDataService, ranListManager) ricE2nodeConfigUpdateHandler := rmrmsghandlers.NewE2nodeConfigUpdateNotificationHandler(logger, rnibDataService, rmrSender) - e2ResetRequestNotificationHandler := rmrmsghandlers.NewE2ResetRequestNotificationHandler(logger, rnibDataService, config) + e2ResetRequestNotificationHandler := rmrmsghandlers.NewE2ResetRequestNotificationHandler(logger, rnibDataService, config, rmrSender) provider.Register(rmrCgo.RIC_X2_SETUP_RESP, x2SetupResponseHandler) provider.Register(rmrCgo.RIC_X2_SETUP_FAILURE, x2SetupFailureResponseHandler) diff --git a/E2Manager/providers/rmrmsghandlerprovider/notification_handler_provider_test.go b/E2Manager/providers/rmrmsghandlerprovider/notification_handler_provider_test.go index 9d6d1ad..43e08c8 100644 --- a/E2Manager/providers/rmrmsghandlerprovider/notification_handler_provider_test.go +++ b/E2Manager/providers/rmrmsghandlerprovider/notification_handler_provider_test.go @@ -99,7 +99,7 @@ func TestGetNotificationHandlerSuccess(t *testing.T) { {rmrCgo.RIC_X2_RESET, rmrmsghandlers.NewX2ResetRequestNotificationHandler(logger, rnibDataService, ranStatusChangeManager, rmrSender)}, {rmrCgo.RIC_SERVICE_UPDATE, rmrmsghandlers.NewRicServiceUpdateHandler(logger, rmrSender, rnibDataService, ranListManager)}, {rmrCgo.RIC_E2NODE_CONFIG_UPDATE, rmrmsghandlers.NewE2nodeConfigUpdateNotificationHandler(logger, rnibDataService, rmrSender)}, - {rmrCgo.RIC_E2_RESET_REQ, rmrmsghandlers.NewE2ResetRequestNotificationHandler(logger, rnibDataService, config)}, + {rmrCgo.RIC_E2_RESET_REQ, rmrmsghandlers.NewE2ResetRequestNotificationHandler(logger, rnibDataService, config, rmrSender)}, } for _, tc := range testCases { diff --git a/E2Manager/rmrCgo/rmrCgoTypes.go b/E2Manager/rmrCgo/rmrCgoTypes.go index 31292ca..2b5c31b 100644 --- a/E2Manager/rmrCgo/rmrCgoTypes.go +++ b/E2Manager/rmrCgo/rmrCgoTypes.go @@ -88,6 +88,7 @@ const ( RIC_E2NODE_CONFIG_UPDATE_ACK = C.RIC_E2NODE_CONFIG_UPDATE_ACK RIC_E2NODE_CONFIG_UPDATE_FAILURE = C.RIC_E2NODE_CONFIG_UPDATE_FAILURE RIC_E2_RESET_REQ = C.RIC_E2_RESET_REQ + RIC_E2_RESET_RESP = C.RIC_E2_RESET_RESP ) const ( -- 2.16.6