0.7.1 Version of submgr 74/974/1
authorkalnagy <kalman.nagy@nokia.com>
Thu, 19 Sep 2019 09:29:29 +0000 (11:29 +0200)
committerkalnagy <kalman.nagy@nokia.com>
Thu, 19 Sep 2019 09:36:01 +0000 (11:36 +0200)
Introducing Routing Manager integration from 0.6.0
Transaction handling for Subscription Requests
DeleteRequest Handling

Change-Id: I029ee51c16e00feb90f61277135b06e784657002
Signed-off-by: kalnagy <kalman.nagy@nokia.com>
24 files changed:
.gitreview
Dockerfile
api/routing_manager.yaml [new file with mode: 0644]
config/submgr.yaml
container-tag.yaml
e2ap/wrapper.c
e2ap/wrapper.h
go.mod
manifests/submgr/submgr-dep.yaml
pkg/control/client.go [new file with mode: 0644]
pkg/control/control.go
pkg/control/e2ap.go
pkg/control/registry.go
pkg/control/tracker.go [new file with mode: 0644]
pkg/control/types.go
test/dbaas/manifests/dbaas-dep.yaml
test/dbaas/manifests/dbaas-svc.yaml
test/e2t/container/Dockerfile
test/e2t/manifests/e2t-dep.yaml
test/e2t/manifests/e2t-svc.yaml
test/rco/container/Dockerfile
test/rco/manifests/rco-dep.yaml
test/rco/manifests/rco-svc.yaml
test/rco/rco.go

index c9650ed..ebabf13 100644 (file)
@@ -1,6 +1,6 @@
 [gerrit]
-host=gerrit.oran-osc.org
-#port=29418
+host=gerrit.o-ran-sc.org
+port=29418
 project=ric-plt/submgr
 defaultbranch=master
 defaultremote=origin
index 76e8c5c..d1f9737 100644 (file)
@@ -25,9 +25,9 @@ FROM nexus3.o-ran-sc.org:10004/bldr-ubuntu18-c-go:1-u18.04-nng1.1.1 as submgrbui
 COPY . /opt/submgr
 
 # Install RMr shared library
-RUN wget --content-disposition https://packagecloud.io/o-ran-sc/master/packages/debian/stretch/rmr_1.0.36_amd64.deb/download.deb && dpkg -i rmr_1.0.36_amd64.deb
+RUN wget --content-disposition https://packagecloud.io/o-ran-sc/staging/packages/debian/stretch/rmr_1.6.0_amd64.deb/download.deb && dpkg -i rmr_1.6.0_amd64.deb
 # Install RMr development header files
-RUN wget --content-disposition https://packagecloud.io/o-ran-sc/master/packages/debian/stretch/rmr-dev_1.0.36_amd64.deb/download.deb && dpkg -i rmr-dev_1.0.36_amd64.deb
+RUN wget --content-disposition https://packagecloud.io/o-ran-sc/staging/packages/debian/stretch/rmr-dev_1.6.0_amd64.deb/download.deb && dpkg -i rmr-dev_1.6.0_amd64.deb
 
 # "PULLING LOG and COMPILING LOG"
 RUN git clone "https://gerrit.o-ran-sc.org/r/com/log" /opt/log && cd /opt/log && \
