[RIC-571] Setup request of new eNB 34/4434/3
authorAmichai <amichai.sichel@intl.att.com>
Thu, 23 Jul 2020 11:28:40 +0000 (11:28 +0000)
committerAmichai Sichel <amichai.sichel@intl.att.com>
Thu, 23 Jul 2020 12:38:37 +0000 (12:38 +0000)
Change-Id: I2c5d153d82bd38faeb589a59568be967fc26a5d9
Signed-off-by: Amichai <amichai.sichel@intl.att.com>
13 files changed:
E2Manager/container-tag.yaml
E2Manager/controllers/nodeb_controller_test.go
E2Manager/e2managererrors/unknown_setup_request_ranname_error.go [new file with mode: 0644]
E2Manager/go.mod
E2Manager/go.sum
E2Manager/handlers/httpmsghandlers/add_enb_request_handler.go
E2Manager/handlers/httpmsghandlers/delete_all_request_handler_test.go
E2Manager/handlers/rmrmsghandlers/e2_setup_request_notification_handler.go
E2Manager/handlers/rmrmsghandlers/e2_setup_request_notification_handler_test.go
E2Manager/mocks/rnibWriterMock.go
E2Manager/rNibWriter/rNibWriter.go
E2Manager/rNibWriter/rNibWriter_test.go
E2Manager/services/rnib_data_service.go

index d0105e3..45daa1d 100644 (file)
@@ -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.20
\ No newline at end of file
+tag: 5.2.21
\ No newline at end of file
index a8a4e9f..1b3a7db 100644 (file)
@@ -101,7 +101,7 @@ type updateEnbCellsParams struct {
        err error
 }
 
