2 # ============LICENSE_START===============================================
3 # Copyright (C) 2020 Nordix Foundation. All rights reserved.
4 # ========================================================================
5 # Licensed under the Apache License, Version 2.0 (the "License");
6 # you may not use this file except in compliance with the License.
7 # You may obtain a copy of the License at
9 # http://www.apache.org/licenses/LICENSE-2.0
11 # Unless required by applicable law or agreed to in writing, software
12 # distributed under the License is distributed on an "AS IS" BASIS,
13 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 # See the License for the specific language governing permissions and
15 # limitations under the License.
16 # ============LICENSE_END=================================================
20 // Sim mon server - query the agent and the simulators for counters and other data
21 // Presents a web page on localhost:9999/mon
23 var LOCALHOST="http://127.0.0.1:"
24 var MRSTUB_PORT="3905"
28 var PRODSTUB_PORT="8092"
31 var http = require('http');
33 var express = require('express');
34 const { POINT_CONVERSION_HYBRID } = require('constants')
41 app.get("/",function(req, res){
45 //Get parameter value from other server
46 function getSimCtr(url, index, cb) {
50 http.get(url, (resp) => {
51 // A chunk of data has been recieved.
52 resp.on('data', (chunk) => {
56 // The whole response has been received.
57 resp.on('end', () => {
58 var code=resp.statusCode
59 if (code > 199 && code < 300) {
62 cb("not found", index);
66 }).on("error", (err) => {
67 console.log("Error: " + err.message);
68 cb("no response", index);
71 cb("no response", index);
76 //Format a comma separated list of data to a html-safe string with fixed fieldsizes
77 function formatDataRow(commaList) {
79 var tmp=commaList.split(',');
80 for(var i=0;i<tmp.length;i++) {
82 var len = fieldSize-data.length;
87 str=str+data+" ";
92 //Format a comma separated list of ids to a html-safe string with fixed fieldsizes
93 function formatIdRow(commaList) {
95 var tmp=commaList.split(',');
96 for(var i=0;i<tmp.length;i++) {
97 tmp[i] = tmp[i].trim();
98 var data="<"+tmp[i]+">";
99 var len = fieldSize+4-data.length;
101 data = data+" ";
104 str=str+data+" ";
109 //Format a list of ids to a html-safe string in compact format
110 function formatIdRowCompact(commaList) {
111 if (commaList == undefined) {
115 var tmp=commaList.split(',');
116 for(var i=0;i<tmp.length;i++) {
117 tmp[i] = tmp[i].trim();
118 var data="<"+tmp[i]+">";
119 str=str+data+" ";
124 //Pad a string upto a certain size using a pad string
125 function padding(val, size, pad) {
127 for(var i=s.length;i<size;i++) {
133 //Function to check if the previous call has returned, if so return true, if not return false
134 //For preventing multiple calls to slow containers.
135 function checkFunctionFlag(flag) {
136 if (flagstore.hasOwnProperty(flag)) {
137 if (flagstore[flag] == 0) {
140 } else if (flagstore[flag] > 10) {
141 //Reset flag after ten attempts
142 console.log("Force release flag "+flag)
146 //Previous call not returned
147 console.log("Flag not available "+flag)
148 flagstore[flag]=flagstore[flag]+1
156 //Clear flag for parameter
157 function clearFlag(flag) {
161 //Status variables, for parameters values fetched from other simulators
162 var mr1="", mr2="", mr3="", mr4="", mr5="", mr6="";
164 //Status variables for agent
171 //Status variables for callback receiver
177 //Container names and ports of the ric simulator
181 //Status variables for each ric simulator
189 //Status variables, for parameters values fetched from ecs
190 var ecs1="", ecs2="", ecs3="", ecs4="", ecs_types="-", ecs_producers="-";
191 var ecs_producer_arr=new Array(0)
192 var ecs_producer_type_arr=new Array(0)
193 var ecs_producer_jobs_arr=new Array(0)
194 var ecs_producer_status_arr=new Array(0)
195 var ecs_jobs=new Array(0)
196 var ecs_job_status=new Array(0)
198 //Status variables, for parameters values fetched from prodstub
199 var ps2="", ps3="", ps4="", ps_types="-", ps_producers="-";
200 var ps_producer_type_arr=new Array(0)
201 var ps_producer_jobs_arr=new Array(0)
202 var ps_producer_delivery_arr=new Array(0)
207 //Counts the number of get request for the html page
210 var refreshCount_pol=-1
212 var refreshCount_ecs=-1
214 var refreshCount_cr=-1
216 var refreshCount_rc=-1
218 var ricbasename="ricsim"
222 function fetchAllMetrics_pol() {
224 console.log("Fetching policy metrics " + refreshCount_pol)
226 if (refreshCount_pol < 0) {
227 refreshCount_pol = -1
230 refreshCount_pol = refreshCount_pol - 1
235 //Extract the port numbers from the running simulators, for every 3 calls
236 const { exec } = require('child_process');
237 exec('docker ps --filter "name='+ricbasename+'" --format "{{.Names}} {{.Ports}}" | sed s/0.0.0.0:// | cut -d \'>\' -f1 | sed \'s/[[-]]*$//\'', (err, stdout, stderr) => {
240 simulators=`${stdout}`.replace(/(\r\n|\n|\r)/gm," ");
241 simulators=simulators.trim();
242 var sims=simulators.split(" ")
245 for(var i=0;i<sims.length;i=i+2) {
246 simnames[i/2]=sims[i]
247 simports[i/2]=sims[i+1]
253 //Get metric values from the simulators
254 for(var index=0;index<simnames.length;index++) {
256 if (checkFunctionFlag("simvar1_"+index)) {
257 getSimCtr(LOCALHOST+simports[index]+"/counter/num_instances", index, function(data, idx) {
259 clearFlag("simvar1_"+idx)
262 if (checkFunctionFlag("simvar2_"+index)) {
263 getSimCtr(LOCALHOST+simports[index]+"/counter/num_types", index, function(data,idx) {
265 clearFlag("simvar2_"+idx)
268 if (checkFunctionFlag("simvar3_"+index)) {
269 getSimCtr(LOCALHOST+simports[index]+"/policytypes", index, function(data,idx) {
270 data=data.replace(/\[/g,'');
271 data=data.replace(/\]/g,'');
272 data=data.replace(/ /g,'');
273 data=data.replace(/\"/g,'');
275 clearFlag("simvar3_"+idx)
278 if (checkFunctionFlag("simvar4_"+index)) {
279 getSimCtr(LOCALHOST+simports[index]+"/counter/interface", index, function(data,idx) {
281 clearFlag("simvar4_"+idx)
284 if (checkFunctionFlag("simvar5_"+index)) {
285 getSimCtr(LOCALHOST+simports[index]+"/counter/remote_hosts", index, function(data,idx) {
287 clearFlag("simvar5_"+idx)
290 if (checkFunctionFlag("simvar6_"+index)) {
291 getSimCtr(LOCALHOST+simports[index]+"/counter/datadelivery", index, function(data,idx) {
293 clearFlag("simvar6_"+idx)
298 //MR - get metrics values from the MR stub
299 if (checkFunctionFlag("mr1")) {
300 getSimCtr(LOCALHOST+MRSTUB_PORT+"/counter/requests_submitted", 0, function(data, idx) {
305 if (checkFunctionFlag("mr2")) {
306 getSimCtr(LOCALHOST+MRSTUB_PORT+"/counter/requests_fetched", 0, function(data, idx) {
311 if (checkFunctionFlag("mr3")) {
312 getSimCtr(LOCALHOST+MRSTUB_PORT+"/counter/current_requests", 0, function(data, idx) {
317 if (checkFunctionFlag("mr4")) {
318 getSimCtr(LOCALHOST+MRSTUB_PORT+"/counter/responses_submitted", 0, function(data, idx) {
323 if (checkFunctionFlag("mr5")) {
324 getSimCtr(LOCALHOST+MRSTUB_PORT+"/counter/responses_fetched", 0, function(data, idx) {
329 if (checkFunctionFlag("mr6")) {
330 getSimCtr(LOCALHOST+MRSTUB_PORT+"/counter/current_responses", 0, function(data, idx) {
336 //CR - get metrics values from the callbackreceiver
337 if (checkFunctionFlag("cr1")) {
338 getSimCtr(LOCALHOST+CR_PORT+"/counter/received_callbacks", 0, function(data, idx) {
343 if (checkFunctionFlag("cr2")) {
344 getSimCtr(LOCALHOST+CR_PORT+"/counter/fetched_callbacks", 0, function(data, idx) {
349 if (checkFunctionFlag("cr3")) {
350 getSimCtr(LOCALHOST+CR_PORT+"/counter/current_messages", 0, function(data, idx) {
355 //Agent - more get metrics from the agent
356 if (checkFunctionFlag("ag1")) {
357 getSimCtr(LOCALHOST+AGENT_PORT+"/status", 0, function(data, idx) {
362 if (checkFunctionFlag("ag2")) {
363 getSimCtr(LOCALHOST+AGENT_PORT+"/services", 0, function(data, idx) {
366 var jd=JSON.parse(data);
368 if (ag2.length > 1) {
371 ag2=ag2+(jd[key]["serviceName"]).trim()
380 if (checkFunctionFlag("ag3")) {
381 getSimCtr(LOCALHOST+AGENT_PORT+"/policy_types", 0, function(data, idx) {
384 var jd=JSON.parse(data);
386 if (ag3.length > 0) {
389 ag3=ag3+jd[key].trim()
399 if (checkFunctionFlag("ag4")) {
400 getSimCtr(LOCALHOST+AGENT_PORT+"/policy_ids", 0, function(data, idx) {
402 var jd=JSON.parse(data);
412 if (checkFunctionFlag("ag5")) {
413 getSimCtr(LOCALHOST+AGENT_PORT+"/rics", 0, function(data, idx) {
415 var jd=JSON.parse(data);
425 fetchAllMetrics_pol();
430 function fetchAllMetrics_ecs() {
432 console.log("Fetching enrichment metrics - timer:" + refreshCount_ecs)
434 if (refreshCount_ecs < 0) {
435 refreshCount_ecs = -1
438 refreshCount_ecs = refreshCount_ecs - 1
442 if (checkFunctionFlag("ecs_stat")) {
443 getSimCtr(LOCALHOST+ECS_PORT+"/status", 0, function(data, index) {
445 var jd=JSON.parse(data);
447 ecs2=""+jd["no_of_producers"]
448 ecs3=""+jd["no_of_types"]
449 ecs4=""+jd["no_of_jobs"]
452 ecs1="error response"
453 ecs2="error response"
454 ecs3="error response"
455 ecs4="error response"
458 clearFlag("ecs_stat")
460 if (checkFunctionFlag("ecs_types")) {
461 getSimCtr(LOCALHOST+ECS_PORT+"/ei-producer/v1/eitypes", 0, function(data, index) {
462 var tmp_ecs_types="-"
464 var jd=JSON.parse(data);
465 for(var i=0;i<jd.length;i++) {
466 if (tmp_ecs_types.length == 1) {
469 tmp_ecs_types=""+tmp_ecs_types+jd[i]+" "
473 tmp_ecs_types="error response"
475 ecs_types = tmp_ecs_types
477 clearFlag("ecs_types")
479 if (checkFunctionFlag("ecs_producers")) {
480 getSimCtr(LOCALHOST+ECS_PORT+"/ei-producer/v1/eiproducers", 0, function(data, index) {
481 var tmp_ecs_producers="-"
483 var jd=JSON.parse(data);
484 var tmp_ecs_producer_arr=new Array(jd.length)
485 for(var i=0;i<jd.length;i++) {
486 if (tmp_ecs_producers.length == 1) {
489 tmp_ecs_producers=""+tmp_ecs_producers+jd[i]+" "
490 tmp_ecs_producer_arr[i]=jd[i]
492 ecs_producer_arr = tmp_ecs_producer_arr
493 ecs_producers = tmp_ecs_producers
496 ecs_producers="error response"
497 ecs_producer_arr=new Array(0)
500 clearFlag("ecs_producers")
502 if (checkFunctionFlag("ecs_data")) {
504 var tmp_ecs_producer_type_arr = JSON.parse(JSON.stringify(ecs_producer_arr))
505 for(var x=0;x<tmp_ecs_producer_type_arr.length;x++) {
506 getSimCtr(LOCALHOST+ECS_PORT+"/ei-producer/v1/eiproducers/"+tmp_ecs_producer_type_arr[x], x, function(data, idx) {
507 var row=""+tmp_ecs_producer_type_arr[idx]+" : "
509 var jd=JSON.parse(data);
510 var jda=jd["supported_ei_types"]
511 for(var j=0;j<jda.length;j++) {
512 row=""+row+jda[j]["ei_type_identity"]+" "
514 tmp_ecs_producer_type_arr[idx]=row
517 tmp_ecs_producer_type_arr=new Array(0)
521 ecs_producer_type_arr = tmp_ecs_producer_type_arr
523 ecs_producer_type_arr=new Array(0)
526 var tmp_ecs_producer_jobs_arr = JSON.parse(JSON.stringify(ecs_producer_arr))
527 for(x=0;x<tmp_ecs_producer_jobs_arr.length;x++) {
528 getSimCtr(LOCALHOST+ECS_PORT+"/ei-producer/v1/eiproducers/"+tmp_ecs_producer_jobs_arr[x]+"/eijobs", x, function(data, idx) {
529 var row=""+tmp_ecs_producer_jobs_arr[idx]+" : "
531 var jd=JSON.parse(data);
532 for(var j=0;j<jd.length;j++) {
534 row=""+row+jda["ei_job_identity"]+"("+jda["ei_type_identity"]+") "
536 tmp_ecs_producer_jobs_arr[idx]=row
539 tmp_ecs_producer_jobs_arr=new Array(0)
543 ecs_producer_jobs_arr = tmp_ecs_producer_jobs_arr
545 ecs_producer_jobs_arr=new Array(0)
549 var tmp_ecs_producer_status_arr = JSON.parse(JSON.stringify(ecs_producer_arr))
550 for(x=0;x<tmp_ecs_producer_status_arr.length;x++) {
551 getSimCtr(LOCALHOST+ECS_PORT+"/ei-producer/v1/eiproducers/"+tmp_ecs_producer_status_arr[x]+"/status", x, function(data, idx) {
552 var row=""+tmp_ecs_producer_status_arr[idx]+" : "
554 var jd=JSON.parse(data);
555 row=""+row+jd["operational_state"]
556 tmp_ecs_producer_status_arr[idx]=row
559 tmp_ecs_producer_status_arr=new Array(0)
563 ecs_producer_status_arr = tmp_ecs_producer_status_arr
565 ecs_producer_status_arr=new Array(0)
567 clearFlag("ecs_data")
569 if (checkFunctionFlag("ecs_jobs")) {
570 getSimCtr(LOCALHOST+ECS_PORT+"/A1-EI/v1/eijobs", 0, function(data, index) {
572 var jd=JSON.parse(data);
573 var tmpArr=new Array(jd.length)
574 for(var i=0;i<jd.length;i++) {
580 ecs_jobs=new Array(0)
583 clearFlag("ecs_jobs")
585 if (checkFunctionFlag("ecs_job_status")) {
587 var tmp_ecs_job_status= JSON.parse(JSON.stringify(ecs_jobs))
588 for(x=0;x<tmp_ecs_job_status.length;x++) {
589 getSimCtr(LOCALHOST+ECS_PORT+"/A1-EI/v1/eijobs/"+tmp_ecs_job_status[x]+"/status", x, function(data, idx) {
591 var jd=JSON.parse(data);
592 tmp_ecs_job_status[idx]=""+tmp_ecs_job_status[idx]+":"+jd["eiJobStatus"]
595 tmp_ecs_job_status="-"
599 ecs_job_status = tmp_ecs_job_status
603 clearFlag("ecs_job_status")
605 if (checkFunctionFlag("prodstub_stat")) {
606 getSimCtr(LOCALHOST+PRODSTUB_PORT+"/status", x, function(data, idx) {
607 var ctr2_map=new Map()
608 var ctr3_map=new Map()
611 var tmp_ps_producers=""
613 var tmp_ps_producer_type_arr=new Array()
614 var tmp_ps_producer_jobs_arr=new Array()
615 var tmp_ps_producer_delivery_arr=new Array()
620 var jp=JSON.parse(data);
621 for(var prod_name in jp) {
622 ctr2_map.set(prod_name, prod_name)
625 var row=""+prod_name+" : "
626 var rowj=""+prod_name+" : "
627 var rowd=""+prod_name+" : "
628 tmp_ps_producers += prod_name + " "
632 for(var i=0;i<ta.length;i++) {
633 ctr3_map.set(ta[i], ta[i])
636 } else if (ji == "supervision_response") {
638 } else if (ji == "supervision_counter") {
640 } else if (ji == "types") {
646 var job_data=jj[ji]["json"]
647 if (job_data != undefined) {
648 rowj += "("+job_data["ei_type_identity"]+")"
650 rowd += "("+jj[ji]["delivery_attempts"]+")"
653 tmp_ps_producer_type_arr[(ctr2-1)]=row
654 tmp_ps_producer_jobs_arr[(ctr2-1)]=rowj
655 tmp_ps_producer_delivery_arr[(ctr2-1)]=rowd
657 tmp_ps2=""+ctr2_map.size
658 tmp_ps3=""+ctr3_map.size
659 for(const [key, value] of ctr3_map.entries()) {
660 tmp_ps_types += key + " "
664 ps_producers=tmp_ps_producers
665 ps_types=tmp_ps_types
666 ps_producer_type_arr=tmp_ps_producer_type_arr
667 ps_producer_jobs_arr=tmp_ps_producer_jobs_arr
668 ps_producer_delivery_arr=tmp_ps_producer_delivery_arr
674 ps_producers="error response"
675 ps_types="error response"
676 ps_producer_type_arr=new Array()
677 ps_producer_jobs_arr=new Array()
678 ps_producer_delivery_arr=new Array()
684 clearFlag("prodstub_stat")
687 fetchAllMetrics_ecs();
692 function fetchAllMetrics_cr() {
694 console.log("Fetching CR DB - timer:" + refreshCount_ecs)
696 if (refreshCount_cr < 0) {
700 refreshCount_cr = refreshCount_cr - 1
704 if (checkFunctionFlag("cr_stat")) {
705 getSimCtr(LOCALHOST+CR_PORT+"/db", 0, function(data, index) {
707 cr_db=JSON.parse(data);
715 fetchAllMetrics_cr();
719 function fetchAllMetrics_rc() {
721 console.log("Fetching RC services - timer:" + refreshCount_ecs)
723 if (refreshCount_rc < 0) {
727 refreshCount_rc = refreshCount_rc - 1
731 if (checkFunctionFlag("rc_stat")) {
732 getSimCtr(LOCALHOST+RC_PORT+"/services", 0, function(data, index) {
735 var jd=JSON.parse(data);
736 for(var i=0;i<jd.length;i++) {
737 if (tmp_serv.length > 0) {
738 tmp_serv=tmp_serv+","
740 tmp_serv=tmp_serv+jd[i]["name"]
745 tmp_serv="no_response"
751 fetchAllMetrics_rc();
756 app.get("/mon3",function(req, res){
758 console.log("Creating CR DB page - timer: " + refreshCount_ecs)
760 if (refreshCount_cr < 0) {
765 var json_str=JSON.stringify(cr_db, null, 1)
766 var htmlStr = "<!DOCTYPE html>" +
769 "<meta http-equiv=\"refresh\" content=\"2\">"+ //2 sec auto refresh
770 "<title>CR DB dump</title>"+
772 "<body style=\"white-space: pre-wrap\">" +
780 app.get("/mon2",function(req, res){
782 console.log("Creating enrichment metrics - timer: " + refreshCount_ecs)
784 if (refreshCount_ecs < 0) {
786 fetchAllMetrics_ecs()
790 var summary=req.query.summary
792 if (summary == undefined) {
793 return res.redirect('/mon2?summary=false');
797 var htmlStr = "<!DOCTYPE html>" +
800 "<meta http-equiv=\"refresh\" content=\"2\">"+ //2 sec auto refresh
801 "<title>Enrichment coordinator service and producer stub</title>"+
804 "<font size=\"-3\" face=\"summary\">"
805 if (summary == "false") {
806 htmlStr=htmlStr+"<p>Set query param '?summary' to true to only show summary statistics.</p>"
808 htmlStr=htmlStr+"<p>Set query param '?summary' to false to only show full statistics</p>"
810 if (ecs_job_status.length > 10) {
811 htmlStr=htmlStr+"<div style=\"color:red\"> Avoid running the server for large number of producers and/or jobs</div>"
813 htmlStr=htmlStr+"</font>" +
814 "<h3>Enrichment Coordinator Service</h3>" +
815 "<font face=\"monospace\">" +
816 "Status:..........." + formatDataRow(ecs1) + "<br>" +
817 "Producers:........" + formatDataRow(ecs2) + "<br>" +
818 "Types:............" + formatDataRow(ecs3) + "<br>" +
819 "Jobs:............." + formatDataRow(ecs4) + "<br>" +
821 if (summary == "false") {
824 "<font face=\"monospace\">" +
825 "Producer ids:....." + formatDataRow(ecs_producers) + "<br>" +
826 "Type ids:........." + formatDataRow(ecs_types) + "<br>" +
828 for(var i=0;i<ecs_producer_type_arr.length;i++) {
829 var tmp=ecs_producer_type_arr[i]
830 if (tmp != undefined) {
831 var s = "Producer types...." + formatDataRow(ecs_producer_type_arr[i]) + "<br>"
835 htmlStr=htmlStr+"<br>";
836 for(i=0;i<ecs_producer_jobs_arr.length;i++) {
837 tmp=ecs_producer_jobs_arr[i]
838 if (tmp != undefined) {
839 s = "Producer jobs....." + formatDataRow(ecs_producer_jobs_arr[i]) + "<br>"
843 htmlStr=htmlStr+"<br>";
844 for(i=0;i<ecs_producer_status_arr.length;i++) {
845 tmp=ecs_producer_status_arr[i]
846 if (tmp != undefined) {
847 s = "Producer status..." + formatDataRow(tmp) + "<br>"
851 htmlStr=htmlStr+"<br>";
852 for(i=0;i<ecs_job_status.length;i++) {
853 tmp=ecs_job_status[i]
854 if (tmp != undefined) {
855 s = padding("Job", 18, ".") + formatDataRow(tmp) + "<br>"
859 htmlStr=htmlStr+"<br>"+"<br>" +
864 "<h3>Producer stub</h3>" +
865 "<font face=\"monospace\">" +
866 "Producers:........" + formatDataRow(ps2) + "<br>" +
867 "Types:............" + formatDataRow(ps3) + "<br>" +
868 "Jobs:............." + formatDataRow(ps4) + "<br>" +
870 if (summary == "false") {
873 "<font face=\"monospace\">" +
874 "Producer ids:....." + formatDataRow(ps_producers) + "<br>" +
875 "Type ids:........." + formatDataRow(ps_types) + "<br>" +
877 for(i=0;i<ps_producer_type_arr.length;i++) {
878 tmp=ps_producer_type_arr[i]
879 if (tmp != undefined) {
880 s = "Producer types...." + formatDataRow(ps_producer_type_arr[i]) + "<br>"
884 htmlStr=htmlStr+"<br>";
885 for(i=0;i<ps_producer_jobs_arr.length;i++) {
886 tmp=ps_producer_jobs_arr[i]
887 if (tmp != undefined) {
888 s = "Producer jobs....." + formatDataRow(ps_producer_jobs_arr[i]) + "<br>"
892 htmlStr=htmlStr+"<br>";
893 for(i=0;i<ps_producer_delivery_arr.length;i++) {
894 tmp=ps_producer_delivery_arr[i]
895 if (tmp != undefined) {
896 s = "Producer delivery." + formatDataRow(ps_producer_delivery_arr[i]) + "<br>"
908 // Monitor for policy management
909 app.get("/mon",function(req, res){
911 console.log("Creating policy metrics page " + refreshCount_pol)
913 if (refreshCount_pol < 0) {
915 fetchAllMetrics_pol()
919 if (refreshCount_rc < 0) {
925 var bn=req.query.basename
927 if (bn == undefined) {
929 return res.redirect('/mon?basename=ricsim');
935 var htmlStr = "<!DOCTYPE html>" +
938 "<meta http-equiv=\"refresh\" content=\"2\">"+ //2 sec auto refresh
939 "<title>Policy Agent and simulator monitor</title>"+
942 "<font size=\"-3\" face=\"monospace\">" +
943 "<p>Change basename in url if other ric sim prefix is used</p>" +
945 "<h3>Policy agent</h3>" +
946 "<font face=\"monospace\">" +
947 "Status:..............................." + formatDataRow(ag1) + "<br>" +
948 "Services:............................." + formatIdRowCompact(ag2) + "<br>" +
949 "Types:................................" + formatIdRowCompact(ag3) + "<br>" +
950 "Number of instances:.................." + formatDataRow(ag4) + "<br>" +
951 "Near-RT RICs:........................." + formatDataRow(ag5) + "<br>" +
953 "<h3>MR Stub interface</h3>" +
954 "<font face=\"monospace\">"+
955 "Submitted requests:............................" + formatDataRow(mr1) + "<br>" +
956 "Fetched requests:.............................." + formatDataRow(mr2) + "<br>" +
957 "Current requests waiting:......................" + formatDataRow(mr3) + "<br>" +
958 "Submitted responses:..........................." + formatDataRow(mr4) + "<br>" +
959 "Fetched responses.............................." + formatDataRow(mr5) + "<br>" +
960 "Current responses waiting......................" + formatDataRow(mr6) + "<br>" +
962 "<h3>Callback receiver</h3>" +
963 "<font face=\"monospace\">" +
964 "Callbacks received:..................." + formatDataRow(cr1) + "<br>" +
965 "Callbacks fetched:...................." + formatDataRow(cr2) + "<br>" +
966 "Number of waiting callback messages:.." + formatDataRow(cr3) + "<br>" +
968 "<h3>R-APP Catalogue</h3>" +
969 "<font face=\"monospace\">" +
970 "Services:............................." + formatIdRowCompact(rc_services) + "<br>" +
972 "<h3>Near-RT RIC Simulators</h3>" +
973 "<font face=\"monospace\">"
975 htmlStr=htmlStr+padding("Near-RT RIC Simulator name", 35," ")
976 htmlStr=htmlStr+padding("Types", 10," ")
977 htmlStr=htmlStr+padding("Instances", 12," ")
978 htmlStr=htmlStr+padding("Data delivery", 12," ")+"<br>"
979 htmlStr=htmlStr+padding("",70,"=")+"<br>"
980 for(var simIndex=0;simIndex<simnames.length;simIndex++) {
981 htmlStr=htmlStr+padding(simnames[simIndex]+ " ("+simports[simIndex]+")",35," ");
982 htmlStr=htmlStr+padding(simvar2[simIndex],10," ")
983 htmlStr=htmlStr+padding(simvar1[simIndex],12 ," ")
984 htmlStr=htmlStr+padding(simvar6[simIndex],12," ")
985 htmlStr=htmlStr+"<br>";
988 htmlStr=htmlStr+"<br>";
989 htmlStr=htmlStr+padding("Near-RT RIC Simulator name", 35," ")
990 htmlStr=htmlStr+padding("Version", 20," ")
991 htmlStr=htmlStr+padding("Type-IDs", 10," ")+"<br>"
992 htmlStr=htmlStr+padding("",65,"=")+"<br>"
993 for(simIndex=0;simIndex<simnames.length;simIndex++) {
994 htmlStr=htmlStr+padding(simnames[simIndex]+ " ("+simports[simIndex]+")",35," ");
995 htmlStr=htmlStr+padding(simvar4[simIndex],20," ")
996 htmlStr=htmlStr+padding(formatIdRowCompact(simvar3[simIndex]),10," ")
997 htmlStr=htmlStr+"<br>";
1000 htmlStr=htmlStr+"<br>";
1001 htmlStr=htmlStr+padding("Near-RT RIC Simulator name", 35," ")
1002 htmlStr=htmlStr+padding("Remote hosts", 50," ")+"<br>"
1003 htmlStr=htmlStr+padding("",90,"=")+"<br>"
1004 for(simIndex=0;simIndex<simnames.length;simIndex++) {
1005 htmlStr=htmlStr+padding(simnames[simIndex]+ " ("+simports[simIndex]+")",35," ");
1006 htmlStr=htmlStr+padding(simvar5[simIndex],50," ")
1007 htmlStr=htmlStr+"<br>";
1016 var httpServer = http.createServer(app);
1018 httpServer.listen(httpPort);
1019 console.log("Simulator monitor listening (http) at "+httpPort);
1020 console.log("Open the web page on localhost:9999/mon to view the policy statistics page.")
1021 console.log("Open the web page on localhost:9999/mon2 to view the enrichment statistics page.")
1022 console.log("Open the web page on localhost:9999/mon3 to view CR DB in json.")