@@ -41,6 +41,22 @@ RUN cd /opt/submgr/e2ap && \
  cp wrapper.h headers/*.h /usr/local/include/ && \
  ldconfig
 
+# "Installing Swagger"
+RUN cd /usr/local/go/bin \
+    && wget --quiet https://github.com/go-swagger/go-swagger/releases/download/v0.19.0/swagger_linux_amd64 \
+    && mv swagger_linux_amd64 swagger \
+    && chmod +x swagger
+
+# "Getting and generating routing managers api client"
+RUN cd /opt/submgr \
+    && git clone "https://gerrit.o-ran-sc.org/r/ric-plt/rtmgr" \
+    && cp rtmgr/api/routing_manager.yaml api/ \
+    && rm -rf rtmgr
+
+RUN cd /opt/submgr \
+    && mkdir -p /root/go \
+    && /usr/local/go/bin/swagger generate client -f api/routing_manager.yaml -t pkg/ -m rtmgr_models -c rtmgr_client
+
 # "COMPILING Subscription manager"
 RUN mkdir -p /opt/bin && cd /opt/submgr && \
  /usr/local/go/bin/go get && \
@@ -55,4 +71,4 @@ COPY --from=submgrbuild /usr/local/include /usr/local/include
 COPY --from=submgrbuild /usr/local/lib /usr/local/lib
 RUN ldconfig
 
-CMD /run_submgr.sh
\ No newline at end of file
+RUN chmod 755 /run_submgr.sh
diff --git a/api/routing_manager.yaml b/api/routing_manager.yaml
new file mode 100644 (file)
index 0000000..8fabfb4
--- /dev/null
@@ -0,0 +1,181 @@
+#
+#==================================================================================
+#   Copyright (c) 2019 AT&T Intellectual Property.
+#   Copyright (c) 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.
+#==================================================================================
+#
+#
+#   Abstract:   Routing Manager's RESTful API definition
+#   Date:      29 March 2019
+#
+swagger: "2.0"
+info:
+  title: Routing Manager
+  description: "This is the Swagger/OpenAPI 2.0 definition of Routing Manager's Northbound API."
+  version: "0.3.0"
+  license:
+    name: "Apache 2.0"
+    url: "http://www.apache.org/licenses/LICENSE-2.0.html"
+host: "rtmgr"
+basePath: "/ric/v1"
+tags:
+- name: "handle"
+  description: "Available handles"
+#  externalDocs:
+#    description: "Find out more"
+#    url: "http://127.0.0.1"
+- name: "health"
+  description: "Health of the system"
+schemes:
+#- "https"
+- "http"
+paths:
+  /health:
+    get:
+      tags:
+      - "health"
+      summary: "Retrive the health of Routing Manager"
+      description: "By performing a GET method on the health resource, the API caller is able to retrieve the health of Routing Manager"
+      operationId: "get_health"
+      consumes:
+      - "application/json"
+#      - "application/yaml"
+      produces:
+      - "application/json"
+#      - "application/yaml"
+      responses:
+        200:
+          description: "The health of the system"
+          schema:
+            "$ref": "#/definitions/health-status"
+  /handles:
+    get:
+      tags:
+      - "handle"
+      summary: "Placeholder for further usage"
+      description: "Placeholder for further usage."
+      operationId: "get_handles"
+      consumes:
+      - "application/json"
+#      - "application/yaml"
+      produces:
+      - "application/json"
+#      - "application/yaml"
+      responses:
+        200:
+          description: "Dummy response"
+  /handles/xapp-handle:
+    post:
+      tags:
+      - "handle"
+      summary: "Provide callback"
+      description: "By performing a POST method on the xapp-handle resource, the API caller is able to perform a callback on Routing Manager."
+      operationId: "provide_xapp_handle"
+      consumes:
+      - "application/json"
+#      - "application/yaml"
+      produces:
+      - "application/json"
+#      - "application/yaml"
+      parameters:
+      - in: "body"
+        name: "xapp-callback-data"
+        description: "xApp related callback data"
+        required: true
+        schema:
+          $ref: "#/definitions/xapp-callback-data"
+      responses:
+        400:
+          description: "Invalid data"
+        201:
+          description: "Callback received"
+  /handles/xapp-subscription-handle:
+    post:
+      tags:
+      - "handle"
+      summary: "API for updating about new xapp subscription"
+      description: "By performing a POST method on the xapp-subscription-handle resource, the API caller is able to update the Routing manager about the creation of new subscription by an Xapp instance."
+      operationId: "provide_xapp_subscription_handle"
+      consumes:
+      - "application/json"
+#      - "application/yaml"
+      produces:
+      - "application/json"
+#      - "application/yaml"
+      parameters:
+      - in: "body"
+        name: "xapp-subscription-data"
+        description: "xApp related subscription data"
+        required: true
+        schema:
+          $ref: "#/definitions/xapp-subscription-data"
+      responses:
+        400:
+          description: "Invalid data"
+        201:
+          description: "Xapp Subscription data received"
+          schema:
+            $ref: "#/definitions/xapp-subscription-data-response"
+definitions:
+  health-status:
+    type: "object"
+    properties:
+      status:
+        type: string
+        enum:
+        - healthy
+        - unhealthy
+  xapp-callback-data:
+    type: "object"
+    properties:
+      id:
+        type: "integer"
+        format: "int64"
+      event:
+        type: "string"
+      version:
+        type: "integer"
+        format: "int64"
+      xApps:
+        type: "string" #This should be a JSON object, array of xapps
+  xapp-subscription-data:
+    type: "object"
+    required:
+      - "address"
+      - "port"
+      - "subscription_id"
+    properties:
+      address:
+        type: "string" #This is the xapp instance hostname or ip address
+      port: #xapp instance port address
+        type: "integer"
+        format: "uint16"
+        minimum: 0
+        maximum: 65535
+      subscription_id: #subscription sequence number
+        type: "integer"
+        format: "int32" 
+  xapp-subscription-data-response:
+    type: "object"
+    required:
+      - "location"
+    properties:
+      location:
+        type: "string"
+
+externalDocs:
+  description: "Routing Manager"
+  url: "http://placeholder"
+
index 0060727..c1dda48 100644 (file)
@@ -21,3 +21,7 @@
   "protPort": "tcp:4560"
   "maxSize": 2072
   "numWorkers": 1
+"rtmgr":
+  "hostAddr": "rtmgr"
+  "port"    : 8888
+  "baseUrl" : "/ric/v1"
index 70ff3e3..87e4654 100644 (file)
@@ -2,4 +2,4 @@
 # By default this file is in the docker build directory,
 # but the location can configured in the JJB template.
 ---
-tag: 0.5.0
+tag: 0.7.1
index 61c13a9..e0f90e4 100644 (file)
-#include <errno.h>\r
-#include "wrapper.h"\r
-\r
-ssize_t encode_RIC_subscription_request(RICsubscriptionRequest_t* pdu, void* buffer, size_t buf_size)\r
-{\r
-\r
-    asn_enc_rval_t encode_result;\r
-    encode_result = aper_encode_to_buffer(&asn_DEF_RICsubscriptionRequest, NULL, pdu, buffer, buf_size);\r
-    if(encode_result.encoded == -1) {\r
-        return -1;\r
-    }\r
-    return encode_result.encoded;\r
-}\r
-\r
-RICsubscriptionRequest_t* decode_RIC_subscription_request(const void *buffer, size_t buf_size)\r
-{\r
-    asn_dec_rval_t decode_result;\r
-    RICsubscriptionRequest_t *pdu = 0;\r
-    decode_result = aper_decode_complete(NULL, &asn_DEF_RICsubscriptionRequest, (void **)&pdu, buffer, buf_size);\r
-    if(decode_result.code == RC_OK) {\r
-        return pdu;\r
-    } else {\r
-        ASN_STRUCT_FREE(asn_DEF_RICsubscriptionRequest, pdu);\r
-        return 0;\r
-    }\r
-}\r
-\r
-long e2ap_get_ric_subscription_request_sequence_number(void *buffer, size_t buf_size)\r
-{\r
-    RICsubscriptionRequest_t *pdu = decode_RIC_subscription_request(buffer, buf_size);\r
-    if(pdu != NULL)\r
-    {\r
-        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )\r
-            {\r
-                if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )\r
-                {\r
-                    return pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber;\r
-                }\r
-            }\r
-    }\r
-    return -1;\r
-}\r
-\r
-ssize_t  e2ap_set_ric_subscription_request_sequence_number(void *buffer, size_t buf_size, long sequence_number)\r
-{\r
-    RICsubscriptionRequest_t *pdu = decode_RIC_subscription_request(buffer, buf_size);\r
-    if(pdu != NULL)\r
-    {\r
-        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )\r
-            {\r
-                if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )\r
-                {\r
-                    pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber = sequence_number;\r
-                    return encode_RIC_subscription_request(pdu, buffer, buf_size);\r
-                }\r
-            }\r
-    }\r
-    return -1;\r
-}\r
-\r
-ssize_t encode_RIC_subscription_response(RICsubscriptionResponse_t* pdu, void* buffer, size_t buf_size)\r
-{\r
-\r
-    asn_enc_rval_t encode_result;\r
-    encode_result = aper_encode_to_buffer(&asn_DEF_RICsubscriptionResponse, NULL, pdu, buffer, buf_size);\r
-    if(encode_result.encoded == -1) {\r
-        return -1;\r
-    }\r
-    return encode_result.encoded;\r
-}\r
-\r
-RICsubscriptionResponse_t* decode_RIC_subscription_response(const void *buffer, size_t buf_size)\r
-{\r
-    asn_dec_rval_t decode_result;\r
-    RICsubscriptionResponse_t *pdu = 0;\r
-    decode_result = aper_decode_complete(NULL, &asn_DEF_RICsubscriptionResponse, (void **)&pdu, buffer, buf_size);\r
-    if(decode_result.code == RC_OK) {\r
-        return pdu;\r
-    } else {\r
-        ASN_STRUCT_FREE(asn_DEF_RICsubscriptionResponse, pdu);\r
-        return 0;\r
-    }\r
-}\r
-\r
-long e2ap_get_ric_subscription_response_sequence_number(void *buffer, size_t buf_size)\r
-{\r
-    RICsubscriptionResponse_t *pdu = decode_RIC_subscription_response(buffer, buf_size);\r
-    if(pdu != NULL)\r
-    {\r
-        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )\r
-        {\r
-            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )\r
-            {\r
-                return pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber;\r
-            }\r
-        }\r
-    }\r
-    return -1;\r
-}\r
-\r
-ssize_t  e2ap_set_ric_subscription_response_sequence_number(void *buffer, size_t buf_size, long sequence_number)\r
-{\r
-    RICsubscriptionResponse_t *pdu = decode_RIC_subscription_response(buffer, buf_size);\r
-    if(pdu != NULL)\r
-    {\r
-        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )\r
-        {\r
-            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )\r
-            {\r
-                pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber = sequence_number;\r
-                return encode_RIC_subscription_response(pdu, buffer, buf_size);\r
-            }\r
-        }\r
-    }\r
-    return -1;\r
-}\r
+#include <errno.h>
+#include "wrapper.h"
+
+ssize_t encode_RIC_subscription_request(RICsubscriptionRequest_t* pdu, void* buffer, size_t buf_size)
+{
+    asn_enc_rval_t encode_result;
+    encode_result = aper_encode_to_buffer(&asn_DEF_RICsubscriptionRequest, NULL, pdu, buffer, buf_size);
+    if(encode_result.encoded == -1) {
+        return -1;
+    }
+    return encode_result.encoded;
+}
+
+RICsubscriptionRequest_t* decode_RIC_subscription_request(const void *buffer, size_t buf_size)
+{
+    asn_dec_rval_t decode_result;
+    RICsubscriptionRequest_t *pdu = 0;
+    decode_result = aper_decode_complete(NULL, &asn_DEF_RICsubscriptionRequest, (void **)&pdu, buffer, buf_size);
+    if(decode_result.code == RC_OK) {
+        return pdu;
+    } else {
+        ASN_STRUCT_FREE(asn_DEF_RICsubscriptionRequest, pdu);
+        return 0;
+    }
+}
+
+long e2ap_get_ric_subscription_request_sequence_number(void *buffer, size_t buf_size)
+{
+    RICsubscriptionRequest_t *pdu = decode_RIC_subscription_request(buffer, buf_size);
+    if ( pdu != NULL )
+    {
+        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )
+        {
+            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )
+            {
+                return pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber;
+            }
+        }
+    }
+    return -1;
+}
+
+ssize_t  e2ap_set_ric_subscription_request_sequence_number(void *buffer, size_t buf_size, long sequence_number)
+{
+    RICsubscriptionRequest_t *pdu = decode_RIC_subscription_request(buffer, buf_size);
+    if ( pdu != NULL )
+    {
+        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )
+        {
+            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )
+            {
+                pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber = sequence_number;
+                return encode_RIC_subscription_request(pdu, buffer, buf_size);
+            }
+        }
+    }
+    return -1;
+}
+
+/* RICsubscriptionResponse */
+ssize_t encode_RIC_subscription_response(RICsubscriptionResponse_t* pdu, void* buffer, size_t buf_size)
+{
+    asn_enc_rval_t encode_result;
+    encode_result = aper_encode_to_buffer(&asn_DEF_RICsubscriptionResponse, NULL, pdu, buffer, buf_size);
+    if(encode_result.encoded == -1) {
+        return -1;
+    }
+    return encode_result.encoded;
+}
+
+RICsubscriptionResponse_t* decode_RIC_subscription_response(const void *buffer, size_t buf_size)
+{
+    asn_dec_rval_t decode_result;
+    RICsubscriptionResponse_t *pdu = 0;
+    decode_result = aper_decode_complete(NULL, &asn_DEF_RICsubscriptionResponse, (void **)&pdu, buffer, buf_size);
+    if(decode_result.code == RC_OK) {
+        fprintf(stdout, "decoded bytes: %ld\n", decode_result.consumed);
+        return pdu;
+    } else {
+        ASN_STRUCT_FREE(asn_DEF_RICsubscriptionResponse, pdu);
+        return 0;
+    }
+}
+
+long e2ap_get_ric_subscription_response_sequence_number(void *buffer, size_t buf_size)
+{
+    RICsubscriptionResponse_t *pdu = decode_RIC_subscription_response(buffer, buf_size);
+    if ( pdu != NULL )
+    {
+        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )
+        {
+            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )
+            {
+                return pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber;
+            }
+        }
+    }
+    return -1;
+}
+
+ssize_t  e2ap_set_ric_subscription_response_sequence_number(void *buffer, size_t buf_size, long sequence_number)
+{
+    RICsubscriptionResponse_t *pdu = decode_RIC_subscription_response(buffer, buf_size);
+    if ( pdu != NULL )
+    {
+        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )
+        {
+            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )
+            {
+                pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber = sequence_number;
+                return encode_RIC_subscription_response(pdu, buffer, buf_size);
+            }
+        }
+    }
+    return -1;
+}
+
+/* RICsubscriptionDeleteRequest */
+ssize_t encode_RIC_subscription_delete_request(RICsubscriptionDeleteRequest_t* pdu, void* buffer, size_t buf_size)
+{
+    asn_enc_rval_t encode_result;
+    encode_result = aper_encode_to_buffer(&asn_DEF_RICsubscriptionDeleteRequest, NULL, pdu, buffer, buf_size);
+    if(encode_result.encoded == -1) {
+        return -1;
+    }
+    return encode_result.encoded;
+}
+
+RICsubscriptionDeleteRequest_t* decode_RIC_subscription_delete_request(const void *buffer, size_t buf_size)
+{
+    asn_dec_rval_t decode_result;
+    RICsubscriptionDeleteRequest_t *pdu = 0;
+    decode_result = aper_decode_complete(NULL, &asn_DEF_RICsubscriptionDeleteRequest, (void **)&pdu, buffer, buf_size);
+    if(decode_result.code == RC_OK) {
+        return pdu;
+    } else {
+        ASN_STRUCT_FREE(asn_DEF_RICsubscriptionDeleteRequest, pdu);
+        return 0;
+    }
+}
+
+long e2ap_get_ric_subscription_delete_request_sequence_number(void *buffer, size_t buf_size)
+{
+    RICsubscriptionDeleteRequest_t *pdu = decode_RIC_subscription_delete_request(buffer, buf_size);
+    if ( pdu != NULL )
+    {
+        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )
+        {
+            /* TODO */
+            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )
+            {
+                return pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber;
+            }
+        }
+    }
+    return -1;
+}
+
+ssize_t  e2ap_set_ric_subscription_delete_request_sequence_number(void *buffer, size_t buf_size, long sequence_number)
+{
+    RICsubscriptionDeleteRequest_t *pdu = decode_RIC_subscription_delete_request(buffer, buf_size);
+    if ( pdu != NULL )
+    {
+        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )
+        {
+            /* TODO */
+            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )
+            {
+                pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber = sequence_number;
+                return encode_RIC_subscription_delete_request(pdu, buffer, buf_size);
+            }
+        }
+    }
+    return -1;
+}
+
+/* RICsubscriptionDeleteResponse */
+ssize_t encode_RIC_subscription_delete_response(RICsubscriptionDeleteResponse_t* pdu, void* buffer, size_t buf_size)
+{
+    asn_enc_rval_t encode_result;
+    encode_result = aper_encode_to_buffer(&asn_DEF_RICsubscriptionDeleteResponse, NULL, pdu, buffer, buf_size);
+    if(encode_result.encoded == -1) {
+        return -1;
+    }
+    return encode_result.encoded;
+}
+
+RICsubscriptionDeleteResponse_t* decode_RIC_subscription_delete_response(const void *buffer, size_t buf_size)
+{
+    asn_dec_rval_t decode_result;
+    RICsubscriptionDeleteResponse_t *pdu = 0;
+    decode_result = aper_decode_complete(NULL, &asn_DEF_RICsubscriptionDeleteResponse, (void **)&pdu, buffer, buf_size);
+    if(decode_result.code == RC_OK) {
+        fprintf(stdout, "decoded bytes: %ld\n", decode_result.consumed);
+        return pdu;
+    } else {
+        ASN_STRUCT_FREE(asn_DEF_RICsubscriptionDeleteResponse, pdu);
+        return 0;
+    }
+}
+
+long e2ap_get_ric_subscription_delete_response_sequence_number(void *buffer, size_t buf_size)
+{
+    RICsubscriptionDeleteResponse_t *pdu = decode_RIC_subscription_delete_response(buffer, buf_size);
+    if ( pdu != NULL )
+    {
+        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )
+        {
+            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )
+            {
+                /* TODO */
+                return pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber;
+            }
+        }
+    }
+    return -1;
+}
+
+ssize_t  e2ap_set_ric_subscription_delete_response_sequence_number(void *buffer, size_t buf_size, long sequence_number)
+{
+    RICsubscriptionDeleteResponse_t *pdu = decode_RIC_subscription_delete_response(buffer, buf_size);
+    if ( pdu != NULL )
+    {
+        for (int i = 0; i < pdu->protocolIEs.list.count; ++i )
+        {
+            if ( pdu->protocolIEs.list.array[i]->id == ProtocolIE_ID_id_RICrequestID )
+            {
+                /* todo */
+                pdu->protocolIEs.list.array[i]->value.choice.RICrequestID.ricRequestSequenceNumber = sequence_number;
+                return encode_RIC_subscription_delete_response(pdu, buffer, buf_size);
+            }
+        }
+    }
+    return -1;
+}
index 0e919b8..6aa2bb5 100644 (file)
@@ -1,23 +1,43 @@
-#ifndef        _WRAPPER_H_\r
-#define        _WRAPPER_H_\r
-\r
-#include "RICsubscriptionRequest.h"\r
-#include "RICsubscriptionResponse.h"\r
-#include "ProtocolIE-Container.h"\r
-#include "ProtocolIE-Field.h"\r
-\r
-\r
-ssize_t encode_RIC_subscription_request(RICsubscriptionRequest_t* pdu, void* buffer, size_t buf_size);\r
-RICsubscriptionRequest_t* decode_RIC_subscription_request(const void *buffer, size_t buf_size);\r
-\r
-long e2ap_get_ric_subscription_request_sequence_number(void *buffer, size_t buf_size);\r
-ssize_t  e2ap_set_ric_subscription_request_sequence_number(void *buffer, size_t buf_size, long sequence_number);\r
-\r
-ssize_t encode_RIC_subscription_response(RICsubscriptionResponse_t* pdu, void* buffer, size_t buf_size);\r
-RICsubscriptionResponse_t* decode_RIC_subscription_response(const void *buffer, size_t buf_size);\r
-\r
-long e2ap_get_ric_subscription_response_sequence_number(void *buffer, size_t buf_size);\r
-ssize_t  e2ap_set_ric_subscription_response_sequence_number(void *buffer, size_t buf_size, long sequence_number);\r
-\r
-\r
+#ifndef        _WRAPPER_H_
+#define        _WRAPPER_H_
+
+#include "RICsubscriptionRequest.h"
+#include "RICsubscriptionResponse.h"
+#include "RICsubscriptionDeleteRequest.h"
+#include "RICsubscriptionDeleteResponse.h"
+#include "ProtocolIE-Container.h"
+#include "ProtocolIE-Field.h"
+
+
+/* RICsubscriptionRequest */
+ssize_t encode_RIC_subscription_request(RICsubscriptionRequest_t* pdu, void* buffer, size_t buf_size);
+RICsubscriptionRequest_t* decode_RIC_subscription_request(const void *buffer, size_t buf_size);
+
+long e2ap_get_ric_subscription_request_sequence_number(void *buffer, size_t buf_size);
+ssize_t  e2ap_set_ric_subscription_request_sequence_number(void *buffer, size_t buf_size, long sequence_number);
+RICsubscription_t* e2ap_get_ric_subscription_request_ric_subscription(void *buffer, size_t buffer_size);
+
+/* RICsubscriptionResponse */
+ssize_t encode_RIC_subscription_response(RICsubscriptionResponse_t* pdu, void* buffer, size_t buf_size);
+RICsubscriptionResponse_t* decode_RIC_subscription_response(const void *buffer, size_t buf_size);
+
+long e2ap_get_ric_subscription_response_sequence_number(void *buffer, size_t buf_size);
+ssize_t  e2ap_set_ric_subscription_response_sequence_number(void *buffer, size_t buf_size, long sequence_number);
+
+/* RICsubscriptionDeleteRequest */
+ssize_t encode_RIC_subscription_delete_request(RICsubscriptionDeleteRequest_t* pdu, void* buffer, size_t buf_size);
+RICsubscriptionDeleteRequest_t* decode_RIC_subscription_delete_request(const void *buffer, size_t buf_size);
+
+long e2ap_get_ric_subscription_delete_request_sequence_number(void *buffer, size_t buf_size);
+ssize_t  e2ap_set_ric_subscription_delete_request_sequence_number(void *buffer, size_t buf_size, long sequence_number);
+
+/* RICsubscriptionDeleteResponse */
+ssize_t encode_RIC_subscription_delete_response(RICsubscriptionDeleteResponse_t* pdu, void* buffer, size_t buf_size);
+RICsubscriptionDeleteResponse_t* decode_RIC_subscription_delete_response(const void *buffer, size_t buf_size);
+
+long e2ap_get_ric_subscription_delete_response_sequence_number(void *buffer, size_t buf_size);
+ssize_t  e2ap_set_ric_subscription_delete_response_sequence_number(void *buffer, size_t buf_size, long sequence_number);
+
+
+
 #endif /* _WRAPPER_H_ */
