Version bump to 1.1.1
[ric-app/hw-python.git] / README.md
1 # O-RAN-SC Hello World Xapp in Python
2
3 This repository contains open-source code for a prototype python xAPP for near real-time
4 RAN Intelligent Controller which makes use of python Xapp Framework.
5
6 This xAPP aims to provide basic implementation of :
7
8 1. A1 interfaces interactions
9
10 2. Read-write operations into a persistent storage. 
11
12 3. xAPP Configuration management
13
14 4. RMR Health Check
15
16 5. xAPP SDL Check
17
18 6. Raising alarms
19
20 7. Generating metrics (TBD)
21
22 8. E2 Interface intereactions (TBD)
23
24
25 Introduction
26 ------------
27
28 This document provides guidelines on how to install and configure the HW Python xAPP in various environments/operating modes.
29 The audience of this document is assumed to have good knowledge in RIC Platform.
30
31
32 Preface
33 -------
34 This xAPP can be run directly as a Linux binary, as a docker image, or in a pod in a Kubernetes environment.  The first
35 two can be used for dev testing. The last option is how an xAPP is deployed in the RAN Intelligent Controller environment.
36 This covers all three methods. 
37
38 1. Docker 
39
40 2. Linux Binary
41
42 3. Kubernetes 
43
44
45
46
47
48 ##Build Process
49
50 The HW xAPP can be either tested as a Linux binary or as a docker image.
51    1. **Linux binary**: The HW xAPP may be compiled and invoked directly.
52       Pre-requisite software packages that must be installed prior to 
53       compiling are documented in the Dockerfile in the repository.
54       
55
56    2. **Docker Image**:For building docker images, the Docker environment 
57       must be present in the system.
58       
59       Change to the root of the repository   
60       ```
61       $ docker --no-cache build -t hw-python ./
62       Sending build context to Docker daemon  439.3kB
63       Step 1/18 : FROM python:3.8-alpine
64       3.8-alpine: Pulling from library/python
65       .
66       .
67       .
68       .
69       
70       Step 17/18 : ENV DBAAS_SERVICE_HOST=service-ricplt-dbaas-tcp.ricplt.svc.cluster.local
71        ---> Running in d00e08612ff4
72       Removing intermediate container d00e08612ff4
73        ---> da54555174d1
74       Step 18/18 : CMD run-hw-python.py
75        ---> Running in f96da2ac3f43
76       Removing intermediate container f96da2ac3f43
77        ---> 1b96cc7da63c
78       Successfully built 1b96cc7da63c
79       Successfully tagged hw-python:latest
80
81       ```
82
83       After the docker image is Successfully built , 
84       Now run the hw-python:latest by following command:
85       ```
86       
87       $ docker run hw-python:latest
88       1625730731 1/RMR [INFO] sends: ts=1625730731 src=fdbb898edc12:4560 target=service-ricplt-a1mediator-rmr.ricplt:4562 open=0 succ=0 fail=0 (hard=0 soft=0)
89       1625730731 1/RMR [INFO] sends: ts=1625730731 src=fdbb898edc12:4560 target=127.0.0.1:4560 open=0 succ=0 fail=0 (hard=0 soft=0)
90       1625730762 1/RMR [INFO] sends: ts=1625730762 src=fdbb898edc12:4560 target=service-ricplt-a1mediator-rmr.ricplt:4562 open=0 succ=0 fail=0 (hard=0 soft=0)
91       1625730762 1/RMR [INFO] sends: ts=1625730762 src=fdbb898edc12:4560 target=127.0.0.1:4560 open=0 succ=0 fail=0 (hard=0 soft=0)
92
93       ```
94       
95 Software Installation and Deployment
96 ------------------------------------
97 ### Onboarding of hw-python using dms_cli tool
98
99 `dms_cli` offers rich set of command line utility to onboard `hw-python` xapp
100 to `chartmuseme`.
101
102 First checkout the [hw-python](https://gerrit.o-ran-sc.org/r/ric-app/hw-python) repository from gerrit.
103
104 ```
105 git clone "https://gerrit.o-ran-sc.org/r/ric-app/hw-python"
106 ```
107
108 `hw-python` has following folder structure
109 ```
110 +---docs
111 |           
112 +---hw_python.egg-info
113 |       
114 +---init
115 |       config-file.json # descriptor for xapp deployment.
116 |       init_script.py
117 |       test_route.rt
118 |       schema.json #schema for validating the config-file.json
119 |       
120 +---releases
121 |       
122 +---resources
123 |       
124 +---src
125
126 ```
127
128 For onboarding `hw-python` make sure that `dms_cli` and helm3 is installed. One can follow [documentation](https://docs.o-ran-sc.org/projects/o-ran-sc-it-dep/en/latest/installation-guides.html#ric-applications) to
129 configure `dms_cli`.
130
131 Once `dms_cli` is availabe we can proceed to onboarding proceure.
132
133 configure the `export CHART_REPO_URL` to point `chartmuseme`.
134 ```
135 $export CHART_REPO_URL=http://<service-ricplt-xapp-onboarder-http.ricplt>:8080
136 ``` 
137
138 check if `dms_cli` working fine.
139 ```
140 $ dms_cli health
141 True
142 ```
143
144 Now move to `init` folder to initiate onboarding.
145
146 ```
147 $ cd init
148
149 $ dms_cli onboard --config_file_path=config-file.json --shcema_file_path=schema.json
150 httpGet:
151   path: '{{ index .Values "readinessProbe" "httpGet" "path" | toJson }}'
152   port: '{{ index .Values "readinessProbe" "httpGet" "port" | toJson }}'
153 initialDelaySeconds: '{{ index .Values "readinessProbe" "initialDelaySeconds" | toJson }}'
154 periodSeconds: '{{ index .Values "readinessProbe" "periodSeconds" | toJson }}'
155
156 httpGet:
157   path: '{{ index .Values "livenessProbe" "httpGet" "path" | toJson }}'
158   port: '{{ index .Values "livenessProbe" "httpGet" "port" | toJson }}'
159 initialDelaySeconds: '{{ index .Values "livenessProbe" "initialDelaySeconds" | toJson }}'
160 periodSeconds: '{{ index .Values "livenessProbe" "periodSeconds" | toJson }}'
161
162 {
163     "status": "Created"
164 }
165 ```
166
167 Check if `hw-python` is onborded
168 ```
169 $ curl --location --request GET "http://<appmgr>:32080/onboard/api/v1/charts"  --header 'Content-Type: application/json'
170 {
171     "hw-python": [
172         {
173             "name": "hw-python",
174             "version": "1.0.0",
175             "description": "Standard xApp Helm Chart",
176             "apiVersion": "v1",
177             "appVersion": "1.0",
178             "urls": [
179                 "charts/hw-python-1.0.0.tgz"
180             ],
181             "created": "2021-07-05T15:07:34.518377486Z",
182             "digest": "e9db874d35154643a2c6f26dd52929c9dcf143f165683c03d07518bb0c2d768d"
183         }
184     ],
185     "hw-python": [
186         {
187             "name": "hw-python",
188             "version": "1.0.0",
189             "description": "Standard xApp Helm Chart",
190             "apiVersion": "v1",
191             "appVersion": "1.0",
192             "urls": [
193                 "charts/hw-python-1.0.0.tgz"
194             ],
195             "created": "2021-07-05T15:20:13.965653743Z",
196             "digest": "975b1da1f8669e8ed1b1e5be809e7cf4841ef33abcb88207bc3a735e9b543a9a"
197         }
198     ]
199 }
200 ```
201
202 If we would wish to download the charts then we can perform following curl operation :
203
204 ```
205 curl --location --request GET "http://<appmgr>:32080/onboard/api/v1/charts/xapp/hw-python/ver/1.0.0"  --header 'Content-Type: application/json' --output hw-python.tgz
206 ```
207 The downloaded folder has the deployment files for hw-python 
208 ```
209 tar -xvzf hw-python.tgz
210 hw-python/Chart.yaml
211 hw-python/values.yaml
212 hw-python/templates/_helpers.tpl
213 hw-python/templates/appconfig.yaml
214 hw-python/templates/appenv.yaml
215 hw-python/templates/deployment.yaml
216 hw-python/templates/service-http.yaml
217 hw-python/templates/service-rmr.yaml
218 hw-python/config/config-file.json
219 hw-python/descriptors/schema.json
220
221 ```
222
223 Now the onboarding is done.
224
225 ### Deployment of hw-python 
226
227 Once charts are available we can deploy the the `hw-python` using following curl command :
228
229 ```
230 $ curl --location --request POST "http://<appmgr>:32080/appmgr/ric/v1/xapps"  --header 'Content-Type: application/json'  --data-raw '{"xappName": "hw-python", "helmVersion": "1.0.0"}'
231 {"instances":null,"name":"hw-python","status":"deployed","version":"1.0"}
232 ```
233
234 Deployment will be done in `ricxapp` ns :
235
236 ```
237 # kubectl get pods -n ricxapp
238 NAME                                 READY   STATUS    RESTARTS   AGE
239 ricxapp-hw-python-64b5447dcc-mbt5w   1/1     Running   0          5m45s
240
241        CLUSTER-IP       EXTERNAL-IP   PORT(S)             AGE
242 aux-entry                        ClusterIP   10.111.35.76     <none>        80/TCP,443/TCP      9d
243 service-ricxapp-hw-python-http   ClusterIP   10.104.223.245   <none>        8080/TCP            6m23s
244 service-ricxapp-hw-python-rmr    ClusterIP   10.103.243.21    <none>        4560/TCP,4561/TCP   6m23s
245
246 ```
247
248 Now we can query to appmgr to get list of all the deployed xapps :
249
250 ```
251 # curl http://service-ricplt-appmgr-http.ricplt:8080/ric/v1/xapps | jq .
252   % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
253                                  Dload  Upload   Total   Spent    Left  Speed
254 100   347  100   347    0     0    578      0 --:--:-- --:--:-- --:--:--   579
255 [
256   {
257     "instances": [
258       {
259         "ip": "service-ricxapp-hw-python-rmr.ricxapp",
260         "name": "hw-python-55ff7549df-kpj6k",
261         "policies": [
262           1
263         ],
264         "port": 4560,
265         "rxMessages": [
266           "RIC_SUB_RESP",
267           "A1_POLICY_REQ",
268           "RIC_HEALTH_CHECK_REQ"
269         ],
270         "status": "running",
271         "txMessages": [
272           "RIC_SUB_REQ",
273           "A1_POLICY_RESP",
274           "A1_POLICY_QUERY",
275           "RIC_HEALTH_CHECK_RESP"
276         ]
277       }
278     ],
279     "name": "hw-python",
280     "status": "deployed",
281     "version": "1.0"
282   }
283 ]
284
285 ```
286 Logs from `hw-python` :
287
288 ```
289 # kubectl  logs ricxapp-hw-python-55ff7549df-kpj6k -n ricxapp
290 {"ts":1624562552123,"crit":"INFO","id":"hw-app","mdc":{"time":"2021-06-24T19:22:32"},"msg":"Using config file: config/config-file.json"}
291 {"ts":1624562552124,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"Serving metrics on: url=/ric/v1/metrics namespace=ricxapp"}
292 {"ts":1624562552133,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"Register new counter with opts: {ricxapp SDL Stored The total number of stored SDL transactions map[]}"}
293 {"ts":1624562552133,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"Register new counter with opts: {ricxapp SDL StoreError The total number of SDL store errors map[]}"}
294 1624562552 6/RMR [INFO] ric message routing library on SI95 p=0 mv=3 flg=00 (fd4477a 4.5.2 built: Jan 21 2021)
295 {"ts":1624562552140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"new rmrClient with parameters: ProtPort=0 MaxSize=0 ThreadType=0 StatDesc=RMR LowLatency=false FastAck=false Policies=[]"}
296 {"ts":1624562552140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"Register new counter with opts: {ricxapp RMR Transmitted The total number of transmited RMR messages map[]}"}
297 {"ts":1624562552140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"Register new counter with opts: {ricxapp RMR Received The total number of received RMR messages map[]}"}
298 {"ts":1624562552140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"Register new counter with opts: {ricxapp RMR TransmitError The total number of RMR transmission errors map[]}"}
299 {"ts":1624562552140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"Register new counter with opts: {ricxapp RMR ReceiveError The total number of RMR receive errors map[]}"}
300 {"ts":1624562552140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"Xapp started, listening on: :8080"}
301 {"ts":1624562552140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:32"},"msg":"rmrClient: Waiting for RMR to be ready ..."}
302 {"ts":1624562553140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:33"},"msg":"rmrClient: RMR is ready after 1 seconds waiting..."}
303 {"ts":1624562553141,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:33"},"msg":"xApp ready call back received"}
304 1624562553 6/RMR [INFO] sends: ts=1624562553 src=service-ricxapp-hw-python-rmr.ricxapp:0 target=localhost:4591 open=0 succ=0 fail=0 (hard=0 soft=0)
305 1624562553 6/RMR [INFO] sends: ts=1624562553 src=service-ricxapp-hw-python-rmr.ricxapp:0 target=localhost:4560 open=0 succ=0 fail=0 (hard=0 soft=0)
306 1624562553 6/RMR [INFO] sends: ts=1624562553 src=service-ricxapp-hw-python-rmr.ricxapp:0 target=service-ricplt-a1mediator-rmr.ricplt:4562 open=0 succ=0 fail=0 (hard=0 soft=0)
307 RMR is ready now ...
308 {"ts":1624562557140,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:37"},"msg":"Application='hw-python' is not ready yet, waiting ..."}
309 {"ts":1624562562141,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:42"},"msg":"Application='hw-python' is not ready yet, waiting ..."}
310 {"ts":1624562567141,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:47"},"msg":"Application='hw-python' is not ready yet, waiting ..."}
311 {"ts":1624562567370,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:47"},"msg":"restapi: method=GET url=/ric/v1/health/ready"}
312 {"ts":1624562569766,"crit":"INFO","id":"hw-app","mdc":{"CONTAINER_NAME":"","HOST_NAME":"","HWApp":"0.0.1","PID":"6","POD_NAME":"","SERVICE_NAME":"","SYSTEM_NAME":"","time":"2021-06-24T19:22:49"},"msg":"restapi: method=GET url=/ric/v1/health/alive"}
313 ```
314
315 Here we are done with the onboaring and deployment of `hw-python`.
316
317
318
319
320
321 Testing 
322 --------
323
324 Unit tests TBD
325
326
327 ## License
328
329 ```
330
331    Copyright (c) 2020 Samsung Electronics Co., Ltd. All Rights Reserved.
332
333    Licensed under the Apache License, Version 2.0 (the "License");
334    you may not use this file except in compliance with the License.
335    You may obtain a copy of the License at
336
337        http://www.apache.org/licenses/LICENSE-2.0
338
339    Unless required by applicable law or agreed to in writing, software
340    distributed under the License is distributed on an "AS IS" BASIS,
341    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
342    See the License for the specific language governing permissions and
343    limitations under the License.
344
345 ```