[RIC-396] Reject E2 Setup when ricEnabled = false 04/4104/1
authoridanshal <idan.shalom@intl.att.com>
Mon, 15 Jun 2020 14:49:34 +0000 (17:49 +0300)
committeridanshal <idan.shalom@intl.att.com>
Mon, 15 Jun 2020 14:49:41 +0000 (17:49 +0300)
Change-Id: I94897e199189072331d2f85ca95eb97a98775329
Signed-off-by: idanshal <idan.shalom@intl.att.com>
Automation/Tests/E2_Setup_Failure/Enable_Ric_False_Setup_Failure.robot [new file with mode: 0644]
Automation/Tests/E2_Setup_Failure/RM_Error_Setup_Failure.robot [moved from Automation/Tests/Setup_Failure/Setup_failure.robot with 97% similarity]
Automation/Tests/E2_Setup_Failure/__init__.robot [moved from Automation/Tests/Setup_Failure/__init__.robot with 100% similarity]
Automation/Tests/Resource/Keywords.robot
Automation/Tests/Scripts/cleanup_db.py
Automation/Tests/Scripts/e2mdbscripts.py
E2Manager/handlers/rmrmsghandlers/e2_setup_request_notification_handler.go
E2Manager/handlers/rmrmsghandlers/e2_setup_request_notification_handler_test.go
E2Manager/models/cause.go [new file with mode: 0644]
E2Manager/models/e2_setup_response_message.go
E2Manager/rNibWriter/rNibWriter_test.go

diff --git a/Automation/Tests/E2_Setup_Failure/Enable_Ric_False_Setup_Failure.robot b/Automation/Tests/E2_Setup_Failure/Enable_Ric_False_Setup_Failure.robot
new file mode 100644 (file)
index 0000000..acada18
--- /dev/null
@@ -0,0 +1,50 @@
+##############################################################################
+#
+#   Copyright (c) 2019 AT&T Intellectual Property.
+#
+#   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).
+#
+
+
+*** Settings ***
+Suite Setup   Prepare Enviorment
+Resource   ../Resource/resource.robot
+Resource   ../Resource/Keywords.robot
+Resource    ../Resource/scripts_variables.robot
+Library     OperatingSystem
+Library     ../Scripts/find_rmr_message.py
+Library     ../Scripts/e2mdbscripts.py
+Library     REST        ${url}
+Suite Teardown  Flush And Populate DB
+
+
+*** Test Cases ***
+
+Disable ric and restart simulator
+    ${result}    e2mdbscripts.set_enable_ric_false
+    Restart simulator
+
+
+prepare logs for tests
+    Remove log files
+    Save logs
+
+
+E2M Logs - Verify RMR Message
+    ${result}    find_rmr_message.verify_logs   ${EXECDIR}   ${e2mgr_log_filename}  ${Setup_failure_message_type}    ${None}
+    Should Be Equal As Strings    ${result}      True
\ No newline at end of file
@@ -32,8 +32,6 @@ Library     REST        ${url}
 Suite Teardown  Start RoutingManager Simulator
 
 
-
-
 *** Test Cases ***
 Stop Routing manager simulator and restarting simulator
     Stop RoutingManager Simulator
@@ -59,9 +57,4 @@ Get request gnb
 
 E2M Logs - Verify RMR Message
     ${result}    find_rmr_message.verify_logs   ${EXECDIR}   ${e2mgr_log_filename}  ${Setup_failure_message_type}    ${None}
-    Should Be Equal As Strings    ${result}      True
-
-
-
-
-
+    Should Be Equal As Strings    ${result}      True
\ No newline at end of file
index 46296d8..2f45a2d 100644 (file)
@@ -126,3 +126,7 @@ Restart simulator with less docker
     ${result}=  Run And Return Rc And Output     ${docker_command}
     Should Be Equal As Integers    ${result[1]}    ${docker_number-1}
 
+Flush And Populate DB
+    ${flush}  cleanup_db.flush
+    Sleep  2s
+
index 4dd3ff0..979da9a 100644 (file)
@@ -33,9 +33,8 @@ def flush():
     r = redis.Redis(host=c, port=p, db=0)
 
     r.flushall()
-
+    r.set("{e2Manager},GENERAL","{\"enableRic\":true}")
     r.set("{e2Manager},E2TAddresses", "[\"10.0.2.15:38000\"]")
-
     r.set("{e2Manager},E2TInstance:10.0.2.15:38000","{\"address\":\"10.0.2.15:38000\",\"associatedRanList\":[],\"keepAliveTimestamp\":" + str(int((time.time()+2) * 1000000000)) + ",\"state\":\"ACTIVE\",\"deletionTimeStamp\":0}")
 
     return True
index b671cd5..b209ea3 100644 (file)
 ##############################################################################
 
 import config
-import redis
-import cleanup_db
 import json
+import redis
+
 
 def getRedisClientDecodeResponse():
     c = config.redis_ip_address
     p = config.redis_ip_port
     return redis.Redis(host=c, port=p, db=0, decode_responses=True)
 
+
 def verify_ran_is_associated_with_e2t_instance(ranName, e2tAddress):
     r = getRedisClientDecodeResponse()
-    e2tInstanceJson = r.get("{e2Manager},E2TInstance:"+e2tAddress)
+    e2tInstanceJson = r.get("{e2Manager},E2TInstance:" + e2tAddress)
     e2tInstanceDic = json.loads(e2tInstanceJson)
     assocRanList = e2tInstanceDic.get("associatedRanList")
     return ranName in assocRanList
 