\ No newline at end of file
diff --git a/go.mod b/go.mod
index 6f22d1f..4de6318 100644 (file)
--- a/go.mod
+++ b/go.mod
@@ -3,12 +3,15 @@ go 1.12
 module gerrit.o-ran-sc.org/r/ric-plt/submgr
 
 require (
-       gerrit.o-ran-sc.org/r/ric-plt/xapp-frame v0.0.5
+       gerrit.o-ran-sc.org/r/ric-plt/ue-nib v0.0.1
+       gerrit.o-ran-sc.org/r/ric-plt/xapp-frame v0.0.8
        github.com/spf13/viper v1.3.2
 )
 
-replace gerrit.o-ran-sc.org/r/ric-plt/sdlgo => gerrit.o-ran-sc.org/r/ric-plt/sdlgo.git v0.1.1
+replace gerrit.o-ran-sc.org/r/ric-plt/sdlgo => gerrit.o-ran-sc.org/r/ric-plt/sdlgo.git v0.2.0
 
-replace gerrit.o-ran-sc.org/r/ric-plt/xapp-frame => gerrit.o-ran-sc.org/r/ric-plt/xapp-frame.git v0.0.5
+replace gerrit.o-ran-sc.org/r/ric-plt/xapp-frame => gerrit.o-ran-sc.org/r/ric-plt/xapp-frame.git v0.0.8
 
 replace gerrit.o-ran-sc.org/r/com/golog => gerrit.o-ran-sc.org/r/com/golog.git v0.0.1