-type saveNodebParams struct {
+type addEnbParams struct {
        err error
 }
 
@@ -139,7 +139,7 @@ type controllerUpdateGnbTestContext struct {
 
 type controllerAddEnbTestContext struct {
        getNodebInfoResult   *getNodebInfoResult
-       saveNodebParams      *saveNodebParams
+       addEnbParams         *addEnbParams
        addNbIdentityParams  *addNbIdentityParams
        requestBody          map[string]interface{}
        expectedStatusCode   int
@@ -432,7 +432,7 @@ func controllerGetNodebIdListTestExecuter(t *testing.T, context *controllerGetNo
        controller.GetNodebIdList(writer, req)
        assert.Equal(t, context.expectedStatusCode, writer.Result().StatusCode)
        bodyBytes, _ := ioutil.ReadAll(writer.Body)
-       assert.Equal(t, context.expectedJsonResponse, string(bodyBytes))
+       assert.Contains(t, context.expectedJsonResponse, string(bodyBytes))
 }
 
 func activateControllerUpdateEnbMocks(context *controllerUpdateEnbTestContext, readerMock *mocks.RnibReaderMock, writerMock *mocks.RnibWriterMock, updateEnbRequest *models.UpdateEnbRequest) {
@@ -562,7 +562,7 @@ func activateControllerAddEnbMocks(context *controllerAddEnbTestContext, readerM
                readerMock.On("GetNodeb", RanName).Return(context.getNodebInfoResult.nodebInfo, context.getNodebInfoResult.rnibError)
        }
 
-       if context.saveNodebParams != nil {
+       if context.addEnbParams != nil {
                nodebInfo := entities.NodebInfo{
                        RanName:          addEnbRequest.RanName,
                        Ip:               addEnbRequest.Ip,
@@ -573,7 +573,7 @@ func activateControllerAddEnbMocks(context *controllerAddEnbTestContext, readerM
                        ConnectionStatus: entities.ConnectionStatus_DISCONNECTED,
                }
 
-               writerMock.On("SaveNodeb", &nodebInfo).Return(context.saveNodebParams.err)
+               writerMock.On("AddEnb", &nodebInfo).Return(context.addEnbParams.err)
        }
 
        if context.addNbIdentityParams != nil {
@@ -1220,8 +1220,8 @@ func TestControllerAddEnbNodebExistsFailure(t *testing.T) {
 
 func TestControllerAddEnbSaveNodebFailure(t *testing.T) {
        context := controllerAddEnbTestContext{
-               saveNodebParams: &saveNodebParams{
-                       err: common.NewInternalError(errors.New("#reader.SaveeNodeb - Internal Error")),
+               addEnbParams: &addEnbParams{
+                       err: common.NewInternalError(errors.New("#reader.AddEnb - Internal Error")),
                },
                getNodebInfoResult: &getNodebInfoResult{
                        nodebInfo: nil,
@@ -1237,7 +1237,7 @@ func TestControllerAddEnbSaveNodebFailure(t *testing.T) {
 
 func TestControllerAddEnbAddNbIdentityFailure(t *testing.T) {
        context := controllerAddEnbTestContext{
-               saveNodebParams: &saveNodebParams{
+               addEnbParams: &addEnbParams{
                        err: nil,
                },
                addNbIdentityParams: &addNbIdentityParams{
@@ -1342,7 +1342,7 @@ func TestControllerAddEnbMissingRequiredServedCellProps(t *testing.T) {
 
 func TestControllerAddEnbSuccess(t *testing.T) {
        context := controllerAddEnbTestContext{
-               saveNodebParams: &saveNodebParams{
+               addEnbParams: &addEnbParams{
                        err: nil,
                },
                addNbIdentityParams: &addNbIdentityParams{
@@ -1479,7 +1479,7 @@ func TestControllerGetNodebIdListSuccess(t *testing.T) {
                nodebIdList:          nodebIdList,
                rnibError:            rnibError,
                expectedStatusCode:   http.StatusOK,
-               expectedJsonResponse: "[{\"inventoryName\":\"test1\",\"globalNbId\":{\"plmnId\":\"plmnId1\",\"nbId\":\"nbId1\"}},{\"inventoryName\":\"test2\",\"globalNbId\":{\"plmnId\":\"plmnId2\",\"nbId\":\"nbId2\"}}]",
+               expectedJsonResponse: "[{\"inventoryName\":\"test1\",\"globalNbId\":{\"plmnId\":\"plmnId1\",\"nbId\":\"nbId1\"}},{\"inventoryName\":\"test2\",\"globalNbId\":{\"plmnId\":\"plmnId2\",\"nbId\":\"nbId2\"}}][{\"inventoryName\":\"test2\",\"globalNbId\":{\"plmnId\":\"plmnId2\",\"nbId\":\"nbId2\"}},{\"inventoryName\":\"test1\",\"globalNbId\":{\"plmnId\":\"plmnId1\",\"nbId\":\"nbId1\"}}]",
        }
 
        controllerGetNodebIdListTestExecuter(t, &context)
diff --git a/E2Manager/e2managererrors/unknown_setup_request_ranname_error.go b/E2Manager/e2managererrors/unknown_setup_request_ranname_error.go
new file mode 100644 (file)
index 0000000..72f7f56
--- /dev/null
@@ -0,0 +1,42 @@
+//
+// Copyright 2019 AT&T Intellectual Property
+// Copyright 2019 Nokia
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+
+//  This source code is part of the near-RT RIC (RAN Intelligent Controller)
+//  platform project (RICP).
+
+package e2managererrors
+
+import "fmt"
+
+type UnknownSetupRequestRanNameError struct {
+       *BaseError
+       ranName string
+}
+
+func NewUnknownSetupRequestRanNameError(ranName string) *UnknownSetupRequestRanNameError {
+       return &UnknownSetupRequestRanNameError{
+               &BaseError{
+                       Code:    599,
+                       Message: fmt.Sprintf("Can't extract node-type out of RAN name %s", ranName),
+               },
+               ranName,
+       }
+}
+
+func (e *UnknownSetupRequestRanNameError) Error() string {
+       return e.Message
+}
index 9cf5006..344bac4 100644 (file)
@@ -1,9 +1,9 @@
 module e2mgr
 
 require (
-       gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.46
-       gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.46
-       gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.46
+       gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.47
+       gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.47
+       gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.47
        gerrit.o-ran-sc.org/r/ric-plt/sdlgo v0.5.2
        github.com/golang/protobuf v1.4.2
        github.com/gorilla/mux v1.7.0
index 62ac537..6cea29b 100644 (file)
@@ -1,22 +1,10 @@
 cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.44 h1:rda7Ubx7ZW579wWNduk/MD/9Fl7fsKo08KE+2ngIkZM=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.44/go.mod h1:QJ1uPPZosGbhxUWpUpeM5fLqFHdnWTrVnvW2DgyOCes=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.45 h1:2zwckksGVcIkXJeymAPvtyaO3bb+8UCyRENY8/q1yZs=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.45/go.mod h1:QJ1uPPZosGbhxUWpUpeM5fLqFHdnWTrVnvW2DgyOCes=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.46 h1:mUn8CsJYcliKK35Xm7xMjkrTnhksZ9AinPkTu44ABKA=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.46/go.mod h1:QJ1uPPZosGbhxUWpUpeM5fLqFHdnWTrVnvW2DgyOCes=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.44 h1:/Kye3C5ZAJkK1ux1mNrQEE4Jph537EV6DJ1qOCtKPqQ=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.44/go.mod h1:YaQ+XEI4PcAoISxp9wUpUr2TP0J7JihpQTD0G1Lpd4A=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.45 h1:YuNGHpf6UsHkvi4qqxbE6ijuceRqoz5+qdWe6nUTNIU=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.45/go.mod h1:YaQ+XEI4PcAoISxp9wUpUr2TP0J7JihpQTD0G1Lpd4A=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.46 h1:bd1nDjy20ia7vUWw3Dqvxf9shMSAtJOObSotr4iwGxM=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.46/go.mod h1:YaQ+XEI4PcAoISxp9wUpUr2TP0J7JihpQTD0G1Lpd4A=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.44 h1:VCOBMhSZJE3hZJLA+eJOZCrCoifCDi7ZmR3aMdV5mP8=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.44/go.mod h1:eRI+ExoQG8rEzexqRtW5Shn2tT/7w9l+WqaiPZqOsEA=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.45 h1:p+yPMhomeiQy+qermMGzBhwh/i9T2gaL8cWOT3V5DG4=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.45/go.mod h1:3p1bZS4GA2MGVg5CHZEnMlCuO7KXpfW3Y38HTAbo6/4=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.46 h1:GlwpSMYc0wuARKfiEfF0p0ttsinWhmvKVpFZknGor24=
-gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.46/go.mod h1:O83fcA6x8B7tPBgr2ihBXsfRkcL0m3NWYMLsD/gvGWU=
+gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.47 h1:ANQeff4O93le30a0pLrN51feB+jMTCSQZ1txzlGodZU=
+gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/common v1.0.47/go.mod h1:QJ1uPPZosGbhxUWpUpeM5fLqFHdnWTrVnvW2DgyOCes=
+gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.47 h1:wIiT6TjsCHBw1J9ro9FcjtnU6R9TPHPPFrIzc7LejQM=
+gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/entities v1.0.47/go.mod h1:YaQ+XEI4PcAoISxp9wUpUr2TP0J7JihpQTD0G1Lpd4A=
+gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.47 h1:jMK6IoI7ibAzV96WtVDo4BJzENUYAQ3Y47kqdNgW0Ts=
+gerrit.o-ran-sc.org/r/ric-plt/nodeb-rnib.git/reader v1.0.47/go.mod h1:cicCB/v15pTNovRNhyL6MBEHCwNsF/RU8xBc5vdoA7k=
 gerrit.o-ran-sc.org/r/ric-plt/sdlgo.git v0.5.2 h1:UK7awyRKIkVdokWvvkYvazlg3EWIfMnIqCcJxTnLlDA=
 gerrit.o-ran-sc.org/r/ric-plt/sdlgo.git v0.5.2/go.mod h1:y2WhrCvdLkAKdH+ySdHSOSehACJkTMyZghCGVcqoZzc=
 github.com/BurntSushi/toml v0.3.1 h1:WXkYYl6Yr3qBf1K79EBnL4mak0OimBfB0XUf9Vl28OQ=
index 46cd802..6f7fcd6 100644 (file)
@@ -73,10 +73,10 @@ func (h *AddEnbRequestHandler) Handle(request models.Request) (models.IResponse,
        }
 
        nodebInfo := h.createNodebInfo(addEnbRequest)
-       err = h.rNibDataService.SaveNodeb(nodebInfo)
+       err = h.rNibDataService.AddEnb(nodebInfo)
 
        if err != nil {
-               h.logger.Errorf("#AddEnbRequestHandler.Handle - RAN name: %s - failed to save nodeb entity in RNIB. Error: %s", addEnbRequest.RanName, err)
+               h.logger.Errorf("#AddEnbRequestHandler.Handle - RAN name: %s - failed to add eNB entity in RNIB. Error: %s", addEnbRequest.RanName, err)
                return nil, e2managererrors.NewRnibDbError()
        }
 
index 3cf5b46..cd2a4f2 100644 (file)
@@ -147,8 +147,10 @@ func TestTwoRansGetE2TAddressesEmptyListOneGetNodebFailure(t *testing.T) {
        readerMock.On("GetNodeb", "RanName_2").Return(nb2, common.NewInternalError(errors.New("error")))
        _, err = h.Handle(nil)
        assert.IsType(t, &e2managererrors.RnibDbError{}, err)
-       writerMock.AssertExpectations(t)
-       readerMock.AssertExpectations(t)
+       writerMock.AssertNotCalled(t, "UpdateNodebInfo", nb2)
+       readerMock.AssertCalled(t, "GetE2TAddresses")
+       readerMock.AssertCalled(t, "GetListNodebIds")
+       readerMock.AssertCalled(t, "GetNodeb", "RanName_2")
 }
 
 func TestUpdateNodebInfoOnConnectionStatusInversionFailure(t *testing.T) {
@@ -163,6 +165,10 @@ func TestUpdateNodebInfoOnConnectionStatusInversionFailure(t *testing.T) {
        nb1 := &entities.NodebInfo{RanName: "RanName_1", ConnectionStatus: entities.ConnectionStatus_CONNECTED}
        readerMock.On("GetNodeb", "RanName_1").Return(nb1, nil)
 
+       nb2 := &entities.NodebInfo{RanName: "RanName_2", ConnectionStatus: entities.ConnectionStatus_SHUT_DOWN}
+       readerMock.On("GetNodeb", "RanName_2").Return(nb2, nil)
+       writerMock.On("UpdateNodebInfo", nb2)
+
        updatedNb1 := *nb1
        updatedNb1.ConnectionStatus = entities.ConnectionStatus_SHUT_DOWN
        writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNb1, "RanName_1_DISCONNECTED").Return(common.NewInternalError(errors.New("error")))
@@ -170,8 +176,10 @@ func TestUpdateNodebInfoOnConnectionStatusInversionFailure(t *testing.T) {
        _, err := h.Handle(nil)
 
        assert.IsType(t, &e2managererrors.RnibDbError{}, err)
-       writerMock.AssertExpectations(t)
-       readerMock.AssertExpectations(t)
+       writerMock.AssertCalled(t, "UpdateNodebInfoOnConnectionStatusInversion", &updatedNb1, "RanName_1_DISCONNECTED")
+       readerMock.AssertCalled(t, "GetE2TAddresses")
+       readerMock.AssertCalled(t, "GetListNodebIds")
+       readerMock.AssertCalled(t, "GetNodeb", "RanName_1")
 }
 
 func TestTwoRansGetE2TAddressesEmptyListOneUpdateNodebInfoFailure(t *testing.T) {
@@ -197,8 +205,10 @@ func TestTwoRansGetE2TAddressesEmptyListOneUpdateNodebInfoFailure(t *testing.T)
        writerMock.On("UpdateNodebInfo", updatedNb2).Return(common.NewInternalError(errors.New("error")))
        _, err = h.Handle(nil)
        assert.IsType(t, &e2managererrors.RnibDbError{}, err)
-       readerMock.AssertExpectations(t)
-       writerMock.AssertExpectations(t)
+       readerMock.AssertCalled(t, "GetE2TAddresses")
+       readerMock.AssertCalled(t, "GetListNodebIds")
+       readerMock.AssertCalled(t, "GetNodeb", "RanName_2")
+       writerMock.AssertCalled(t, "UpdateNodebInfo", updatedNb2)
 }
 
 func TestOneRanWithStateShutDown(t *testing.T) {
index 04b33d7..5565513 100644 (file)
@@ -39,8 +39,21 @@ import (
 )
 
 var (
-       emptyTagsToReplaceToSelfClosingTags = []string{"reject", "ignore", "transport-resource-unavailable", "om-intervention",
+       emptyTagsToReplaceToSelfClosingTags = []string{"reject", "ignore", "transport-resource-unavailable", "om-intervention", "request-id-unknown",
                "v60s", "v20s", "v10s", "v5s", "v2s", "v1s"}
+       gnbTypesMap = map[string]entities.GnbType{
+               "gnb":entities.GnbType_GNB,
+               "en_gnb":entities.GnbType_EN_GNB,
+       }
+       enbTypesMap = map[string]entities.EnbType{
+               "enB_macro":entities.EnbType_MACRO_ENB,
+               "enB_home":entities.EnbType_HOME_ENB,
+               "enB_shortmacro":entities.EnbType_SHORT_MACRO_ENB,
+               "enB_longmacro":entities.EnbType_LONG_MACRO_ENB,
+               "ng_enB_macro":entities.EnbType_MACRO_NG_ENB,
+               "ng_enB_shortmacro":entities.EnbType_SHORT_MACRO_NG_ENB,
+               "ng_enB_longmacro":entities.EnbType_LONG_MACRO_NG_ENB,
+       }
 )
 
 type E2SetupRequestNotificationHandler struct {
@@ -113,6 +126,10 @@ func (h *E2SetupRequestNotificationHandler) Handle(request *models.NotificationR
                }
 
                if nodebInfo, err = h.handleNewRan(ranName, e2tIpAddress, setupRequest); err != nil {
+                       if _, ok := err.(*e2managererrors.UnknownSetupRequestRanNameError); ok {
+                               cause := models.Cause{RicRequest: &models.CauseRic{RequestIdUnknown: &struct{}{}}}
+                               h.handleUnsuccessfulResponse(ranName, request, cause)
+                       }
                        return
                }
 
@@ -139,9 +156,13 @@ func (h *E2SetupRequestNotificationHandler) Handle(request *models.NotificationR
 
 func (h *E2SetupRequestNotificationHandler) handleNewRan(ranName string, e2tIpAddress string, setupRequest *models.E2SetupRequestMessage) (*entities.NodebInfo, error) {
 
-       nodebInfo := h.buildNodebInfo(ranName, e2tIpAddress, setupRequest)
-       err := h.rNibDataService.SaveNodeb(nodebInfo)
+       nodebInfo, err := h.buildNodebInfo(ranName, e2tIpAddress, setupRequest)
+       if err != nil {
+               h.logger.Errorf("#E2SetupRequestNotificationHandler.handleNewRan - RAN name: %s - failed building nodebInfo. Error: %s", ranName, err)
+               return nil, err
+       }
 
+       err = h.rNibDataService.SaveNodeb(nodebInfo)
        if err != nil {
                h.logger.Errorf("#E2SetupRequestNotificationHandler.handleNewRan - RAN name: %s - failed saving nodebInfo. Error: %s", ranName, err)
                return nil, err
@@ -149,7 +170,7 @@ func (h *E2SetupRequestNotificationHandler) handleNewRan(ranName string, e2tIpAd
 
        nbIdentity := h.buildNbIdentity(ranName, setupRequest)
 
-       err = h.ranListManager.AddNbIdentity(entities.Node_GNB, nbIdentity)
+       err = h.ranListManager.AddNbIdentity(nodebInfo.GetNodeType(), nbIdentity)
 
        if err != nil {
                return nil, err
@@ -159,8 +180,11 @@ func (h *E2SetupRequestNotificationHandler) handleNewRan(ranName string, e2tIpAd
 }
 
 func (h *E2SetupRequestNotificationHandler) setGnbFunctions(nodebInfo *entities.NodebInfo, setupRequest *models.E2SetupRequestMessage) {
-       ranFunctions := setupRequest.ExtractRanFunctionsList()
+       if nodebInfo.GetNodeType() == entities.Node_ENB {
+               return
+       }
 
+       ranFunctions := setupRequest.ExtractRanFunctionsList()
        if ranFunctions != nil {
                nodebInfo.GetGnb().RanFunctions = ranFunctions
        }
@@ -289,17 +313,38 @@ func normalizeXml(payload []byte) []byte {
        return []byte(normalized)
 }
 
-func (h *E2SetupRequestNotificationHandler) buildNodebInfo(ranName string, e2tAddress string, request *models.E2SetupRequestMessage) *entities.NodebInfo {
+func (h *E2SetupRequestNotificationHandler) buildNodebInfo(ranName string, e2tAddress string, request *models.E2SetupRequestMessage) (*entities.NodebInfo, error) {
        nodebInfo := &entities.NodebInfo{
                AssociatedE2TInstanceAddress: e2tAddress,
                RanName:                      ranName,
-               NodeType:                     entities.Node_GNB,
-               Configuration:                &entities.NodebInfo_Gnb{Gnb: &entities.Gnb{}},
                GlobalNbId:                   h.buildGlobalNbId(request),
+               SetupFromNetwork:                         true,
+       }
+       err := h.setNodeTypeAndConfiguration(nodebInfo)
+       if err != nil {
+               return nil, err
        }
-
        h.setGnbFunctions(nodebInfo, request)
-       return nodebInfo
+       return nodebInfo, nil
+}
+
+func (h *E2SetupRequestNotificationHandler) setNodeTypeAndConfiguration(nodebInfo *entities.NodebInfo) error {
+       for k, v := range gnbTypesMap {
+               if strings.HasPrefix(nodebInfo.RanName, k) {
+                       nodebInfo.NodeType = entities.Node_GNB
+                       nodebInfo.Configuration = &entities.NodebInfo_Gnb{Gnb: &entities.Gnb{GnbType: v}}
+                       return nil
+               }
+       }
+       for k, v := range enbTypesMap {
+               if strings.HasPrefix(nodebInfo.RanName, k) {
+                       nodebInfo.NodeType = entities.Node_ENB
+                       nodebInfo.Configuration = &entities.NodebInfo_Enb{Enb: &entities.Enb{EnbType: v}}
+                       return nil
+               }
+       }
+
+       return e2managererrors.NewUnknownSetupRequestRanNameError(nodebInfo.RanName)
 }
 
 func (h *E2SetupRequestNotificationHandler) buildGlobalNbId(setupRequest *models.E2SetupRequestMessage) *entities.GlobalNbId {
index a52e8f5..f0af881 100644 (file)
@@ -42,7 +42,8 @@ import (
 const (
        e2tInstanceFullAddress                   = "10.0.2.15:9999"
        e2SetupMsgPrefix                         = e2tInstanceFullAddress + "|"
-       nodebRanName                             = "gnb:310-410-b5c67788"
+       gnbNodebRanName                          = "gnb:310-410-b5c67788"
+       enbNodebRanName                          = "enB_macro:P310-410-b5c67788"
        GnbSetupRequestXmlPath                   = "../../tests/resources/setupRequest_gnb.xml"
        EnGnbSetupRequestXmlPath                 = "../../tests/resources/setupRequest_en-gNB.xml"
        NgEnbSetupRequestXmlPath                 = "../../tests/resources/setupRequest_ng-eNB.xml"
@@ -50,6 +51,7 @@ const (
        GnbWithoutFunctionsSetupRequestXmlPath   = "../../tests/resources/setupRequest_gnb_without_functions.xml"
        E2SetupFailureResponseWithMiscCause      = "<E2AP-PDU><unsuccessfulOutcome><procedureCode>1</procedureCode><criticality><reject/></criticality><value><E2setupFailure><protocolIEs><E2setupFailureIEs><id>1</id><criticality><ignore/></criticality><value><Cause><misc><om-intervention/></misc></Cause></value></E2setupFailureIEs><E2setupFailureIEs><id>31</id><criticality><ignore/></criticality><value><TimeToWait><v60s/></TimeToWait></value></E2setupFailureIEs></protocolIEs></E2setupFailure></value></unsuccessfulOutcome></E2AP-PDU>"
        E2SetupFailureResponseWithTransportCause = "<E2AP-PDU><unsuccessfulOutcome><procedureCode>1</procedureCode><criticality><reject/></criticality><value><E2setupFailure><protocolIEs><E2setupFailureIEs><id>1</id><criticality><ignore/></criticality><value><Cause><transport><transport-resource-unavailable/></transport></Cause></value></E2setupFailureIEs><E2setupFailureIEs><id>31</id><criticality><ignore/></criticality><value><TimeToWait><v60s/></TimeToWait></value></E2setupFailureIEs></protocolIEs></E2setupFailure></value></unsuccessfulOutcome></E2AP-PDU>"
+       E2SetupFailureResponseWithRicCause      = "<E2AP-PDU><unsuccessfulOutcome><procedureCode>1</procedureCode><criticality><reject/></criticality><value><E2setupFailure><protocolIEs><E2setupFailureIEs><id>1</id><criticality><ignore/></criticality><value><Cause><ricRequest><request-id-unknown/></ricRequest></Cause></value></E2setupFailureIEs><E2setupFailureIEs><id>31</id><criticality><ignore/></criticality><value><TimeToWait><v60s/></TimeToWait></value></E2setupFailureIEs></protocolIEs></E2setupFailure></value></unsuccessfulOutcome></E2AP-PDU>"
        StateChangeMessageChannel                = "RAN_CONNECTION_STATUS_CHANGE"
 )
 
@@ -129,7 +131,7 @@ func TestE2SetupRequestNotificationHandler_GetGeneralConfigurationFailure(t *tes
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{}, common.NewInternalError(errors.New("some error")))
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
        handler.Handle(notificationRequest)
        rmrMessengerMock.AssertNotCalled(t, "SendMsg")
        e2tInstancesManagerMock.AssertNotCalled(t, "GetE2TInstance")
@@ -138,9 +140,9 @@ func TestE2SetupRequestNotificationHandler_GetGeneralConfigurationFailure(t *tes
        writerMock.AssertNotCalled(t, "SaveNodeb")
 }
 
-func getMbuf(msgType int, payloadStr string, request *models.NotificationRequest) *rmrCgo.MBuf {
+func getMbuf(ranName string, msgType int, payloadStr string, request *models.NotificationRequest) *rmrCgo.MBuf {
        payload := []byte(payloadStr)
-       mbuf := rmrCgo.NewMBuf(msgType, len(payload), nodebRanName, &payload, &request.TransactionId, request.GetMsgSrc())
+       mbuf := rmrCgo.NewMBuf(msgType, len(payload), ranName, &payload, &request.TransactionId, request.GetMsgSrc())
        return mbuf
 }
 
@@ -148,8 +150,8 @@ func TestE2SetupRequestNotificationHandler_EnableRicFalse(t *testing.T) {
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: false}, nil)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
-       mbuf := getMbuf(rmrCgo.RIC_E2_SETUP_FAILURE, E2SetupFailureResponseWithMiscCause, notificationRequest)
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
+       mbuf := getMbuf(gnbNodebRanName, rmrCgo.RIC_E2_SETUP_FAILURE, E2SetupFailureResponseWithMiscCause, notificationRequest)
        rmrMessengerMock.On("WhSendMsg", mbuf, true).Return(&rmrCgo.MBuf{}, nil)
        handler.Handle(notificationRequest)
        rmrMessengerMock.AssertCalled(t, "WhSendMsg", mbuf, true)
@@ -159,16 +161,15 @@ func TestE2SetupRequestNotificationHandler_EnableRicFalse(t *testing.T) {
        writerMock.AssertNotCalled(t, "SaveNodeb")
 }
 
-
 func TestE2SetupRequestNotificationHandler_HandleNewRanSaveNodebFailure(t *testing.T) {
        xml := readXmlFile(t, GnbSetupRequestXmlPath)
        handler, readerMock, writerMock, _, e2tInstancesManagerMock, _ := initMocks(t)
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
-       readerMock.On("GetNodeb", nodebRanName).Return(gnb, common.NewResourceNotFoundError("Not found"))
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xml...)}
-       nodebInfo := getExpectedNodebForNewRan(notificationRequest.Payload)
+       readerMock.On("GetNodeb", gnbNodebRanName).Return(gnb, common.NewResourceNotFoundError("Not found"))
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xml...)}
+       nodebInfo := getExpectedGnbNodebForNewRan(notificationRequest.Payload)
        writerMock.On("SaveNodeb", nodebInfo).Return(common.NewInternalError(errors.New("error")))
        handler.Handle(notificationRequest)
 
@@ -177,17 +178,36 @@ func TestE2SetupRequestNotificationHandler_HandleNewRanSaveNodebFailure(t *testi
        e2tInstancesManagerMock.AssertExpectations(t)
 }
 
+func TestE2SetupRequestNotificationHandler_HandleNewRan_invalidRanName(t *testing.T) {
+       xml := readXmlFile(t, EnbSetupRequestXmlPath)
+       handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, _ := initMocks(t)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
+       var enb *entities.NodebInfo
+       invalidEnbRanName := "enB-macro:P310-410-b5c67788"
+       readerMock.On("GetNodeb", invalidEnbRanName).Return(enb, common.NewResourceNotFoundError("Not found"))
+       notificationRequest := &models.NotificationRequest{RanName: invalidEnbRanName, Payload: append([]byte(e2SetupMsgPrefix), xml...)}
+       mbuf := getMbuf(invalidEnbRanName, rmrCgo.RIC_E2_SETUP_FAILURE, E2SetupFailureResponseWithRicCause, notificationRequest)
+       rmrMessengerMock.On("WhSendMsg", mbuf, true).Return(&rmrCgo.MBuf{}, nil)
+       handler.Handle(notificationRequest)
+
+       readerMock.AssertExpectations(t)
+       writerMock.AssertExpectations(t)
+       rmrMessengerMock.AssertCalled(t, "WhSendMsg", mbuf, true)
+       e2tInstancesManagerMock.AssertExpectations(t)
+}
+
 func TestE2SetupRequestNotificationHandler_HandleNewRanAddNbIdentityFailure(t *testing.T) {
        xml := readXmlFile(t, GnbSetupRequestXmlPath)
        handler, readerMock, writerMock, _, e2tInstancesManagerMock, _ := initMocks(t)
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
-       readerMock.On("GetNodeb", nodebRanName).Return(gnb, common.NewResourceNotFoundError("Not found"))
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xml...)}
-       nodebInfo := getExpectedNodebForNewRan(notificationRequest.Payload)
+       readerMock.On("GetNodeb", gnbNodebRanName).Return(gnb, common.NewResourceNotFoundError("Not found"))
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xml...)}
+       nodebInfo := getExpectedGnbNodebForNewRan(notificationRequest.Payload)
        writerMock.On("SaveNodeb", nodebInfo).Return(nil)
-       nbIdentity := &entities.NbIdentity{InventoryName: nodebRanName, GlobalNbId: nodebInfo.GlobalNbId}
+       nbIdentity := &entities.NbIdentity{InventoryName: gnbNodebRanName, GlobalNbId: nodebInfo.GlobalNbId}
        writerMock.On("AddNbIdentity", entities.Node_GNB, nbIdentity).Return(common.NewInternalError(errors.New("error")))
        handler.Handle(notificationRequest)
        readerMock.AssertExpectations(t)
@@ -195,27 +215,38 @@ func TestE2SetupRequestNotificationHandler_HandleNewRanAddNbIdentityFailure(t *t
        e2tInstancesManagerMock.AssertExpectations(t)
 }
 
-func testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t *testing.T, xmlPath string) {
+func testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t *testing.T, xmlPath string, nodeType entities.Node_Type) {
        xml := readXmlFile(t, xmlPath)
+       var ranName string
+       if nodeType == entities.Node_GNB {
+               ranName = gnbNodebRanName
+       } else {
+               ranName = enbNodebRanName
+       }
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
-       readerMock.On("GetNodeb", nodebRanName).Return(gnb, common.NewResourceNotFoundError("Not found"))
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xml...)}
-       nodebInfo := getExpectedNodebForNewRan(notificationRequest.Payload)
-       writerMock.On("SaveNodeb", nodebInfo).Return(nil)
-       nbIdentity := &entities.NbIdentity{InventoryName: nodebRanName, GlobalNbId: nodebInfo.GlobalNbId}
-       writerMock.On("AddNbIdentity", entities.Node_GNB, nbIdentity).Return(nil)
-       updatedNodebInfo := *nodebInfo
+       readerMock.On("GetNodeb", ranName).Return(gnb, common.NewResourceNotFoundError("Not found"))
+       notificationRequest := &models.NotificationRequest{RanName: ranName, Payload: append([]byte(e2SetupMsgPrefix), xml...)}
+       var expectedNodebInfo *entities.NodebInfo
+       if nodeType == entities.Node_GNB {
+               expectedNodebInfo = getExpectedGnbNodebForNewRan(notificationRequest.Payload)
+       } else {
+               expectedNodebInfo = getExpectedEnbNodebForNewRan(notificationRequest.Payload)
+       }
+       writerMock.On("SaveNodeb", expectedNodebInfo).Return(nil)
+       nbIdentity := &entities.NbIdentity{InventoryName: ranName, GlobalNbId: expectedNodebInfo.GlobalNbId}
+       writerMock.On("AddNbIdentity", nodeType, nbIdentity).Return(nil)
+       updatedNodebInfo := *expectedNodebInfo
        updatedNodebInfo.ConnectionStatus = entities.ConnectionStatus_CONNECTED
-       writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNodebInfo, nodebRanName+"_CONNECTED").Return(nil)
+       writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNodebInfo, ranName+"_CONNECTED").Return(nil)
        routingManagerClientMock.On("AssociateRanToE2TInstance", e2tInstanceFullAddress, mock.Anything).Return(nil)
-       updatedNodebInfo2 := *nodebInfo
+       updatedNodebInfo2 := *expectedNodebInfo
        updatedNodebInfo2.ConnectionStatus = entities.ConnectionStatus_CONNECTED
        updatedNodebInfo2.AssociatedE2TInstanceAddress = e2tInstanceFullAddress
        writerMock.On("UpdateNodebInfo", &updatedNodebInfo2).Return(nil)
-       e2tInstancesManagerMock.On("AddRansToInstance", e2tInstanceFullAddress, []string{nodebRanName}).Return(nil)
+       e2tInstancesManagerMock.On("AddRansToInstance", e2tInstanceFullAddress, []string{ranName}).Return(nil)
        rmrMessengerMock.On("SendMsg", mock.Anything, mock.Anything).Return(&rmrCgo.MBuf{}, nil)
 
        handler.Handle(notificationRequest)
@@ -225,22 +256,36 @@ func testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t *testing.T, xml
        e2tInstancesManagerMock.AssertExpectations(t)
 }
 
-
-
 func TestE2SetupRequestNotificationHandler_HandleNewGnbSuccess(t *testing.T) {
-       testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t, GnbSetupRequestXmlPath)
+       testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t, GnbSetupRequestXmlPath, entities.Node_GNB)
 }
 
 func TestE2SetupRequestNotificationHandler_HandleNewGnbWithoutFunctionsSuccess(t *testing.T) {
-       testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t, GnbWithoutFunctionsSetupRequestXmlPath)
+       testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t, GnbWithoutFunctionsSetupRequestXmlPath, entities.Node_GNB)
 }
 
 func TestE2SetupRequestNotificationHandler_HandleNewEnGnbSuccess(t *testing.T) {
-       testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t, EnGnbSetupRequestXmlPath)
+       testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t, EnGnbSetupRequestXmlPath, entities.Node_GNB)
 }
 
 func TestE2SetupRequestNotificationHandler_HandleNewNgEnbSuccess(t *testing.T) {
-       testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t, NgEnbSetupRequestXmlPath)
+       testE2SetupRequestNotificationHandler_HandleNewRanSuccess(t, NgEnbSetupRequestXmlPath, entities.Node_ENB)
+}
+
+func TestExtractionOfNodeTypeFromRanName(t *testing.T) {
+       handler, _, _, _, _, _ := initMocks(t)
+       validRanNames := []string {"gnb_P310_410_b5c67788","en_gnb_P310_410_b5c67788","ng_enB_macro_P310_410_b5c67788","ng_enB_shortmacro_P310_410_b5c67788","ng_enB_longmacro_P310_410_b5c67788","enB_macro_P310_410_b5c67788","enB_home_P310_410_b5c67788","enB_shortmacro_P310_410_b5c67788","enB_longmacro_P310_410_b5c67788"}
+       for _,v := range validRanNames {
+               nodeb := &entities.NodebInfo{RanName: v}
+               err := handler.setNodeTypeAndConfiguration(nodeb)
+               assert.Nil(t, err)
+       }
+       inValidRanNames := []string {"P310_410_b5c67788","blabla_P310_410_b5c67788","ng_enB-macro_P310_410_b5c67788","ng_enb_shortmacro_P310_410_b5c67788","ng_enB-longmacro_P310_410_b5c67788","enB_new_macro_P310_410_b5c67788"}
+       for _,v := range inValidRanNames {
+               nodeb := &entities.NodebInfo{RanName: v}
+               err := handler.setNodeTypeAndConfiguration(nodeb)
+               assert.NotNil(t, err, v)
+       }
 }
 
 func testE2SetupRequestNotificationHandler_HandleExistingConnectedGnbSuccess(t *testing.T, withFunctions bool) {
@@ -249,7 +294,7 @@ func testE2SetupRequestNotificationHandler_HandleExistingConnectedGnbSuccess(t *
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var nodebInfo = &entities.NodebInfo{
-               RanName:                      nodebRanName,
+               RanName:                      gnbNodebRanName,
                AssociatedE2TInstanceAddress: e2tInstanceFullAddress,
                ConnectionStatus:             entities.ConnectionStatus_CONNECTED,
                NodeType:                     entities.Node_GNB,
@@ -261,13 +306,13 @@ func testE2SetupRequestNotificationHandler_HandleExistingConnectedGnbSuccess(t *
                gnb.RanFunctions = []*entities.RanFunction{{RanFunctionId: 2, RanFunctionRevision: 2}}
        }
 
-       readerMock.On("GetNodeb", nodebRanName).Return(nodebInfo, nil)
+       readerMock.On("GetNodeb", gnbNodebRanName).Return(nodebInfo, nil)
        routingManagerClientMock.On("AssociateRanToE2TInstance", e2tInstanceFullAddress, mock.Anything).Return(nil)
 
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
        gnbToUpdate := getExpectedNodebForExistingRan(*nodebInfo, notificationRequest.Payload)
        writerMock.On("UpdateNodebInfo", gnbToUpdate).Return(nil)
-       e2tInstancesManagerMock.On("AddRansToInstance", e2tInstanceFullAddress, []string{nodebRanName}).Return(nil)
+       e2tInstancesManagerMock.On("AddRansToInstance", e2tInstanceFullAddress, []string{gnbNodebRanName}).Return(nil)
        var errEmpty error
        rmrMessengerMock.On("SendMsg", mock.Anything, true).Return(&rmrCgo.MBuf{}, errEmpty)
        handler.Handle(notificationRequest)
@@ -292,27 +337,27 @@ func TestE2SetupRequestNotificationHandler_HandleExistingDisconnectedGnbSuccess(
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var nodebInfo = &entities.NodebInfo{
-               RanName:                      nodebRanName,
+               RanName:                      gnbNodebRanName,
                AssociatedE2TInstanceAddress: e2tInstanceFullAddress,
                ConnectionStatus:             entities.ConnectionStatus_DISCONNECTED,
                NodeType:                     entities.Node_GNB,
                Configuration:                &entities.NodebInfo_Gnb{Gnb: &entities.Gnb{}},
        }
 
-       readerMock.On("GetNodeb", nodebRanName).Return(nodebInfo, nil)
+       readerMock.On("GetNodeb", gnbNodebRanName).Return(nodebInfo, nil)
        routingManagerClientMock.On("AssociateRanToE2TInstance", e2tInstanceFullAddress, mock.Anything).Return(nil)
 
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
        gnbToUpdate := getExpectedNodebForExistingRan(*nodebInfo, notificationRequest.Payload)
        writerMock.On("UpdateNodebInfo", gnbToUpdate).Return(nil)
        gnbToUpdate2 := *gnbToUpdate
        gnbToUpdate2.ConnectionStatus = entities.ConnectionStatus_CONNECTED
-       writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &gnbToUpdate2, nodebRanName+"_CONNECTED").Return(nil)
+       writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &gnbToUpdate2, gnbNodebRanName+"_CONNECTED").Return(nil)
        gnbToUpdate3 := *gnbToUpdate
        gnbToUpdate3.ConnectionStatus = entities.ConnectionStatus_CONNECTED
        gnbToUpdate3.AssociatedE2TInstanceAddress = e2tInstanceFullAddress
        writerMock.On("UpdateNodebInfo", &gnbToUpdate3).Return(nil)
-       e2tInstancesManagerMock.On("AddRansToInstance", e2tInstanceFullAddress, []string{nodebRanName}).Return(nil)
+       e2tInstancesManagerMock.On("AddRansToInstance", e2tInstanceFullAddress, []string{gnbNodebRanName}).Return(nil)
        var errEmpty error
        rmrMessengerMock.On("SendMsg", mock.Anything, mock.Anything).Return(&rmrCgo.MBuf{}, errEmpty)
        handler.Handle(notificationRequest)
@@ -330,17 +375,19 @@ func getExpectedNodebForExistingRan(nodeb entities.NodebInfo, payload []byte) *e
        return &nodeb
 }
 
-func getExpectedNodebForNewRan(payload []byte) *entities.NodebInfo {
+func getExpectedGnbNodebForNewRan(payload []byte) *entities.NodebInfo {
        pipInd := bytes.IndexByte(payload, '|')
        setupRequest := &models.E2SetupRequestMessage{}
        _ = xml.Unmarshal(normalizeXml(payload[pipInd+1:]), &setupRequest.E2APPDU)
 
        nodeb := &entities.NodebInfo{
                AssociatedE2TInstanceAddress: e2tInstanceFullAddress,
-               RanName:                      nodebRanName,
+               RanName:                      gnbNodebRanName,
+               SetupFromNetwork:             true,
                NodeType:                     entities.Node_GNB,
                Configuration: &entities.NodebInfo_Gnb{
                        Gnb: &entities.Gnb{
+                               GnbType:      entities.GnbType_GNB,
                                RanFunctions: setupRequest.ExtractRanFunctionsList(),
                        },
                },
@@ -353,11 +400,35 @@ func getExpectedNodebForNewRan(payload []byte) *entities.NodebInfo {
        return nodeb
 }
 
+func getExpectedEnbNodebForNewRan(payload []byte) *entities.NodebInfo {
+       pipInd := bytes.IndexByte(payload, '|')
+       setupRequest := &models.E2SetupRequestMessage{}
+       _ = xml.Unmarshal(normalizeXml(payload[pipInd+1:]), &setupRequest.E2APPDU)
+
+       nodeb := &entities.NodebInfo{
+               AssociatedE2TInstanceAddress: e2tInstanceFullAddress,
+               RanName:                      enbNodebRanName,
+               SetupFromNetwork:             true,
+               NodeType:                     entities.Node_ENB,
+               Configuration: &entities.NodebInfo_Enb{
+                       Enb: &entities.Enb{
+                               EnbType:      entities.EnbType_MACRO_ENB,
+                       },
+               },
+               GlobalNbId: &entities.GlobalNbId{
+                       PlmnId: setupRequest.GetPlmnId(),
+                       NbId:   setupRequest.GetNbId(),
+               },
+       }
+
+       return nodeb
+}
+
 func TestE2SetupRequestNotificationHandler_HandleParseError(t *testing.T) {
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte("invalid_prefix"), xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte("invalid_prefix"), xmlGnb...)}
        handler.Handle(notificationRequest)
        readerMock.AssertNotCalled(t, "GetNodeb", mock.Anything)
        writerMock.AssertNotCalled(t, "SaveNodeb", mock.Anything, mock.Anything)
@@ -370,7 +441,7 @@ func TestE2SetupRequestNotificationHandler_HandleParseError(t *testing.T) {
 func TestE2SetupRequestNotificationHandler_HandleUnmarshalError(t *testing.T) {
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), "xmlGnb"...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), "xmlGnb"...)}
        handler.Handle(notificationRequest)
        readerMock.AssertNotCalled(t, "GetNodeb", mock.Anything)
        writerMock.AssertNotCalled(t, "SaveNodeb", mock.Anything, mock.Anything)
@@ -386,7 +457,7 @@ func TestE2SetupRequestNotificationHandler_HandleGetE2TInstanceError(t *testing.
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, common.NewResourceNotFoundError("Not found"))
        prefBytes := []byte(e2SetupMsgPrefix)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append(prefBytes, xmlGnb...)}
        handler.Handle(notificationRequest)
        e2tInstancesManagerMock.AssertCalled(t, "GetE2TInstance", e2tInstanceFullAddress)
        readerMock.AssertNotCalled(t, "GetNodeb", mock.Anything)
@@ -404,7 +475,7 @@ func TestE2SetupRequestNotificationHandler_HandleGetNodebError(t *testing.T) {
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
        readerMock.On("GetNodeb", mock.Anything).Return(gnb, common.NewInternalError(errors.New("some error")))
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
        handler.Handle(notificationRequest)
        e2tInstancesManagerMock.AssertCalled(t, "GetE2TInstance", e2tInstanceFullAddress)
        readerMock.AssertCalled(t, "GetNodeb", mock.Anything)
@@ -423,22 +494,22 @@ func TestE2SetupRequestNotificationHandler_HandleAssociationError(t *testing.T)
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
        readerMock.On("GetNodeb", mock.Anything).Return(gnb, common.NewResourceNotFoundError("Not found"))
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
-       nodebInfo := getExpectedNodebForNewRan(notificationRequest.Payload)
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append([]byte(e2SetupMsgPrefix), xmlGnb...)}
+       nodebInfo := getExpectedGnbNodebForNewRan(notificationRequest.Payload)
        writerMock.On("SaveNodeb", nodebInfo).Return(nil)
-       nbIdentity := &entities.NbIdentity{InventoryName: nodebRanName, GlobalNbId: nodebInfo.GlobalNbId}
+       nbIdentity := &entities.NbIdentity{InventoryName: gnbNodebRanName, GlobalNbId: nodebInfo.GlobalNbId}
        writerMock.On("AddNbIdentity", entities.Node_GNB, nbIdentity).Return(nil)
        updatedNodebInfo := *nodebInfo
        updatedNodebInfo.ConnectionStatus = entities.ConnectionStatus_CONNECTED
-       writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNodebInfo, nodebRanName+"_CONNECTED").Return(nil)
+       writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNodebInfo, gnbNodebRanName+"_CONNECTED").Return(nil)
        writerMock.On("UpdateNodebInfo", mock.Anything).Return(nil)
        e2tInstancesManagerMock.On("AddRansToInstance", mock.Anything, mock.Anything).Return(nil)
        routingManagerClientMock.On("AssociateRanToE2TInstance", e2tInstanceFullAddress, mock.Anything).Return(errors.New("association error"))
        updatedNodebInfo2 := *nodebInfo
        updatedNodebInfo2.ConnectionStatus = entities.ConnectionStatus_DISCONNECTED
-       writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNodebInfo2, nodebRanName+"_DISCONNECTED").Return(nil)
+       writerMock.On("UpdateNodebInfoOnConnectionStatusInversion", &updatedNodebInfo2, gnbNodebRanName+"_DISCONNECTED").Return(nil)
        var errEmpty error
-       mbuf := getMbuf(rmrCgo.RIC_E2_SETUP_FAILURE, E2SetupFailureResponseWithTransportCause, notificationRequest)
+       mbuf := getMbuf(gnbNodebRanName, rmrCgo.RIC_E2_SETUP_FAILURE, E2SetupFailureResponseWithTransportCause, notificationRequest)
        rmrMessengerMock.On("WhSendMsg", mbuf, true).Return(&rmrCgo.MBuf{}, errEmpty)
        handler.Handle(notificationRequest)
        readerMock.AssertCalled(t, "GetNodeb", mock.Anything)
@@ -490,7 +561,7 @@ func TestE2SetupRequestNotificationHandler_ConvertTo20BitStringError(t *testing.
        rmrMessage := &rmrCgo.MBuf{}
        rmrMessengerMock.On("SendMsg", mock.Anything, mock.Anything).Return(rmrMessage, errEmpty)
        prefBytes := []byte(e2SetupMsgPrefix)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, xmlEnGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append(prefBytes, xmlEnGnb...)}
        handler.Handle(notificationRequest)
        readerMock.AssertCalled(t, "GetNodeb", mock.Anything)
        e2tInstancesManagerMock.AssertCalled(t, "GetE2TInstance", e2tInstanceFullAddress)
@@ -504,12 +575,12 @@ func TestE2SetupRequestNotificationHandler_ConvertTo20BitStringError(t *testing.
 func TestE2SetupRequestNotificationHandler_HandleExistingGnbInvalidStatusError(t *testing.T) {
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
        handler, readerMock, writerMock, routingManagerClientMock, e2tInstancesManagerMock, rmrMessengerMock := initMocks(t)
-       var gnb = &entities.NodebInfo{RanName: nodebRanName, ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN}
+       var gnb = &entities.NodebInfo{RanName: gnbNodebRanName, ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN}
        readerMock.On("GetNodeb", mock.Anything).Return(gnb, nil)
        readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
        e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        prefBytes := []byte(e2SetupMsgPrefix)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: gnbNodebRanName, Payload: append(prefBytes, xmlGnb...)}
        handler.Handle(notificationRequest)
        readerMock.AssertCalled(t, "GetNodeb", mock.Anything)
        e2tInstancesManagerMock.AssertCalled(t, "GetE2TInstance", e2tInstanceFullAddress)
index fa711fb..35a255a 100644 (file)
@@ -130,3 +130,8 @@ func (rnibWriterMock *RnibWriterMock) RemoveNbIdentity(nodeType entities.Node_Ty
        args := rnibWriterMock.Called(nodeType, nbIdentity)
        return args.Error(0)
 }
+
+func (rnibWriterMock *RnibWriterMock) AddEnb(nodebInfo *entities.NodebInfo) error {
+       args := rnibWriterMock.Called(nodebInfo)
+       return args.Error(0)
+}
\ No newline at end of file
index 3069258..7678fb3 100644 (file)
@@ -59,6 +59,7 @@ type RNibWriter interface {
        UpdateEnb(nodebInfo *entities.NodebInfo, servedCells []*entities.ServedCellInfo) error
        AddNbIdentity(nodeType entities.Node_Type, nbIdentity *entities.NbIdentity) error
        RemoveNbIdentity(nodeType entities.Node_Type, nbIdentity *entities.NbIdentity) error
+       AddEnb(nodebInfo *entities.NodebInfo) error
 }
 
 /*
@@ -166,13 +167,48 @@ func (w *rNibWriterInstance) SaveNodeb(nodebInfo *entities.NodebInfo) error {
                }
        }
 
-       if nodebInfo.GetNodeType() == entities.Node_ENB {
-               channelsAndEvents := getChannelsAndEventsPair(w.rnibWriterConfig.RanManipulationMessageChannel, nodebInfo.RanName, RanAddedEvent)
-               err = w.sdl.SetAndPublish(channelsAndEvents, pairs)
-       } else {
-               err = w.sdl.Set(pairs)
+       err = w.sdl.Set(pairs)
+
+       if err != nil {
+               return common.NewInternalError(err)
        }
 
+       return nil
+}
+
+func (w *rNibWriterInstance) AddEnb(nodebInfo *entities.NodebInfo) error {
+
+       data, err := proto.Marshal(nodebInfo)
+
+       if err != nil {
+               return common.NewInternalError(err)
+       }
+
+       var pairs []interface{}
+       key, rNibErr := common.ValidateAndBuildNodeBNameKey(nodebInfo.RanName)
+
+       if rNibErr != nil {
+               return rNibErr
+       }
+
+       pairs = append(pairs, key, data)
+
+       if nodebInfo.GlobalNbId != nil {
+
+               key, rNibErr = common.ValidateAndBuildNodeBIdKey(nodebInfo.GetNodeType().String(), nodebInfo.GlobalNbId.GetPlmnId(), nodebInfo.GlobalNbId.GetNbId())
+               if rNibErr != nil {
+                       return rNibErr
+               }
+               pairs = append(pairs, key, data)
+       }
+
+       pairs, rNibErr = appendEnbCells(nodebInfo.RanName, nodebInfo.GetEnb().GetServedCells(), pairs)
+       if rNibErr != nil {
+               return rNibErr
+       }
+
+       channelsAndEvents := getChannelsAndEventsPair(w.rnibWriterConfig.RanManipulationMessageChannel, nodebInfo.RanName, RanAddedEvent)
+       err = w.sdl.SetAndPublish(channelsAndEvents, pairs)
        if err != nil {
                return common.NewInternalError(err)
        }
index 0c92aa8..4e0cdfc 100644 (file)
@@ -379,8 +379,7 @@ func TestSaveEnb(t *testing.T) {
        setExpected = append(setExpected, fmt.Sprintf("CELL:%s", cell.GetCellId()), cellData)
        setExpected = append(setExpected, fmt.Sprintf("PCI:%s:%02x", RanName, cell.GetPci()), cellData)
 
-       sdlInstanceMock.On("SetAndPublish", []string{"RAN_MANIPULATION", RanName + "_" + RanAddedEvent}, []interface{}{setExpected}).Return(e)
-
+       sdlInstanceMock.On("Set", []interface{}{setExpected}).Return(e)
        rNibErr := w.SaveNodeb(&nb)
        assert.Nil(t, rNibErr)
 }
@@ -648,14 +647,23 @@ func TestSaveUnknownTypeEntityFailure(t *testing.T) {
        assert.IsType(t, &common.ValidationError{}, actualErr)
 }
 
-func TestSaveEntityFailure(t *testing.T) {
+func TestSaveEntitySetFailure(t *testing.T) {
        name := "name"
        plmnId := "02f829"
        nbId := "4a952a0a"
 
        w, sdlInstanceMock := initSdlInstanceMock(namespace)
-       gnb := entities.NodebInfo{}
-       gnb.NodeType = entities.Node_GNB
+       gnb := entities.NodebInfo{
+               RanName: name,
+               NodeType:         entities.Node_GNB,
+               ConnectionStatus: 1,
+               GlobalNbId: &entities.GlobalNbId{
+                       NbId:   nbId,
+                       PlmnId: plmnId,
+               },
+               Ip:   "localhost",
+               Port: 5656,
+       }
        data, err := proto.Marshal(&gnb)
        if err != nil {
                t.Errorf("#rNibWriter_test.TestSaveEntityFailure - Failed to marshal NodeB entity. Error: %v", err)
@@ -668,6 +676,35 @@ func TestSaveEntityFailure(t *testing.T) {
        assert.NotEmpty(t, rNibErr)
 }
 
+func TestSaveEntitySetAndPublishFailure(t *testing.T) {
+       name := "name"
+       plmnId := "02f829"
+       nbId := "4a952a0a"
+
+       w, sdlInstanceMock := initSdlInstanceMock(namespace)
+       enb := entities.NodebInfo{
+               RanName: name,
+               NodeType:         entities.Node_ENB,
+               ConnectionStatus: 1,
+               GlobalNbId: &entities.GlobalNbId{
+                       NbId:   nbId,
+                       PlmnId: plmnId,
+               },
+               Ip:   "localhost",
+               Port: 5656,
+       }
+       data, err := proto.Marshal(&enb)
+       if err != nil {
+               t.Errorf("#rNibWriter_test.TestSaveEntityFailure - Failed to marshal NodeB entity. Error: %v", err)
+       }
+       setExpected := []interface{}{"RAN:" + name, data}
+       setExpected = append(setExpected, "ENB:"+plmnId+":"+nbId, data)
+       expectedErr := errors.New("expected error")
+       sdlInstanceMock.On("SetAndPublish", []string{"RAN_MANIPULATION", name + "_" + RanAddedEvent}, []interface{}{setExpected}).Return(expectedErr)
+       rNibErr := w.AddEnb(&enb)
+       assert.NotEmpty(t, rNibErr)
+}
+
 func TestGetRNibWriter(t *testing.T) {
        received, _ := initSdlInstanceMock(namespace)
        assert.NotEmpty(t, received)
@@ -1105,6 +1142,88 @@ func TestRemoveNbIdentityError(t *testing.T) {
        sdlInstanceMock.AssertExpectations(t)
 }
 
+func TestAddEnb(t *testing.T) {
+       ranName := "RAN:" + RanName
+       w, sdlInstanceMock := initSdlInstanceMock(namespace)
+       nb := entities.NodebInfo{
+               RanName:          RanName,
+               NodeType:         entities.Node_ENB,
+               ConnectionStatus: entities.ConnectionStatus_CONNECTED,
+               Ip:               "localhost",
+               Port:             5656,
+               GlobalNbId: &entities.GlobalNbId{
+                       NbId:   "4a952a0a",
+                       PlmnId: "02f829",
+               },
+       }
+
+       enb := entities.Enb{}
+       cell := &entities.ServedCellInfo{CellId: "aaff", Pci: 3}
+       cellEntity := entities.Cell{Type: entities.Cell_LTE_CELL, Cell: &entities.Cell_ServedCellInfo{ServedCellInfo: cell}}
+       enb.ServedCells = []*entities.ServedCellInfo{cell}
+       nb.Configuration = &entities.NodebInfo_Enb{Enb: &enb}
+       data, err := proto.Marshal(&nb)
+       if err != nil {
+               t.Errorf("#rNibWriter_test.TestSaveEnb - Failed to marshal NodeB entity. Error: %v", err)
+       }
+       var e error
+
+       cellData, err := proto.Marshal(&cellEntity)
+       if err != nil {
+               t.Errorf("#rNibWriter_test.TestSaveEnb - Failed to marshal Cell entity. Error: %v", err)
+       }
+       var setExpected []interface{}
+       setExpected = append(setExpected, ranName, data)
+       setExpected = append(setExpected, "ENB:02f829:4a952a0a", data)
+       setExpected = append(setExpected, fmt.Sprintf("CELL:%s", cell.GetCellId()), cellData)
+       setExpected = append(setExpected, fmt.Sprintf("PCI:%s:%02x", RanName, cell.GetPci()), cellData)
+
+       sdlInstanceMock.On("SetAndPublish", []string{"RAN_MANIPULATION", RanName + "_" + RanAddedEvent}, []interface{}{setExpected}).Return(e)
+
+       rNibErr := w.AddEnb(&nb)
+       assert.Nil(t, rNibErr)
+}
+
+func TestAddEnbCellIdValidationFailure(t *testing.T) {
+       w, _ := initSdlInstanceMock(namespace)
+       nb := entities.NodebInfo{}
+       nb.RanName = "name"
+       nb.NodeType = entities.Node_ENB
+       nb.ConnectionStatus = 1
+       nb.Ip = "localhost"
+       nb.Port = 5656
+       enb := entities.Enb{}
+       cell := &entities.ServedCellInfo{Pci: 3}
+       enb.ServedCells = []*entities.ServedCellInfo{cell}
+       nb.Configuration = &entities.NodebInfo_Enb{Enb: &enb}
+       rNibErr := w.AddEnb(&nb)
+       assert.NotNil(t, rNibErr)
+       assert.IsType(t, &common.ValidationError{}, rNibErr)
+       assert.Equal(t, "#utils.ValidateAndBuildCellIdKey - an empty cell id received", rNibErr.Error())
+}
+
+func TestAddEnbInventoryNameValidationFailure(t *testing.T) {
+       w, _ := initSdlInstanceMock(namespace)
+       nb := entities.NodebInfo{
+               NodeType:         entities.Node_ENB,
+               ConnectionStatus: entities.ConnectionStatus_CONNECTED,
+               Ip:               "localhost",
+               Port:             5656,
+               GlobalNbId: &entities.GlobalNbId{
+                       NbId:   "4a952a0a",
+                       PlmnId: "02f829",
+               },
+       }
+       enb := entities.Enb{}
+       cell := &entities.ServedCellInfo{CellId: "aaa", Pci: 3}
+       enb.ServedCells = []*entities.ServedCellInfo{cell}
+       nb.Configuration = &entities.NodebInfo_Enb{Enb: &enb}
+       rNibErr := w.AddEnb(&nb)
+       assert.NotNil(t, rNibErr)
+       assert.IsType(t, &common.ValidationError{}, rNibErr)
+       assert.Equal(t, "#utils.ValidateAndBuildNodeBNameKey - an empty inventory name received", rNibErr.Error())
+}
+
 //Integration tests
 //
 //func TestSaveEnbGnbInteg(t *testing.T){
index 7125271..7d3d6c5 100644 (file)
@@ -57,6 +57,7 @@ type RNibDataService interface {
        UpdateEnb(nodebInfo *entities.NodebInfo, servedCells []*entities.ServedCellInfo) error
        AddNbIdentity(nodeType entities.Node_Type, nbIdentity *entities.NbIdentity) error
        RemoveNbIdentity(nodeType entities.Node_Type, nbIdentity *entities.NbIdentity) error
+       AddEnb(nodebInfo *entities.NodebInfo) error
 }
 
 type rNibDataService struct {
@@ -368,6 +369,17 @@ func (w *rNibDataService) UpdateNodebInfoOnConnectionStatusInversion(nodebInfo *
        return err
 }
 
+func (w *rNibDataService) AddEnb(nodebInfo *entities.NodebInfo) error {
+       w.logger.Infof("#RnibDataService.AddEnb - nodebInfo: %s", nodebInfo)
+
+       err := w.retry("AddEnb", func() (err error) {
+               err = w.rnibWriter.AddEnb(nodebInfo)
+               return
+       })
+
+       return err
+}
+
 func (w *rNibDataService) retry(rnibFunc string, f func() error) (err error) {
        attempts := w.maxAttempts