+
 def verify_e2t_instance_has_no_associated_rans(e2tAddress):
     r = getRedisClientDecodeResponse()
-    e2tInstanceJson = r.get("{e2Manager},E2TInstance:"+e2tAddress)
+    e2tInstanceJson = r.get("{e2Manager},E2TInstance:" + e2tAddress)
     e2tInstanceDic = json.loads(e2tInstanceJson)
     assocRanList = e2tInstanceDic.get("associatedRanList")
     return not assocRanList
 
+
 def verify_e2t_instance_exists_in_addresses(e2tAddress):
     r = getRedisClientDecodeResponse()
     e2tAddressesJson = r.get("{e2Manager},E2TAddresses")
     e2tAddresses = json.loads(e2tAddressesJson)
     return e2tAddress in e2tAddresses
 
+
 def verify_e2t_instance_key_exists(e2tAddress):
     r = getRedisClientDecodeResponse()
-    return r.exists("{e2Manager},E2TInstance:"+e2tAddress)
+    return r.exists("{e2Manager},E2TInstance:" + e2tAddress)
+
 
 def populate_e2t_instances_in_e2m_db_for_get_e2t_instances_tc():
     r = getRedisClientDecodeResponse()
     r.set("{e2Manager},E2TAddresses", "[\"e2t.att.com:38000\"]")
-    r.set("{e2Manager},E2TInstance:e2t.att.com:38000", "{\"address\":\"e2t.att.com:38000\",\"associatedRanList\":[\"test1\",\"test2\",\"test3\"],\"keepAliveTimestamp\":1577619310484022369,\"state\":\"ACTIVE\"}")
+    r.set("{e2Manager},E2TInstance:e2t.att.com:38000",
+          "{\"address\":\"e2t.att.com:38000\",\"associatedRanList\":[\"test1\",\"test2\",\"test3\"],\"keepAliveTimestamp\":1577619310484022369,\"state\":\"ACTIVE\"}")
     return True
 
-# def dissociate_ran_from_e2tInstance(ranName, e2tAddress):
-#     r = getRedisClientDecodeResponse()
-#     e2tInstanceJson = r.get("{e2Manager},E2TInstance:"+e2tAddress)
-#     e2tInstanceDic = json.loads(e2tInstanceJson)
-#     assocRanList = e2tInstanceDic.get("associatedRanList")
-#     print(assocRanList)
-#     assocRanList.remove(ranName)
-#     updatedE2tInstanceJson = json.dumps(e2tInstanceDic)
-#     print(updatedE2tInstanceJson)
-#     r.set("{e2Manager},E2TInstance:"+e2tAddress, updatedE2tInstanceJson)
-#     nodebBytes = r.get("{e2Manager},RAN:"+ranName)
-#     encoded = nodebBytes.decode().replace(e2tAddress,"").encode()
-#     r.set("{e2Manager},RAN:"+ranName, encoded)
 
+def set_enable_ric_false():
+    r = getRedisClientDecodeResponse()
+    r.set("{e2Manager},GENERAL", "{\"enableRic\":false}")
+    return True
index d65516c..7420a29 100644 (file)
@@ -38,6 +38,11 @@ import (
        "strings"
 )
 