+
+replace gerrit.o-ran-sc.org/r/ric-plt/ue-nib => gerrit.o-ran-sc.org/r/ric-plt/ue-nib.git v0.0.1
index 92b6d15..f710261 100644 (file)
@@ -24,7 +24,7 @@ apiVersion: apps/v1
 kind: Deployment
 metadata:
   name: submgr
-  namespace: example
+  namespace: ricplt
 spec:
   replicas: 1
   selector:
@@ -37,11 +37,11 @@ spec:
     spec:
       containers:
       - name: submgr
-        image: cmaster:5000/submgr:builder
+        image: jenkins:5000/submgr:test
         command: ["/run_submgr.sh"]
         env:
         - name: DBAAS_SERVICE_HOST
-          value: dbaas
+          value: service-ricplt-dbaas-tcp
         - name: SUBMGR_SEED_SN
           value: "1"
         ports:
diff --git a/pkg/control/client.go b/pkg/control/client.go
new file mode 100644 (file)
index 0000000..598c7ef
--- /dev/null
@@ -0,0 +1,76 @@
+/*
+==================================================================================
+  Copyright (c) 2019 AT&T Intellectual Property.
+  Copyright (c) 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.
+==================================================================================
+*/
+
+package control
+
+import (
+       rtmgrclient "gerrit.o-ran-sc.org/r/ric-plt/submgr/pkg/rtmgr_client"
+       rtmgrhandle "gerrit.o-ran-sc.org/r/ric-plt/submgr/pkg/rtmgr_client/handle"
+       "gerrit.o-ran-sc.org/r/ric-plt/submgr/pkg/rtmgr_models"
+       "strings"
+       "strconv"
+       "errors"
+       "gerrit.o-ran-sc.org/r/ric-plt/xapp-frame/pkg/xapp"
+)
+
+type RtmgrClient struct {
+       rtClient         *rtmgrclient.RoutingManager
+       xappHandleParams *rtmgrhandle.ProvideXappSubscriptionHandleParams
+}
+
+func (rc *RtmgrClient) SubscriptionRequestUpdate() error {
+       xapp.Logger.Debug("SubscriptionRequestUpdate() invoked")
+       subRouteAction := <-SubscriptionReqChan
+       // Routing manager handles subscription id as int32 to accomodate -1 and uint16 values
+       subID := int32(subRouteAction.SubID)
+
+       xapp.Logger.Debug("Subscription action details received: ", subRouteAction)
+
+       xappSubReq := rtmgr_models.XappSubscriptionData{&subRouteAction.Address, &subRouteAction.Port, &subID}
+
+       switch subRouteAction.Command {
+       case CREATE:
+               _, postErr := rc.rtClient.Handle.ProvideXappSubscriptionHandle(rc.xappHandleParams.WithXappSubscriptionData(&xappSubReq))
+               if postErr != nil && !(strings.Contains(postErr.Error(), "status 200"))  {
+                       xapp.Logger.Error("Updating routing manager about subscription id = %d failed with error: %v", subID, postErr)
+                       return postErr
+               } else {
+                       xapp.Logger.Info("Succesfully updated routing manager about the subscription: %d", subID)
+                       return nil
+               }
+       default:
+               return nil
+       }
+}
+
+func (rc *RtmgrClient) SplitSource(src string) (*string, *uint16, error) {
+       tcpSrc := strings.Split(src, ":")
+       if len(tcpSrc) != 2 {
+               err := errors.New("Unable to get the source details of the xapp. Check the source string received from the rmr.")
+               return nil, nil, err
+       }
+       srcAddr := tcpSrc[0]
+       xapp.Logger.Info("---Debugging Inside splitsource tcpsrc[0] = %s and tcpsrc[1]= %s ", tcpSrc[0], tcpSrc[1])
+       srcPort, err := strconv.ParseUint(tcpSrc[1], 10, 16)
+       if err != nil {
+               return nil, nil, err
+       }
+       srcPortInt := uint16(srcPort)
+       return &srcAddr, &srcPortInt, nil
+}
index 9a5022f..27e3fbe 100644 (file)
@@ -21,6 +21,7 @@ package control
 
 /*
 #include <rmr/RIC_message_types.h>
+#include <rmr/rmr.h>
 
 #cgo CFLAGS: -I../
 #cgo LDFLAGS: -lrmr_nng -lnng
@@ -31,17 +32,46 @@ import (
        "errors"
        "gerrit.o-ran-sc.org/r/ric-plt/xapp-frame/pkg/xapp"
        "github.com/spf13/viper"
+       "github.com/go-openapi/strfmt"
+       httptransport "github.com/go-openapi/runtime/client"
+       rtmgrclient "gerrit.o-ran-sc.org/r/ric-plt/submgr/pkg/rtmgr_client"
+       rtmgrhandle "gerrit.o-ran-sc.org/r/ric-plt/submgr/pkg/rtmgr_client/handle"
        "math/rand"
        "strconv"
        "time"
 )
 
 type Control struct {
-       e2ap     *E2ap
-       registry *Registry
+       e2ap        *E2ap
+       registry    *Registry
+       rtmgrClient *RtmgrClient
+       tracker     *Tracker
+}
+
+type RMRMeid struct {
+       PlmnID string
+       EnbID  string
+}
+
+type RMRParams struct {
+       Mtype           int
+       Payload         []byte
+       PayloadLen      int
+       Meid            *RMRMeid
+       Xid             string
+       SubId           int
+       Src             string
+       Mbuf            *C.rmr_mbuf_t
 }
 
 var SEEDSN uint16
+var SubscriptionReqChan = make(chan subRouteInfo, 10)
+
+const (
+       CREATE Action = 0
+       MERGE Action = 1
+       DELETE Action = 3
+)
 
 func init() {
        viper.AutomaticEnv()
@@ -61,63 +91,135 @@ func init() {
 func NewControl() Control {
        registry := new(Registry)
        registry.Initialize(SEEDSN)
-       return Control{new(E2ap), registry}
+
+       transport := httptransport.New(viper.GetString("rtmgr.HostAddr") + ":" + viper.GetString("rtmgr.port"), viper.GetString("rtmgr.baseUrl"), []string{"http"})
+       client := rtmgrclient.New(transport, strfmt.Default)
+       handle := rtmgrhandle.NewProvideXappSubscriptionHandleParamsWithTimeout(10 * time.Second)
+       rtmgrClient := RtmgrClient{client, handle}
+
+       return Control{new(E2ap), registry, &rtmgrClient, new(Tracker)}
 }
 
 func (c *Control) Run() {
        xapp.Run(c)
 }
 
-func (c *Control) Consume(mtype, sub_id int, len int, payload []byte) (err error) {
-       switch mtype {
+func (c *Control) Consume(rp *xapp.RMRParams) (err error) {
+       switch rp.Mtype {
        case C.RIC_SUB_REQ:
-               err = c.handleSubscriptionRequest(&RmrDatagram{mtype, uint16(sub_id), payload})
+               err = c.handleSubscriptionRequest(rp)
        case C.RIC_SUB_RESP:
-               err = c.handleSubscriptionResponse(&RmrDatagram{mtype, uint16(sub_id), payload})
+               err = c.handleSubscriptionResponse(rp)
+       case C.RIC_SUB_DEL_REQ:
+               err = c.handleSubscriptionDeleteRequest(rp)
        default:
-               err = errors.New("Message Type " + strconv.Itoa(mtype) + " is discarded")
+               err = errors.New("Message Type " + strconv.Itoa(rp.Mtype) + " is discarded")
        }
        return
 }
 
-func (c *Control) rmrSend(datagram *RmrDatagram) (err error) {
-       if !xapp.Rmr.Send(datagram.MessageType, int(datagram.SubscriptionId), len(datagram.Payload), datagram.Payload) {
+func (c *Control) rmrSend(params *xapp.RMRParams) (err error) {
+       if !xapp.Rmr.Send(params, false) {
                err = errors.New("rmr.Send() failed")
        }
        return
 }
 
-func (c *Control) handleSubscriptionRequest(datagram *RmrDatagram) (err error) {
-       payload_seq_num, err := c.e2ap.GetSubscriptionRequestSequenceNumber(datagram.Payload)
+func (c *Control) handleSubscriptionRequest(params *xapp.RMRParams) (err error) {
+       payload_seq_num, err := c.e2ap.GetSubscriptionRequestSequenceNumber(params.Payload)
        if err != nil {
                err = errors.New("Unable to get Subscription Sequence Number from Payload due to: " + err.Error())
                return
        }
-       xapp.Logger.Info("Subscription Request Received. RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", datagram.SubscriptionId, payload_seq_num)
+       xapp.Logger.Info("Subscription Request Received. RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", params.SubId, payload_seq_num)
+
+       /* Reserve a sequence number and set it in the payload */
        new_sub_id := c.registry.ReserveSequenceNumber()
-       payload, err := c.e2ap.SetSubscriptionRequestSequenceNumber(datagram.Payload, new_sub_id)
+
+       _, err = c.e2ap.SetSubscriptionRequestSequenceNumber(params.Payload, new_sub_id)
        if err != nil {
                err = errors.New("Unable to set Subscription Sequence Number in Payload due to: " + err.Error())
                return
        }
+
+       src_addr, src_port, err := c.rtmgrClient.SplitSource(params.Src)
+       if err != nil {
+               xapp.Logger.Error("Failed to update routing-manager about the subscription request with reason: %s", err)
+               return
+       }
+
+       /* Create transatcion records for every subscription request */
+       xact_key := Transaction_key{new_sub_id, CREATE}
+       xact_value := Transaction{*src_addr, *src_port, params.Payload}
+       err = c.tracker.Track_transaction(xact_key, &xact_value)
+       if err != nil {
+               xapp.Logger.Error("Failed to create a transaction record due to %v", err)
+               return
+       }
+
+       /* Update routing manager about the new subscription*/
+       sub_route_action := subRouteInfo{CREATE, *src_addr, *src_port, new_sub_id }
+       go c.rtmgrClient.SubscriptionRequestUpdate()
+       SubscriptionReqChan <- sub_route_action
+
+       // Setting new subscription ID in the RMR header
+       params.SubId = int(new_sub_id)
+
        xapp.Logger.Info("Generated ID: %v. Forwarding to E2 Termination...", int(new_sub_id))
-       c.rmrSend(&RmrDatagram{C.RIC_SUB_REQ, new_sub_id, payload})
+       c.rmrSend(params)
        return
 }
 