+var (
+       emptyTagsToReplaceToSelfClosingTags = []string{"reject", "ignore", "transport-resource-unavailable", "om-intervention",
+               "v60s", "v20s", "v10s", "v5s", "v2s", "v1s"}
+)
+
 type E2SetupRequestNotificationHandler struct {
        logger                *logger.Logger
        config                *configuration.Configuration
@@ -47,8 +52,8 @@ type E2SetupRequestNotificationHandler struct {
        e2tAssociationManager *managers.E2TAssociationManager
 }
 
-func NewE2SetupRequestNotificationHandler(logger *logger.Logger, config *configuration.Configuration, e2tInstancesManager managers.IE2TInstancesManager, rmrSender *rmrsender.RmrSender, rNibDataService services.RNibDataService, e2tAssociationManager *managers.E2TAssociationManager) E2SetupRequestNotificationHandler {
-       return E2SetupRequestNotificationHandler{
+func NewE2SetupRequestNotificationHandler(logger *logger.Logger, config *configuration.Configuration, e2tInstancesManager managers.IE2TInstancesManager, rmrSender *rmrsender.RmrSender, rNibDataService services.RNibDataService, e2tAssociationManager *managers.E2TAssociationManager) *E2SetupRequestNotificationHandler {
+       return &E2SetupRequestNotificationHandler{
                logger:                logger,
                config:                config,
                e2tInstancesManager:   e2tInstancesManager,
@@ -58,10 +63,23 @@ func NewE2SetupRequestNotificationHandler(logger *logger.Logger, config *configu
        }
 }
 
-func (h E2SetupRequestNotificationHandler) Handle(request *models.NotificationRequest) {
+func (h *E2SetupRequestNotificationHandler) Handle(request *models.NotificationRequest) {
        ranName := request.RanName
        h.logger.Infof("#E2SetupRequestNotificationHandler.Handle - RAN name: %s - received E2_SETUP_REQUEST. Payload: %x", ranName, request.Payload)
 
+       generalConfiguration, err := h.rNibDataService.GetGeneralConfiguration()
+
+       if err != nil {
+               h.logger.Errorf("#E2SetupRequestNotificationHandler.Handle - Failed retrieving e2m general configuration. error: %s", err)
+               return
+       }
+
+       if !generalConfiguration.EnableRic {
+               cause := models.Cause{Misc: &models.CauseMisc{OmIntervention: &struct{}{}}}
+               h.handleUnsuccessfulResponse(ranName, request, cause)
+               return
+       }
+
        setupRequest, e2tIpAddress, err := h.parseSetupRequest(request.Payload)
        if err != nil {
                h.logger.Errorf(err.Error())
@@ -104,7 +122,8 @@ func (h E2SetupRequestNotificationHandler) Handle(request *models.NotificationRe
 
                h.logger.Errorf("#E2SetupRequestNotificationHandler.Handle - RAN name: %s - failed to associate E2T to nodeB entity. Error: %s", ranName, err)
                if _, ok := err.(*e2managererrors.RoutingManagerError); ok {
-                       h.handleUnsuccessfulResponse(nodebInfo, request)
+                       cause := models.Cause{Transport: &models.CauseTransport{TransportResourceUnavailable: &struct{}{}}}
+                       h.handleUnsuccessfulResponse(nodebInfo.RanName, request, cause)
                }
                return
        }
@@ -112,7 +131,7 @@ func (h E2SetupRequestNotificationHandler) Handle(request *models.NotificationRe
        h.handleSuccessfulResponse(ranName, request, setupRequest)
 }
 
-func (h E2SetupRequestNotificationHandler) handleNewRan(ranName string, e2tIpAddress string, setupRequest *models.E2SetupRequestMessage) (*entities.NodebInfo, error) {
+func (h *E2SetupRequestNotificationHandler) handleNewRan(ranName string, e2tIpAddress string, setupRequest *models.E2SetupRequestMessage) (*entities.NodebInfo, error) {
 
        nodebInfo, err := h.buildNodebInfo(ranName, e2tIpAddress, setupRequest)
 
@@ -132,7 +151,7 @@ func (h E2SetupRequestNotificationHandler) handleNewRan(ranName string, e2tIpAdd
        return nodebInfo, nil
 }
 
-func (h E2SetupRequestNotificationHandler) setGnbFunctions(nodebInfo *entities.NodebInfo, setupRequest *models.E2SetupRequestMessage) error {
+func (h *E2SetupRequestNotificationHandler) setGnbFunctions(nodebInfo *entities.NodebInfo, setupRequest *models.E2SetupRequestMessage) error {
        ranFunctions := setupRequest.ExtractRanFunctionsList()
 
        if ranFunctions != nil {
@@ -142,7 +161,7 @@ func (h E2SetupRequestNotificationHandler) setGnbFunctions(nodebInfo *entities.N
        return nil
 }
 
-func (h E2SetupRequestNotificationHandler) handleExistingRan(ranName string, nodebInfo *entities.NodebInfo, setupRequest *models.E2SetupRequestMessage) error {
+func (h *E2SetupRequestNotificationHandler) handleExistingRan(ranName string, nodebInfo *entities.NodebInfo, setupRequest *models.E2SetupRequestMessage) error {
        if nodebInfo.GetConnectionStatus() == entities.ConnectionStatus_SHUTTING_DOWN {
                h.logger.Errorf("#E2SetupRequestNotificationHandler.Handle - RAN name: %s, connection status: %s - nodeB entity in incorrect state", ranName, nodebInfo.ConnectionStatus)
                return errors.New("nodeB entity in incorrect state")
@@ -152,26 +171,25 @@ func (h E2SetupRequestNotificationHandler) handleExistingRan(ranName string, nod
        return err
 }
 
-func (h E2SetupRequestNotificationHandler) handleUnsuccessfulResponse(nodebInfo *entities.NodebInfo, req *models.NotificationRequest) {
-       failureResponse := models.NewE2SetupFailureResponseMessage(models.TimeToWaitEnum.V60s)
+func (h *E2SetupRequestNotificationHandler) handleUnsuccessfulResponse(ranName string, req *models.NotificationRequest, cause models.Cause) {
+       failureResponse := models.NewE2SetupFailureResponseMessage(models.TimeToWaitEnum.V60s, cause)
        h.logger.Debugf("#E2SetupRequestNotificationHandler.handleUnsuccessfulResponse - E2_SETUP_RESPONSE has been built successfully %+v", failureResponse)
 
        responsePayload, err := xml.Marshal(&failureResponse.E2APPDU)
        if err != nil {
-               h.logger.Warnf("#E2SetupRequestNotificationHandler.handleUnsuccessfulResponse - RAN name: %s - Error marshalling RIC_E2_SETUP_RESP. Payload: %s", nodebInfo.RanName, responsePayload)
+               h.logger.Warnf("#E2SetupRequestNotificationHandler.handleUnsuccessfulResponse - RAN name: %s - Error marshalling RIC_E2_SETUP_RESP. Payload: %s", ranName, responsePayload)
        }
 
        responsePayload = replaceEmptyTagsWithSelfClosing(responsePayload)
 
        h.logger.Infof("#E2SetupRequestNotificationHandler.handleUnsuccessfulResponse - payload: %s", responsePayload)
-
-       msg := models.NewRmrMessage(rmrCgo.RIC_E2_SETUP_FAILURE, nodebInfo.RanName, responsePayload, req.TransactionId, req.GetMsgSrc())
-       h.logger.Infof("#E2SetupRequestNotificationHandler.handleUnsuccessfulResponse - RAN name: %s - RIC_E2_SETUP_RESP message has been built successfully. Message: %x", nodebInfo.RanName, msg)
+       msg := models.NewRmrMessage(rmrCgo.RIC_E2_SETUP_FAILURE, ranName, responsePayload, req.TransactionId, req.GetMsgSrc())
+       h.logger.Infof("#E2SetupRequestNotificationHandler.handleUnsuccessfulResponse - RAN name: %s - RIC_E2_SETUP_RESP message has been built successfully. Message: %x", ranName, msg)
        _ = h.rmrSender.WhSend(msg)
 
 }
 
-func (h E2SetupRequestNotificationHandler) handleSuccessfulResponse(ranName string, req *models.NotificationRequest, setupRequest *models.E2SetupRequestMessage) {
+func (h *E2SetupRequestNotificationHandler) handleSuccessfulResponse(ranName string, req *models.NotificationRequest, setupRequest *models.E2SetupRequestMessage) {
 
        plmnId := buildPlmnId(h.config.GlobalRicId.Mcc, h.config.GlobalRicId.Mnc)
 
@@ -196,7 +214,7 @@ func (h E2SetupRequestNotificationHandler) handleSuccessfulResponse(ranName stri
        _ = h.rmrSender.Send(msg)
 }
 
-func buildPlmnId(mmc string, mnc string) string{
+func buildPlmnId(mmc string, mnc string) string {
        var b strings.Builder
 
        b.WriteByte(mmc[1])
@@ -214,17 +232,17 @@ func buildPlmnId(mmc string, mnc string) string{
 }
 
 func replaceEmptyTagsWithSelfClosing(responsePayload []byte) []byte {
-       responseString := strings.NewReplacer(
-               "<reject></reject>", "<reject/>",
-               "<ignore></ignore>", "<ignore/>",
-               "<transport-resource-unavailable></transport-resource-unavailable>", "<transport-resource-unavailable/>",
-               "<v60s></v60s>", "<v60s/>",
-               "<v20s></v20s>", "<v20s/>",
-               "<v10s></v10s>", "<v10s/>",
-               "<v5s></v5s>", "<v5s/>",
-               "<v2s></v2s>", "<v2s/>",
-               "<v1s></v1s>", "<v1s/>",
-       ).Replace(string(responsePayload))
+
+       emptyTagVsSelfClosingTagPairs := make([]string, len(emptyTagsToReplaceToSelfClosingTags)*2)
+
+       j := 0
+
+       for i := 0; i < len(emptyTagsToReplaceToSelfClosingTags); i++ {
+               emptyTagVsSelfClosingTagPairs[j] = fmt.Sprintf("<%[1]s></%[1]s>", emptyTagsToReplaceToSelfClosingTags[i])
+               emptyTagVsSelfClosingTagPairs[j+1] = fmt.Sprintf("<%s/>", emptyTagsToReplaceToSelfClosingTags[i])
+               j += 2
+       }
+       responseString := strings.NewReplacer(emptyTagVsSelfClosingTagPairs...).Replace(string(responsePayload))
        return []byte(responseString)
 }
 
@@ -236,7 +254,7 @@ func convertTo20BitString(ricNearRtId string) (string, error) {
        return fmt.Sprintf("%020b", r)[:20], nil
 }
 
-func (h E2SetupRequestNotificationHandler) parseSetupRequest(payload []byte) (*models.E2SetupRequestMessage, string, error) {
+func (h *E2SetupRequestNotificationHandler) parseSetupRequest(payload []byte) (*models.E2SetupRequestMessage, string, error) {
 
        pipInd := bytes.IndexByte(payload, '|')
        if pipInd < 0 {
index 3f3a27b..41ddcca 100644 (file)
@@ -41,14 +41,16 @@ import (
 )
 
 const (
-       prefix                   = "10.0.2.15:9999|"
-       e2tInstanceFullAddress   = "10.0.2.15:9999"
-       nodebRanName             = "gnb:310-410-b5c67788"
-       GnbSetupRequestXmlPath   = "../../tests/resources/setupRequest_gnb.xml"
-       EnGnbSetupRequestXmlPath = "../../tests/resources/setupRequest_en-gNB.xml"
-       NgEnbSetupRequestXmlPath = "../../tests/resources/setupRequest_ng-eNB.xml"
-       EnbSetupRequestXmlPath   = "../../tests/resources/setupRequest_enb.xml"
-       GnbWithoutFunctionsSetupRequestXmlPath   = "../../tests/resources/setupRequest_gnb_without_functions.xml"
+       prefix                                 = "10.0.2.15:9999|"
+       e2tInstanceFullAddress                 = "10.0.2.15:9999"
+       nodebRanName                           = "gnb:310-410-b5c67788"
+       GnbSetupRequestXmlPath                 = "../../tests/resources/setupRequest_gnb.xml"
+       EnGnbSetupRequestXmlPath               = "../../tests/resources/setupRequest_en-gNB.xml"
+       NgEnbSetupRequestXmlPath               = "../../tests/resources/setupRequest_ng-eNB.xml"
+       EnbSetupRequestXmlPath                 = "../../tests/resources/setupRequest_enb.xml"
+       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>"
 )
 
 func readXmlFile(t *testing.T, xmlPath string) []byte {
@@ -123,11 +125,45 @@ func TestParseSetupRequest_UnmarshalFailure(t *testing.T) {
        assert.EqualError(t, err, "#E2SetupRequestNotificationHandler.parseSetupRequest - Error unmarshalling E2 Setup Request payload: 31302e302e322e31353a393939397c010203")
 }
 
+func TestE2SetupRequestNotificationHandler_GetGeneralConfigurationFailure(t *testing.T) {
+       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(prefix), xmlGnb...)}
+       handler.Handle(notificationRequest)
+       rmrMessengerMock.AssertNotCalled(t, "SendMsg")
+       e2tInstancesManagerMock.AssertNotCalled(t, "GetE2TInstance")
+       routingManagerClientMock.AssertNotCalled(t, "AssociateRanToE2TInstance")
+       readerMock.AssertNotCalled(t, "GetNodeb")
+       writerMock.AssertNotCalled(t, "SaveNodeb")
+}
+
+func getMbuf(msgType int, payloadStr string, request *models.NotificationRequest) *rmrCgo.MBuf {
+       payload := []byte(payloadStr)
+       mbuf := rmrCgo.NewMBuf(msgType, len(payload), nodebRanName,&payload,&request.TransactionId, request.GetMsgSrc() )
+       return mbuf
+}
+
+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(prefix), xmlGnb...)}
+       mbuf := getMbuf(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 )
+       e2tInstancesManagerMock.AssertNotCalled(t, "GetE2TInstance")
+       routingManagerClientMock.AssertNotCalled(t, "AssociateRanToE2TInstance")
+       readerMock.AssertNotCalled(t, "GetNodeb")
+       writerMock.AssertNotCalled(t, "SaveNodeb")
+}
+
 func TestE2SetupRequestNotificationHandler_HandleNewGnbSuccess(t *testing.T) {
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       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(prefix), xmlGnb...)}
@@ -136,9 +172,7 @@ func TestE2SetupRequestNotificationHandler_HandleNewGnbSuccess(t *testing.T) {
        routingManagerClientMock.On("AssociateRanToE2TInstance", e2tInstanceFullAddress, mock.Anything).Return(nil)
        writerMock.On("UpdateNodebInfo", mock.Anything).Return(nil)
        e2tInstancesManagerMock.On("AddRansToInstance", mock.Anything, mock.Anything).Return(nil)
-       var errEmpty error
-       rmrMessage := &rmrCgo.MBuf{}
-       rmrMessengerMock.On("SendMsg", mock.Anything, mock.Anything).Return(rmrMessage, errEmpty)
+       rmrMessengerMock.On("SendMsg", mock.Anything, mock.Anything).Return(&rmrCgo.MBuf{}, nil)
        handler.Handle(notificationRequest)
        writerMock.AssertCalled(t, "SaveNodeb", mock.Anything, nodebInfo)
        assertNewNodebSuccessCalls(readerMock, t, e2tInstancesManagerMock, writerMock, routingManagerClientMock, rmrMessengerMock)
@@ -147,8 +181,8 @@ func TestE2SetupRequestNotificationHandler_HandleNewGnbSuccess(t *testing.T) {
 func TestE2SetupRequestNotificationHandler_HandleNewGnbWithoutFunctionsSuccess(t *testing.T) {
        xmlGnb := readXmlFile(t, GnbWithoutFunctionsSetupRequestXmlPath)
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       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(prefix), xmlGnb...)}
@@ -168,8 +202,8 @@ func TestE2SetupRequestNotificationHandler_HandleNewGnbWithoutFunctionsSuccess(t
 func TestE2SetupRequestNotificationHandler_HandleNewEnGnbSuccess(t *testing.T) {
        xmlEnGnb := readXmlFile(t, EnGnbSetupRequestXmlPath)
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
        readerMock.On("GetNodeb", mock.Anything).Return(gnb, common.NewResourceNotFoundError("Not found"))
        writerMock.On("SaveNodeb", mock.Anything, mock.Anything).Return(nil)
@@ -188,8 +222,8 @@ func TestE2SetupRequestNotificationHandler_HandleNewEnGnbSuccess(t *testing.T) {
 func TestE2SetupRequestNotificationHandler_HandleNewNgEnbSuccess(t *testing.T) {
        xmlNgEnb := readXmlFile(t, NgEnbSetupRequestXmlPath)
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
        readerMock.On("GetNodeb", mock.Anything).Return(gnb, common.NewResourceNotFoundError("Not found"))
        writerMock.On("SaveNodeb", mock.Anything, mock.Anything).Return(nil)
@@ -209,8 +243,8 @@ func TestE2SetupRequestNotificationHandler_HandleExistingGnbSuccess(t *testing.T
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
 
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb = &entities.NodebInfo{
                RanName:                      nodebRanName,
                AssociatedE2TInstanceAddress: e2tInstanceFullAddress,
@@ -236,17 +270,17 @@ func TestE2SetupRequestNotificationHandler_HandleExistingGnbWithFunctionsSuccess
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
 
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb = &entities.NodebInfo{
                RanName:                      nodebRanName,
                AssociatedE2TInstanceAddress: e2tInstanceFullAddress,
                ConnectionStatus:             entities.ConnectionStatus_CONNECTED,
                NodeType:                     entities.Node_GNB,
-               Configuration:                &entities.NodebInfo_Gnb{Gnb: &entities.Gnb{RanFunctions: []*entities.RanFunction{
+               Configuration: &entities.NodebInfo_Gnb{Gnb: &entities.Gnb{RanFunctions: []*entities.RanFunction{
                        {
-                               RanFunctionId: &wrappers.UInt32Value{Value:2},
-                               RanFunctionRevision: &wrappers.UInt32Value{Value:2},
+                               RanFunctionId:       &wrappers.UInt32Value{Value: 2},
+                               RanFunctionRevision: &wrappers.UInt32Value{Value: 2},
                        },
                }}},
        }
@@ -265,7 +299,7 @@ func TestE2SetupRequestNotificationHandler_HandleExistingGnbWithFunctionsSuccess
        assertExistingNodebSuccessCalls(readerMock, t, e2tInstancesManagerMock, writerMock, routingManagerClientMock, rmrMessengerMock)
 }
 
-func getExpectedNodebWithFunctionsForExistingRan(nodeb entities.NodebInfo , payload []byte) *entities.NodebInfo {
+func getExpectedNodebWithFunctionsForExistingRan(nodeb entities.NodebInfo, payload []byte) *entities.NodebInfo {
        pipInd := bytes.IndexByte(payload, '|')
        setupRequest := &models.E2SetupRequestMessage{}
        _ = xml.Unmarshal(normalizeXml(payload[pipInd+1:]), &setupRequest.E2APPDU)
@@ -283,12 +317,12 @@ func getExpectedNodebWithFunctionsForNewRan(payload []byte) *entities.NodebInfo
                ConnectionStatus:             entities.ConnectionStatus_CONNECTED,
                RanName:                      nodebRanName,
                NodeType:                     entities.Node_GNB,
-               Configuration:                &entities.NodebInfo_Gnb{
+               Configuration: &entities.NodebInfo_Gnb{
                        Gnb: &entities.Gnb{
                                RanFunctions: setupRequest.ExtractRanFunctionsList(),
                        },
                },
-               GlobalNbId:                   &entities.GlobalNbId{
+               GlobalNbId: &entities.GlobalNbId{
                        PlmnId: setupRequest.GetPlmnId(),
                        NbId:   setupRequest.GetNbId(),
                },
@@ -299,10 +333,9 @@ func getExpectedNodebWithFunctionsForNewRan(payload []byte) *entities.NodebInfo
 
 func TestE2SetupRequestNotificationHandler_HandleParseError(t *testing.T) {
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
-
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       prefBytes := []byte("invalid_prefix")
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, xmlGnb...)}
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte("invalid_prefix"), xmlGnb...)}
        handler.Handle(notificationRequest)
        readerMock.AssertNotCalled(t, "GetNodeb", mock.Anything)
        writerMock.AssertNotCalled(t, "SaveNodeb", mock.Anything, mock.Anything)
@@ -314,8 +347,8 @@ func TestE2SetupRequestNotificationHandler_HandleParseError(t *testing.T) {
 
 func TestE2SetupRequestNotificationHandler_HandleUnmarshalError(t *testing.T) {
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       prefBytes := []byte(prefix)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, "xmlGnb"...)}
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(prefix), "xmlGnb"...)}
        handler.Handle(notificationRequest)
        readerMock.AssertNotCalled(t, "GetNodeb", mock.Anything)
        writerMock.AssertNotCalled(t, "SaveNodeb", mock.Anything, mock.Anything)
@@ -328,8 +361,8 @@ func TestE2SetupRequestNotificationHandler_HandleUnmarshalError(t *testing.T) {
 func TestE2SetupRequestNotificationHandler_HandleGetE2TInstanceError(t *testing.T) {
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       var e2tInstance *entities.E2TInstance
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, common.NewResourceNotFoundError("Not found"))
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, common.NewResourceNotFoundError("Not found"))
        prefBytes := []byte(prefix)
        notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, xmlGnb...)}
        handler.Handle(notificationRequest)
@@ -344,14 +377,12 @@ func TestE2SetupRequestNotificationHandler_HandleGetE2TInstanceError(t *testing.
 
 func TestE2SetupRequestNotificationHandler_HandleGetNodebError(t *testing.T) {
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
-
        handler, readerMock, writerMock, routingManagerClientMock, e2tInstancesManagerMock, rmrMessengerMock := initMocks(t)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       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")))
-       prefBytes := []byte(prefix)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(prefix), xmlGnb...)}
        handler.Handle(notificationRequest)
        e2tInstancesManagerMock.AssertCalled(t, "GetE2TInstance", e2tInstanceFullAddress)
        readerMock.AssertCalled(t, "GetNodeb", mock.Anything)
@@ -366,8 +397,8 @@ func TestE2SetupRequestNotificationHandler_HandleAssociationError(t *testing.T)
        xmlGnb := readXmlFile(t, GnbSetupRequestXmlPath)
 
        handler, readerMock, writerMock, rmrMessengerMock, e2tInstancesManagerMock, routingManagerClientMock := initMocks(t)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
        readerMock.On("GetNodeb", mock.Anything).Return(gnb, common.NewResourceNotFoundError("Not found"))
        writerMock.On("SaveNodeb", mock.Anything, mock.Anything).Return(nil)
@@ -375,11 +406,9 @@ func TestE2SetupRequestNotificationHandler_HandleAssociationError(t *testing.T)
        e2tInstancesManagerMock.On("AddRansToInstance", mock.Anything, mock.Anything).Return(nil)
        routingManagerClientMock.On("AssociateRanToE2TInstance", e2tInstanceFullAddress, mock.Anything).Return(errors.New("association error"))
        var errEmpty error
-       rmrMessage := &rmrCgo.MBuf{}
-       rmrMessengerMock.On("WhSendMsg", mock.Anything, mock.Anything).Return(rmrMessage, errEmpty)
-
-       prefBytes := []byte(prefix)
-       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, xmlGnb...)}
+       notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append([]byte(prefix), xmlGnb...)}
+       mbuf := getMbuf(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)
        e2tInstancesManagerMock.AssertCalled(t, "GetE2TInstance", e2tInstanceFullAddress)
@@ -387,7 +416,7 @@ func TestE2SetupRequestNotificationHandler_HandleAssociationError(t *testing.T)
        routingManagerClientMock.AssertCalled(t, "AssociateRanToE2TInstance", e2tInstanceFullAddress, mock.Anything)
        writerMock.AssertCalled(t, "UpdateNodebInfo", mock.Anything)
        e2tInstancesManagerMock.AssertNotCalled(t, "AddRansToInstance", mock.Anything, mock.Anything)
-       rmrMessengerMock.AssertCalled(t, "WhSendMsg", mock.Anything, mock.Anything)
+       rmrMessengerMock.AssertCalled(t, "WhSendMsg", mbuf, true)
 }
 
 func TestE2SetupRequestNotificationHandler_ConvertTo20BitStringError(t *testing.T) {
@@ -397,7 +426,7 @@ func TestE2SetupRequestNotificationHandler_ConvertTo20BitStringError(t *testing.
                RicId string
                Mcc   string
                Mnc   string
-       }{Mcc: "327", Mnc: "94" ,RicId: "10011001101010101011"}}
+       }{Mcc: "327", Mnc: "94"RicId: "10011001101010101011"}}
        rmrMessengerMock := &mocks.RmrMessengerMock{}
        rmrSender := tests.InitRmrSender(rmrMessengerMock, logger)
        readerMock := &mocks.RnibReaderMock{}
@@ -407,9 +436,8 @@ func TestE2SetupRequestNotificationHandler_ConvertTo20BitStringError(t *testing.
        e2tInstancesManagerMock := &mocks.E2TInstancesManagerMock{}
        e2tAssociationManager := managers.NewE2TAssociationManager(logger, rnibDataService, e2tInstancesManagerMock, routingManagerClientMock)
        handler := NewE2SetupRequestNotificationHandler(logger, config, e2tInstancesManagerMock, rmrSender, rnibDataService, e2tAssociationManager)
-
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        var gnb *entities.NodebInfo
        readerMock.On("GetNodeb", mock.Anything).Return(gnb, common.NewResourceNotFoundError("Not found"))
        writerMock.On("SaveNodeb", mock.Anything, mock.Anything).Return(nil)
@@ -436,8 +464,8 @@ func TestE2SetupRequestNotificationHandler_HandleExistingGnbInvalidStatusError(t
        handler, readerMock, writerMock, routingManagerClientMock, e2tInstancesManagerMock, rmrMessengerMock := initMocks(t)
        var gnb = &entities.NodebInfo{RanName: nodebRanName, ConnectionStatus: entities.ConnectionStatus_SHUTTING_DOWN}
        readerMock.On("GetNodeb", mock.Anything).Return(gnb, nil)
-       var e2tInstance = &entities.E2TInstance{}
-       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(e2tInstance, nil)
+       readerMock.On("GetGeneralConfiguration").Return(&entities.GeneralConfiguration{EnableRic: true}, nil)
+       e2tInstancesManagerMock.On("GetE2TInstance", e2tInstanceFullAddress).Return(&entities.E2TInstance{}, nil)
        prefBytes := []byte(prefix)
        notificationRequest := &models.NotificationRequest{RanName: nodebRanName, Payload: append(prefBytes, xmlGnb...)}
        handler.Handle(notificationRequest)
@@ -450,13 +478,13 @@ func TestE2SetupRequestNotificationHandler_HandleExistingGnbInvalidStatusError(t
        rmrMessengerMock.AssertNotCalled(t, "SendMsg", mock.Anything, mock.Anything)
 }
 
-func initMocks(t *testing.T) (E2SetupRequestNotificationHandler, *mocks.RnibReaderMock, *mocks.RnibWriterMock, *mocks.RmrMessengerMock, *mocks.E2TInstancesManagerMock, *mocks.RoutingManagerClientMock) {
+func initMocks(t *testing.T) (*E2SetupRequestNotificationHandler, *mocks.RnibReaderMock, *mocks.RnibWriterMock, *mocks.RmrMessengerMock, *mocks.E2TInstancesManagerMock, *mocks.RoutingManagerClientMock) {
        logger := tests.InitLog(t)
        config := &configuration.Configuration{RnibRetryIntervalMs: 10, MaxRnibConnectionAttempts: 3, GlobalRicId: struct {
                RicId string
                Mcc   string
                Mnc   string
-       }{Mcc: "327", Mnc: "94" ,RicId: "AACCE"}}
+       }{Mcc: "327", Mnc: "94"RicId: "AACCE"}}
        rmrMessengerMock := &mocks.RmrMessengerMock{}
        rmrSender := tests.InitRmrSender(rmrMessengerMock, logger)
        readerMock := &mocks.RnibReaderMock{}
diff --git a/E2Manager/models/cause.go b/E2Manager/models/cause.go
new file mode 100644 (file)
index 0000000..15cd7d6
--- /dev/null
@@ -0,0 +1,79 @@
+//
+// 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 models
+
+import "encoding/xml"
+
+type Cause struct {
+       XMLName    xml.Name         `xml:"Cause"`
+       Text       string           `xml:",chardata"`
+       RicRequest *CauseRic        `xml:"ricRequest"`
+       RicService *CauseRicService `xml:"ricService"`
+       Transport  *CauseTransport  `xml:"transport"`
+       Protocol   *CauseProtocol   `xml:"protocol"`
+       Misc       *CauseMisc       `xml:"misc"`
+}
+
+type CauseTransport struct {
+       Text                         string    `xml:",chardata"`
+       TransportResourceUnavailable *struct{} `xml:"transport-resource-unavailable"`
+       Unspecified                  *struct{} `xml:"unspecified"`
+}
+
+type CauseMisc struct {
+       Text                      string    `xml:",chardata"`
+       ControlProcessingOverload *struct{} `xml:"control-processing-overload"`
+       HardwareFailure           *struct{} `xml:"hardware-failure"`
+       OmIntervention            *struct{} `xml:"om-intervention"`
+       Unspecified               *struct{} `xml:"unspecified"`
+}
+
+type CauseProtocol struct {
+       Text                                         string    `xml:",chardata"`
+       TransferSyntaxError                          *struct{} `xml:"transfer-syntax-error"`
+       AbstractSyntaxErrorReject                    *struct{} `xml:"abstract-syntax-error-reject"`
+       AbstractSyntaxErrorIgnoreAndNotify           *struct{} `xml:"abstract-syntax-error-ignore-and-notify"`
+       MessageNotCompatibleWithReceiverState        *struct{} `xml:"message-not-compatible-with-receiver-state"`
+       SemanticError                                *struct{} `xml:"semantic-error"`
+       AbstractSyntaxErrorFalselyConstructedMessage *struct{} `xml:"abstract-syntax-error-falsely-constructed-message"`
+       Unspecified                                  *struct{} `xml:"unspecified"`
+}
+
+type CauseRicService struct {
+       Text                string    `xml:",chardata"`
+       FunctionNotRequired *struct{} `xml:"function-not-required"`
+       ExcessiveFunctions  *struct{} `xml:"excessive-functions"`
+       RicResourceLimit    *struct{} `xml:"ric-resource-limit"`
+}
+
+type CauseRic struct {
+       Text                                       string    `xml:",chardata"`
+       RanFunctionIdInvalid                       *struct{} `xml:"ran-function-id-Invalid"`
+       ActionNotSupported                         *struct{} `xml:"action-not-supported"`
+       ExcessiveActions                           *struct{} `xml:"excessive-actions"`
+       DuplicateAction                            *struct{} `xml:"duplicate-action"`
+       DuplicateEvent                             *struct{} `xml:"duplicate-event"`
+       FunctionResourceLimit                      *struct{} `xml:"function-resource-limit"`
+       RequestIdUnknown                           *struct{} `xml:"request-id-unknown"`
+       InconsistentActionSubsequentActionSequence *struct{} `xml:"inconsistent-action-subsequent-action-sequence"`
+       ControlMessageInvalid                      *struct{} `xml:"control-message-invalid"`
+       CallProcessIdInvalid                       *struct{} `xml:"call-process-id-invalid"`
+       Unspecified                                *struct{} `xml:"unspecified"`
+}
index f689fb6..04d63a1 100644 (file)
@@ -93,12 +93,13 @@ func NewE2SetupSuccessResponseMessage(plmnId string, ricId string, request *E2Se
        return E2SetupResponseMessage{E2APPDU: E2APPDU{Outcome: outcome}}
 }
 
-func NewE2SetupFailureResponseMessage(timeToWait TimeToWait) E2SetupResponseMessage {
+func NewE2SetupFailureResponseMessage(timeToWait TimeToWait, cause Cause) E2SetupResponseMessage {
        outcome := UnsuccessfulOutcome{}
        outcome.Value.E2setupFailure.ProtocolIEs.E2setupFailureIEs = make([]E2setupFailureIEs, 2)
        outcome.ProcedureCode = "1"
        outcome.Value.E2setupFailure.ProtocolIEs.E2setupFailureIEs[0].ID = "1"
-       outcome.Value.E2setupFailure.ProtocolIEs.E2setupFailureIEs[0].Value.Value = Cause{}
+
+       outcome.Value.E2setupFailure.ProtocolIEs.E2setupFailureIEs[0].Value.Value = cause
        outcome.Value.E2setupFailure.ProtocolIEs.E2setupFailureIEs[1].ID = "31"
        outcome.Value.E2setupFailure.ProtocolIEs.E2setupFailureIEs[1].Value.Value = timeToWaitMap[timeToWait]
        return E2SetupResponseMessage{E2APPDU: E2APPDU{Outcome: outcome}}
@@ -213,15 +214,6 @@ type E2setupFailureIEs struct {
        } `xml:"value"`
 }
 
-type Cause struct {
-       XMLName   xml.Name `xml:"Cause"`
-       Text      string   `xml:",chardata"`
-       Transport struct {
-               Text                         string `xml:",chardata"`
-               TransportResourceUnavailable string `xml:"transport-resource-unavailable"`
-       } `xml:"transport"`
-}
-
 func extractRanFunctionsIDList(request *E2SetupRequestMessage) []ProtocolIESingleContainer {
        list := &request.E2APPDU.InitiatingMessage.Value.E2setupRequest.ProtocolIEs.E2setupRequestIEs[1].Value.RANfunctionsList
        ids := make([]ProtocolIESingleContainer, len(list.ProtocolIESingleContainer))
index b77e97e..7875b88 100644 (file)
@@ -564,13 +564,12 @@ func TestSaveNilEntityFailure(t *testing.T) {
 
 func TestSaveUnknownTypeEntityFailure(t *testing.T) {
        w, _ := initSdlInstanceMock(namespace)
-       expectedErr := common.NewValidationError("#rNibWriter.saveNodeB - Unknown responding node type, entity: ip:\"localhost\" port:5656")
        nbIdentity := &entities.NbIdentity{InventoryName: "name", GlobalNbId: &entities.GlobalNbId{PlmnId: "02f829", NbId: "4a952a0a"}}
        nb := &entities.NodebInfo{}
        nb.Port = 5656
        nb.Ip = "localhost"
        actualErr := w.SaveNodeb(nbIdentity, nb)
-       assert.Equal(t, expectedErr, actualErr)
+       assert.IsType(t, &common.ValidationError{}, actualErr)
 }
 
 func TestSaveEntityFailure(t *testing.T) {