-func (c *Control) handleSubscriptionResponse(datagram *RmrDatagram) (err error) {
-       payload_seq_num, err := c.e2ap.GetSubscriptionResponseSequenceNumber(datagram.Payload)
+func (c *Control) handleSubscriptionResponse(params *xapp.RMRParams) (err error) {
+       payload_seq_num, err := c.e2ap.GetSubscriptionResponseSequenceNumber(params.Payload)
        if err != nil {
                err = errors.New("Unable to get Subscription Sequence Number from Payload due to: " + err.Error())
                return
        }
-       xapp.Logger.Info("Subscription Response Received. RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", datagram.SubscriptionId, payload_seq_num)
+       xapp.Logger.Info("Subscription Response Received. RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", params.SubId, payload_seq_num)
        if !c.registry.IsValidSequenceNumber(payload_seq_num) {
                err = errors.New("Unknown Subscription ID: " + strconv.Itoa(int(payload_seq_num)) + " in Subscritpion Response. Message discarded.")
                return
        }
        c.registry.setSubscriptionToConfirmed(payload_seq_num)
        xapp.Logger.Info("Subscription Response Registered. Forwarding to Requestor...")
-       c.rmrSend(&RmrDatagram{C.RIC_SUB_RESP, payload_seq_num, datagram.Payload})
+       c.rmrSend(params)
+       return
+}
+
+func (act Action) String() string {
+       actions := [...]string{
+               "CREATE",
+               "MERGE",
+               "DELETE",
+       }
+
+       if act < CREATE || act > DELETE {
+               return "Unknown"
+       }
+       return actions[act]
+}
+
+func (act Action) valid() bool {
+       switch act {
+       case CREATE, MERGE, DELETE:
+               return true
+       default:
+               return false
+       }
+}
+
+func (c *Control) handleSubscriptionDeleteRequest(params *xapp.RMRParams) (err error) {
+       payload_seq_num, err := c.e2ap.GetSubscriptionDeleteRequestSequenceNumber(params.Payload)
+       if err != nil {
+               err = errors.New("Unable to get Subscription Sequence Number from Payload due to: " + err.Error())
+               return
+       }
+       xapp.Logger.Info("Subscription Delete Request Received. RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", params.SubId, payload_seq_num)
+       if c.registry.IsValidSequenceNumber(payload_seq_num) {
+               c.registry.deleteSubscription(payload_seq_num)
+       }
+       xapp.Logger.Info("Subscription ID: %v. Forwarding to E2 Termination...", int(payload_seq_num))
+       c.rmrSend(params)
        return
 }
index c6b5e28..9ecef4e 100644 (file)
@@ -73,3 +73,47 @@ func (c *E2ap) SetSubscriptionResponseSequenceNumber(payload []byte, newSubscrip
        new_payload = C.GoBytes(cptr, C.int(size))
        return
 }
+
+/* RICsubscriptionDeleteRequest */
+
+func (c *E2ap) GetSubscriptionDeleteRequestSequenceNumber(payload []byte) (sub_id uint16, err error) {
+       cptr := unsafe.Pointer(&payload[0])
+       cret := C.e2ap_get_ric_subscription_delete_request_sequence_number(cptr, C.size_t(len(payload)))
+       if cret < 0 {
+               return 0, errors.New("e2ap wrapper is unable to get Subscirption Delete Request Sequence Number due to wrong or invalid payload")
+       }
+       sub_id = uint16(cret)
+       return
+}
+
+func (c *E2ap) SetSubscriptionDeleteRequestSequenceNumber(payload []byte, newSubscriptionid uint16) (new_payload []byte, err error) {
+       cptr := unsafe.Pointer(&payload[0])
+       size := C.e2ap_set_ric_subscription_delete_request_sequence_number(cptr, C.size_t(len(payload)), C.long(newSubscriptionid))
+       if size < 0 {
+               return make([]byte, 0), errors.New("e2ap wrapper is unable to set Subscirption Request Sequence Number due to wrong or invalid payload")
+       }
+       new_payload = C.GoBytes(cptr, C.int(size))
+       return
+}
+
+/* RICsubscriptionDeleteResponse */
+
+func (c *E2ap) GetSubscriptionDeleteResponseSequenceNumber(payload []byte) (sub_id uint16, err error) {
+       cptr := unsafe.Pointer(&payload[0])
+       cret := C.e2ap_get_ric_subscription_delete_response_sequence_number(cptr, C.size_t(len(payload)))
+       if cret < 0 {
+               return 0, errors.New("e2ap wrapper is unable to get Subscirption Delete Response Sequence Number due to wrong or invalid payload")
+       }
+       sub_id = uint16(cret)
+       return
+}
+
+func (c *E2ap) SetSubscriptionDeleteResponseSequenceNumber(payload []byte, newSubscriptionid uint16) (new_payload []byte, err error) {
+       cptr := unsafe.Pointer(&payload[0])
+       size := C.e2ap_set_ric_subscription_delete_response_sequence_number(cptr, C.size_t(len(payload)), C.long(newSubscriptionid))
+       if size < 0 {
+               return make([]byte, 0), errors.New("e2ap wrapper is unable to set Subscirption Reponse Sequence Number due to wrong or invalid payload")
+       }
+       new_payload = C.GoBytes(cptr, C.int(size))
+       return
+}
index d182b3e..c349921 100644 (file)
@@ -34,6 +34,9 @@ func (r *Registry) Initialize(seedsn uint16) {
 
 // Reserves and returns the next free sequence number
 func (r *Registry) ReserveSequenceNumber() uint16 {
+       if r.IsValidSequenceNumber(r.counter){
+
+       }
        sequenceNumber := r.counter
        r.register[sequenceNumber] = false
        r.shift()
@@ -61,3 +64,13 @@ func (r *Registry) shift() {
                r.counter++
        }
 }
+
+//This function sets the given id as unused in the register
+func (r *Registry) deleteSubscription(sn uint16) {
+       r.register[sn] = false
+}
+
+//This function releases the given id as unused in the register
+//func (r *Registry) releaseSequenceNumber(sn uint16) {
+//     delete(r.register, sn)
+//}
\ No newline at end of file
diff --git a/pkg/control/tracker.go b/pkg/control/tracker.go
new file mode 100644 (file)
index 0000000..bd062da
--- /dev/null
@@ -0,0 +1,73 @@
+/*
+==================================================================================
+  Copyright (c) 2019 AT&T Intellectual Property.
+  Copyright (c) 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.
+==================================================================================
+*/
+
+package control
+
+import (
+       "fmt"
+//     "gerrit.o-ran-sc.org/r/ric-plt/xapp-frame/pkg/xapp"
+)
+
+/*
+Implements a record of ongoing transactions and helper functions to CRUD the records.
+*/
+type Tracker struct {
+       transaction_table map[Transaction_key]*Transaction
+}
+
+/*
+Checks if a tranascation with similar type has been ongoing. If not then creates one.
+Returns error if there is similar transatcion ongoing.
+*/
+func (t *Tracker) Track_transaction(key Transaction_key, xact *Transaction) error{
+       if _, ok := t.transaction_table[key]; ok {
+               // TODO: Implement merge related check here. If the key is same but the value is different.
+               err := fmt.Errorf("Transaction tracker: Similar transaction with sub id %d and type %s is ongoing", key.SubID, key.trans_type )
+               return err
+       }
+       t.transaction_table[key] = xact
+       return nil
+}
+
+/*
+Retreives the transaction table entry for the given request.
+Returns error in case the transaction cannot be found.
+*/
+func (t *Tracker) Retrive_transaction(subID uint16, act Action) (*Transaction, error){
+       key := Transaction_key{subID, act}
+       if xact, ok := t.transaction_table[key]; ok {
+               return xact, nil
+       }
+       err := fmt.Errorf("Tranaction record for Subscription ID %d and action %s does not exist", subID, act)
+       return nil, err
+}
+
+/*
+Deletes the transaction table entry for the given request and returns the deleted xapp's address and port for reference.
+Returns error in case the transaction cannot be found.
+*/
+func (t *Tracker) complete_transaction(subID uint16, act Action) (*string, *uint16, error){
+       key := Transaction_key{subID, act}
+       if xact, ok := t.transaction_table[key]; ok {
+               delete(t.transaction_table, key)
+               return &(xact.Xapp_instance_address), &(xact.Xapp_port), nil
+       }
+       err := fmt.Errorf("Tranaction record for Subscription ID %d and action %s does not exist", subID, act)
+       return nil, nil, err
+}
index 2a4e9d5..1a2c92f 100644 (file)
@@ -24,3 +24,24 @@ type RmrDatagram struct {
        SubscriptionId uint16
        Payload        []byte
 }
+
+type subRouteInfo struct {
+       Command  Action
+       Address  string
+       Port     uint16
+       SubID    uint16
+}
+
+type Action int
+
+type Transaction_key struct {
+       SubID      uint16
+       trans_type Action
+}
+
+type Transaction struct {
+//     Xapp_address          string
+       Xapp_instance_address string
+       Xapp_port             uint16
+       Ric_sub_req           []byte
+}
index 8c874ff..8fe571a 100644 (file)
@@ -24,7 +24,7 @@ apiVersion: apps/v1
 kind: Deployment
 metadata:
   name: dbaas
-  namespace: example
+  namespace: ricplt
 spec:
   replicas: 1
   selector:
index 53df6de..bd5ed8a 100644 (file)
@@ -24,7 +24,7 @@ kind: Service
 apiVersion: v1
 metadata:
   name: dbaas
-  namespace: example
+  namespace: ricplt
 spec:
   selector:
     app: dbaas
index 87f8af7..0f726e7 100644 (file)
@@ -30,10 +30,11 @@ RUN echo 'Acquire::http::Proxy "http://87.254.212.121:8080/";' > /etc/apt/apt.co
 
 COPY . /opt/submgr
 
-# Install RMr shared library
-RUN wget --content-disposition https://packagecloud.io/o-ran-sc/master/packages/debian/stretch/rmr_1.0.36_amd64.deb/download.deb && dpkg -i rmr_1.0.36_amd64.deb
-# Install RMr development header files
-RUN wget --content-disposition https://packagecloud.io/o-ran-sc/master/packages/debian/stretch/rmr-dev_1.0.36_amd64.deb/download.deb && dpkg -i rmr-dev_1.0.36_amd64.deb
+ARG RMRVERSION=1.3.0
+
+RUN wget --content-disposition https://packagecloud.io/o-ran-sc/master/packages/debian/stretch/rmr_${RMRVERSION}_amd64.deb/download.deb && dpkg -i rmr_${RMRVERSION}_amd64.deb
+RUN wget --content-disposition https://packagecloud.io/o-ran-sc/master/packages/debian/stretch/rmr-dev_${RMRVERSION}_amd64.deb/download.deb && dpkg -i rmr-dev_${RMRVERSION}_amd64.deb
+RUN rm -f rmr_${RMRVERSION}_amd64.deb rmr-dev_${RMRVERSION}_amd64.deb
 
 # "PULLING LOG and COMPILING LOG"
 RUN git clone "https://gerrit.o-ran-sc.org/r/com/log" /opt/log && cd /opt/log && \
@@ -47,6 +48,21 @@ RUN cd /opt/submgr/e2ap && \
  cp wrapper.h headers/*.h /usr/local/include/ && \
  ldconfig
 
+# "Installing Swagger"
+RUN cd /usr/local/go/bin \
+    && wget --quiet https://github.com/go-swagger/go-swagger/releases/download/v0.19.0/swagger_linux_amd64 \
+    && mv swagger_linux_amd64 swagger \
+    && chmod +x swagger
+
+# "Getting and generating routing managers api client"
+RUN cd /opt/submgr \
+    && git clone "https://gerrit.o-ran-sc.org/r/ric-plt/rtmgr" \
+    && cp rtmgr/api/routing_manager.yaml api/ \
+    && rm -rf rtmgr
+RUN cd /opt/submgr \
+    && mkdir -p /root/go \
+    && /usr/local/go/bin/swagger generate client -f api/routing_manager.yaml -t pkg/ -m rtmgr_models -c rtmgr_client
+
 RUN mkdir -p /opt/bin && cd /opt/submgr && \
  /usr/local/go/bin/go get && \
    /usr/local/go/bin/go build -o /opt/test/e2t/e2t ./test/e2t/e2t.go && \
@@ -59,4 +75,6 @@ COPY  test/e2t/e2t.yaml test/e2t/container/run_e2t.sh /
 COPY --from=submgrbuild /usr/local/include /usr/local/include
 COPY --from=submgrbuild /usr/local/lib /usr/local/lib
 
-RUN ldconfig
\ No newline at end of file
+RUN ldconfig
+
+RUN chmod 755 /run_e2t.sh
index 61ef9bd..64967c7 100644 (file)
@@ -24,7 +24,7 @@ apiVersion: apps/v1
 kind: Deployment
 metadata:
   name: e2t
-  namespace: example
+  namespace: ricplt
 spec:
   replicas: 1
   selector:
@@ -37,7 +37,7 @@ spec:
     spec:
       containers:
       - name: e2t
-        image: cmaster:5000/e2t:builder
+        image: jenkins:5000/e2t:test
         command: ["/run_e2t.sh"]
         env:
         - name: DBAAS_SERVICE_HOST
index 2658d7c..03b6a75 100644 (file)
@@ -24,7 +24,7 @@ kind: Service
 apiVersion: v1
 metadata:
   name: e2t
-  namespace: example
+  namespace: ricplt
 spec:
   selector:
     app: e2t
index 995fe70..328c85a 100644 (file)
@@ -30,9 +30,9 @@ RUN echo 'Acquire::http::Proxy "http://87.254.212.121:8080/";' > /etc/apt/apt.co
 
 COPY . /opt/submgr
 # Install RMr shared library
-RUN wget --content-disposition https://packagecloud.io/o-ran-sc/master/packages/debian/stretch/rmr_1.0.36_amd64.deb/download.deb && dpkg -i rmr_1.0.36_amd64.deb
+RUN wget --content-disposition https://packagecloud.io/o-ran-sc/staging/packages/debian/stretch/rmr_1.6.0_amd64.deb/download.deb && dpkg -i rmr_1.6.0_amd64.deb
 # Install RMr development header files
-RUN wget --content-disposition https://packagecloud.io/o-ran-sc/master/packages/debian/stretch/rmr-dev_1.0.36_amd64.deb/download.deb && dpkg -i rmr-dev_1.0.36_amd64.deb
+RUN wget --content-disposition https://packagecloud.io/o-ran-sc/staging/packages/debian/stretch/rmr-dev_1.6.0_amd64.deb/download.deb && dpkg -i rmr-dev_1.6.0_amd64.deb
 
 # "PULLING LOG and COMPILING LOG"
 RUN git clone "https://gerrit.o-ran-sc.org/r/com/log" /opt/log && cd /opt/log && \
@@ -46,6 +46,22 @@ RUN cd /opt/submgr/e2ap && \
  cp wrapper.h headers/*.h /usr/local/include/ && \
  ldconfig
 
+# "Installing Swagger"
+RUN cd /usr/local/go/bin \
+    && wget --quiet https://github.com/go-swagger/go-swagger/releases/download/v0.19.0/swagger_linux_amd64 \
+    && mv swagger_linux_amd64 swagger \
+    && chmod +x swagger
+
+# "Getting and generating routing managers api client"
+RUN cd /opt/submgr \
+    && git clone "https://gerrit.o-ran-sc.org/r/ric-plt/rtmgr" \
+    && cp rtmgr/api/routing_manager.yaml api/ \
+    && rm -rf rtmgr
+RUN cd /opt/submgr \
+    && mkdir -p /root/go \
+    && /usr/local/go/bin/swagger generate client -f api/routing_manager.yaml -t pkg/ -m rtmgr_models -c rtmgr_client
+
+
 RUN mkdir -p /opt/bin && cd /opt/submgr && \
  /usr/local/go/bin/go get && \
    /usr/local/go/bin/go build -o /opt/test/rco/rco ./test/rco/rco.go && \
@@ -54,8 +70,10 @@ RUN mkdir -p /opt/bin && cd /opt/submgr && \
 FROM ubuntu:18.04
 
 COPY --from=submgrbuild /opt/test/rco/rco /
-COPY  test/rco/rco.yaml test/rco/container/run_rco.sh /
+COPY  test/rco/rco.yaml test/rco/container/run_rco.sh test/uta_rtg.rt /
 COPY --from=submgrbuild /usr/local/include /usr/local/include
 COPY --from=submgrbuild /usr/local/lib /usr/local/lib
 
-RUN ldconfig
\ No newline at end of file
+RUN ldconfig
+RUN chmod 755 /run_rco.sh
+RUN chmod 755 /rco
index fe4cdb1..25926b8 100644 (file)
@@ -24,7 +24,7 @@ apiVersion: apps/v1
 kind: Deployment
 metadata:
   name: rco
-  namespace: example
+  namespace: ricplt
 spec:
   replicas: 1
   selector:
@@ -37,7 +37,7 @@ spec:
     spec:
       containers:
       - name: rco
-        image: cmaster:5000/rco:builder
+        image: rco:builder
         command: ["/run_rco.sh"]
         env:
         - name: DBAAS_SERVICE_HOST
@@ -46,7 +46,11 @@ spec:
           value: 000003ea7e000500aaaaccccea6300020000ea81000e00045465737400ea6b0003000100
         - name: RCO_SEED_SN
           value: "9999"
+        - name: RMR_SEED_RT
+          value: uta_rtg.rt
+
         ports:
         - containerPort: 8080
         - containerPort: 4560
         - containerPort: 4561
+        imagePullPolicy: Always
index 5310ddd..1648231 100644 (file)
@@ -24,7 +24,7 @@ kind: Service
 apiVersion: v1
 metadata:
   name: rco
-  namespace: example
+  namespace: ricplt
 spec:
   selector:
     app: rco
index 5f740f2..6ba36d0 100644 (file)
@@ -34,28 +34,37 @@ type Rco struct {
 }
 
 var c chan submgr.RmrDatagram = make(chan submgr.RmrDatagram, 1)
+var params *xapp.RMRParams
 
-var RAWDATA string
+var REQUESTRAWDATA string
+var DELETERAWDATA string
 var SEEDSN uint16
+var DELETESEEDSN uint16
 
 func init() {
        viper.AutomaticEnv()
        viper.SetEnvPrefix("rco")
        viper.AllowEmptyEnv(true)
-       RAWDATA = viper.GetString("rawdata")
-       if RAWDATA == "" {
-               RAWDATA = "000003ea7e000500aaaaccccea6300020000ea81000e00045465737400ea6b0003000100"
+       REQUESTRAWDATA = viper.GetString("rawdata")
+       if REQUESTRAWDATA == "" {
+               REQUESTRAWDATA = "000003ea7e000500aaaaccccea6300020000ea81000e00045465737400ea6b0003000100"
        }
-       xapp.Logger.Info("Initial RAW DATA: %v", RAWDATA)
+       DELETERAWDATA = viper.GetString("deleterawdata")
+       if DELETERAWDATA == "" {
+               DELETERAWDATA = "000002ea7e000500aaaabbbbea6300020000"
+       }
+       xapp.Logger.Info("Initial RAW DATA: %v", REQUESTRAWDATA)
+       xapp.Logger.Info("Initial DELETE RAW DATA: %v", DELETERAWDATA)
        SEEDSN = uint16(viper.GetInt("seed_sn"))
        if SEEDSN == 0 || SEEDSN > 65535 {
                SEEDSN = 12345
        }
+       DELETESEEDSN = SEEDSN
        xapp.Logger.Info("Initial SEQUENCE NUMBER: %v", SEEDSN)
 }
 
 func (r *Rco) GeneratePayload(sub_id uint16) (payload []byte, err error) {
-       skeleton, err := hex.DecodeString(RAWDATA)
+       skeleton, err := hex.DecodeString(REQUESTRAWDATA)
        if err != nil {
                return make([]byte, 0), errors.New("Unable to decode data provided in RCO_RAWDATA environment variable")
        }
@@ -63,24 +72,43 @@ func (r *Rco) GeneratePayload(sub_id uint16) (payload []byte, err error) {
        return
 }
 
-func (r Rco) Consume(mtype, sub_id int, len int, payload []byte) (err error) {
-       payload_seq_num, err := r.GetSubscriptionResponseSequenceNumber(payload)
+func (r *Rco) GenerateDeletePayload(sub_id uint16) (payload []byte, err error) {
+       skeleton, err := hex.DecodeString(DELETERAWDATA)
+       if err != nil {
+               return make([]byte, 0), errors.New("Unable to decode data provided in RCO_DELETE RAWDATA environment variable")
+       }
+       xapp.Logger.Info("SetSubscriptionDeleteRequestSequenceNumber1")
+       payload, err = r.SetSubscriptionDeleteRequestSequenceNumber(skeleton, sub_id)
+       xapp.Logger.Info("SetSubscriptionDeleteRequestSequenceNumber2")
+       return
+}
+
+func (r Rco) Consume(params *xapp.RMRParams) (err error) {
+       payload_seq_num, err := r.GetSubscriptionResponseSequenceNumber(params.Payload)
        if err != nil {
                xapp.Logger.Error("Unable to get Subscription Sequence Number from Payload due to: " + err.Error())     
        }
-       xapp.Logger.Info("Message Received: RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", sub_id, payload_seq_num)
+       xapp.Logger.Info("Message Received: RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v", params.SubId, payload_seq_num)
        return
 }
 
-func (r *Rco) SendSubscriptionRequests() (err error) {
+func (r *Rco) SendRequests() (err error) {
        message, err := r.GeneratePayload(SEEDSN)
        if err != nil {
                xapp.Logger.Debug(err.Error())
                return
        }
+       deletemessage, err := r.GenerateDeletePayload(DELETESEEDSN)
+       if err != nil {
+               xapp.Logger.Debug(err.Error())
+               return
+       }
        for {
                time.Sleep(2 * time.Second)
                c <- submgr.RmrDatagram{12010, SEEDSN, message}
+               time.Sleep(2 * time.Second)
+               c <- submgr.RmrDatagram{12020, DELETESEEDSN, deletemessage}
+               DELETESEEDSN++
        }
        return
 }
@@ -92,8 +120,12 @@ func (r *Rco) Run() {
                if err != nil {
                        xapp.Logger.Debug("Unable to get Subscription Sequence Number from Payload due to: " + err.Error())     
                }
+               params.SubId = int(message.SubscriptionId)
+               params.Mtype = message.MessageType
+               params.PayloadLen = len(message.Payload)
+               params.Payload = message.Payload
                xapp.Logger.Info("Sending Message: TYPE: %v | RMR SUBSCRIPTION_ID: %v | PAYLOAD SEQUENCE_NUMBER: %v)", message.MessageType, message.SubscriptionId, payload_seq_num)
-               xapp.Rmr.Send(message.MessageType, int(message.SubscriptionId), len(message.Payload), message.Payload)
+               xapp.Rmr.Send(params, false)
        }
 }
 
@@ -111,7 +143,7 @@ func main() {
        go xapp.Rmr.Start(rco)
        go rco.Run()
        go rco.sendInvalidTestMessages()
-       err := rco.SendSubscriptionRequests()
+       err := rco.SendRequests()
        if err != nil {
                os.Exit(1)
        }