diff --git a/LICENSE b/LICENSE new file mode 100644 index 0000000000000000000000000000000000000000..367b5165b80deeacb4bd3a43b75a7909570cbea7 --- /dev/null +++ b/LICENSE @@ -0,0 +1,25 @@ +ETSI Software License + +As long as the hereunder conditions are respected, non-exclusive permission is +hereby granted, free of charge, to use, reproduce and modify this software +source code, under the following conditions: + +- This source code is provided “AS IS” with no warranties, express or implied, + including but not limited to, the warranties of merchantability, fitness for + a particular purpose and warranties for non-infringement of intellectual + property rights. ETSI shall not be held liable in any event for any direct or + indirect damages whatsoever (including, without limitation, damages for loss + of profits, business interruption, loss of information, or any other pecuniary + loss) arising out of or related to the use of or inability to use the + source code. + +- This permission is granted to facilitate the implementation of the related + ETSI standard, provided that ETSI is given the right to use, reproduce and + amend the modified source code under the same conditions as the + present permission. + +- This permission does not apply to any documentation associated with this + source code for which ETSI keeps all rights reserved. + +The present ETSI Source Code license shall be included in all copies of whole +or part of this source code and shall not imply any sub-license right. diff --git a/TODO.md b/TODO.md index e3f9a2f50d441a9581a78d7d6b946eaa72f1d29a..8ff1e43b4586c4f1d62a1fe1e722ec8bca77e527 100644 --- a/TODO.md +++ b/TODO.md @@ -21,6 +21,14 @@ This file provides the list of the TODOs related to the STF 569. ### RNIS +Draft ETSI GS MEC 012 2.0.4 + +https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/RNIS/RnisSpecificSubscription_BV.tplan2 +https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/RNIS/RnisSpecificSubscription_BV.tplan2 + +- TC_MEC_SRV_RNIS_011_OK To be tested +- TC_MEC_SRV_RNIS_012_OK To be tested + ### SAQ ### SRVSUB @@ -29,18 +37,39 @@ This file provides the list of the TODOs related to the STF 569. ### TRAF +Draft ETSI GS MEC 011 V2.0.9 (2018-10) + +https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/remove-401s/Test%20Purposes/SRV/TRAF/PlatTrafficRules.tplan2 + +- TC_MEC_SRV_TRANS_001_OK To be tested +- TC_MEC_SRV_TRAF_001_OK To be tested +- TC_MEC_SRV_TRAF_002_OK To be tested +- TC_MEC_SRV_TRAF_003_OK To be tested +- TC_MEC_SRV_TRAF_001_NF To be tested + ### TRANS +Draft ETSI GS MEC 011 V2.0.9 (2018-10) + +https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/remove-401s/Test%20Purposes/SRV/TRANS/PlatTransport.tplan2 + +- TP_MEC_SRV_TRAF_001_OK To be tested + ### UEAREASUB +Draft ETSI GS MEC 013 V2.0.3 (2018-10) + +https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/remove-401s/Test%20Purposes/SRV/UEDISTSUB/PlatUeAreaSubscription.tplan2 + +TODO CircleNotificationSubscription data structure not found + ### UEDISTLOOK Draft ETSI GS MEC 013 V2.0.3 (2018-10) -https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/remove-401s/Test%20Purposes/SRV/UEDISTSUB/PlatUeDistanceSubscription.tplan2 - -TODO TerminalDistance data structure not found +https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/remove-401s/Test%20Purposes/SRV/UEDISTLOOK/PlatUeDistanceSubscription.tplan2 +TODO TerminalDistance data structure not found ### UEDISTSUB @@ -50,7 +79,6 @@ https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/remove-401s/Test%20 TODO DistanceNotificationSubscription data structure not found - ### UEINFLOOK Draft ETSI GS MEC 013 V2.0.3 (2018-10) diff --git a/ccsrc/Protocols/Json/json_codec.cc b/ccsrc/Protocols/Json/json_codec.cc index fad5c14590871ea60ece9e5f842612784ba3f0f0..d1759cebe25cc1317dd99f9b717de481ef4e741e 100644 --- a/ccsrc/Protocols/Json/json_codec.cc +++ b/ccsrc/Protocols/Json/json_codec.cc @@ -24,6 +24,10 @@ int json_codec::encode (const LibItsHttp__JsonMessageBodyTypes::JsonBody& msg, O const LocationAPI__TypesAndValues::UserTrackingSubscription& user_tracking_subscription = msg.userTrackingSubscription(); user_tracking_subscription.encode(LocationAPI__TypesAndValues::UserTrackingSubscription_descr_, encoding_buffer, TTCN_EncDec::CT_JSON); data = char2oct(CHARSTRING("{\"userTrackingSubscription\": ")) + OCTETSTRING(encoding_buffer.get_len(), encoding_buffer.get_data()) + char2oct(CHARSTRING("}")); + } else if (msg.ischosen(LibItsHttp__JsonMessageBodyTypes::JsonBody::ALT_cellChangeSubscription)) { + const RnisAPI__TypesAndValues::CellChangeSubscription& cell_change_subscription = msg.cellChangeSubscription(); + cell_change_subscription.encode(RnisAPI__TypesAndValues::CellChangeSubscription_descr_, encoding_buffer, TTCN_EncDec::CT_JSON); + data = char2oct(CHARSTRING("{\"CellChangeSubscription\": ")) + OCTETSTRING(encoding_buffer.get_len(), encoding_buffer.get_data()) + char2oct(CHARSTRING("}")); } else { loggers::get_instance().error("json_codec::encode: Not supported"); } @@ -58,21 +62,26 @@ int json_codec::decode (const OCTETSTRING& p_data, LibItsHttp__JsonMessageBodyTy // ..and create the decoding buffer TTCN_Buffer decoding_buffer(OCTETSTRING(str.length(), (const unsigned char*)str.c_str())); - if (it->second.find("\"userList\"") != std::string::npos) { // Be carefull to the order - // TODO To be refined, find("\"userList\"") is not optimal + if (it->second.find("\"userList\"") != std::string::npos) { // Be careful to the order + // TODO To be refined, find("\"userList\"") is not optimal LocationAPI__TypesAndValues::UserList user_list; user_list.decode(LocationAPI__TypesAndValues::UserList_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); msg.userList() = user_list; - } else if (it->second.find("\"accessPointList\"") != std::string::npos) { // Be carefull to the order - // TODO To be refined, find("\"accessPointList\"") is not optimal + } else if (it->second.find("\"accessPointList\"") != std::string::npos) { // Be careful to the order + // TODO To be refined, find("\"accessPointList\"") is not optimal LocationAPI__TypesAndValues::AccessPointList access_point_list; access_point_list.decode(LocationAPI__TypesAndValues::AccessPointList_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); msg.accessPointList() = access_point_list; - } else if (it->second.find("\"SubscriptionLinkList\"") != std::string::npos) { // Be carefull to the order - // TODO To be refined, find("\"accessPointList\"") is not optimal + } else if (it->second.find("\"SubscriptionLinkList\"") != std::string::npos) { // Be careful to the order + // TODO To be refined, find("\"accessPointList\"") is not optimal RnisAPI__TypesAndValues::SubscriptionLinkList subscription_link_list; subscription_link_list.decode(RnisAPI__TypesAndValues::SubscriptionLinkList_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); msg.subscriptionLinkList() = subscription_link_list; + } else if (it->second.find("\"transportInfoList\"") != std::string::npos) { // Be careful to the order + // TODO To be refined, find("\"accessPointList\"") is not optimal + AppEnablementAPI__TypesAndValues::TransportInfoList transport_info_list; + transport_info_list.decode(AppEnablementAPI__TypesAndValues::TransportInfoList_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); + msg.transportInfoList() = transport_info_list; } else if (it->second.find("\"userTrackingSubscription\"") != std::string::npos) { LocationAPI__TypesAndValues::UserTrackingSubscription user_tracking_subscription; user_tracking_subscription.decode(LocationAPI__TypesAndValues::UserTrackingSubscription_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); @@ -85,6 +94,23 @@ int json_codec::decode (const OCTETSTRING& p_data, LibItsHttp__JsonMessageBodyTy UEidentityAPI__TypesAndValues::UeIdentityTagInfo ue_identity_tag_info; ue_identity_tag_info.decode(UEidentityAPI__TypesAndValues::UeIdentityTagInfo_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); msg.ueIdentityTagInfo() = ue_identity_tag_info; + } else if (it->second.find("\"trafficRule\"") != std::string::npos) { + AppEnablementAPI__TypesAndValues::TrafficRule traffic_rule; + traffic_rule.decode(AppEnablementAPI__TypesAndValues::TrafficRule_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); + msg.trafficRule() = traffic_rule; + } else if (it->second.find("\"CellChangeSubscription\"") != std::string::npos) { + RnisAPI__TypesAndValues::CellChangeSubscription cell_change_subscription; + cell_change_subscription.decode(RnisAPI__TypesAndValues::CellChangeSubscription_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); + msg.cellChangeSubscription() = cell_change_subscription; + //TODO Continue with other ChangeSubscription + } else if (it->second.find("\"RabInfo\"") != std::string::npos) { + RnisAPI__TypesAndValues::RabInfo rab_info; + rab_info.decode(RnisAPI__TypesAndValues::RabInfo_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); + msg.rabInfo() = rab_info; + } else if (it->second.find("\"PlmnInfo\"") != std::string::npos) { + RnisAPI__TypesAndValues::PlmnInfo plmn_info; + plmn_info.decode(RnisAPI__TypesAndValues::PlmnInfo_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); + msg.plmnInfo() = plmn_info; } else if (it->second.find("\"bwInfo\"") != std::string::npos) { BwManagementAPI__TypesAndValues::BwInfo bw_info; @@ -105,9 +131,17 @@ int json_codec::decode (const OCTETSTRING& p_data, LibItsHttp__JsonMessageBodyTy bw_info.decode(BwManagementAPI__TypesAndValues::BwInfo_descr_, decoding_buffer_, TTCN_EncDec::CT_JSON); msg.bwInfo() = bw_info; } else if (it->second.find("\"problemDetails\"") != std::string::npos) { // TODO To be refined, problemDetails in different modules - UEidentityAPI__TypesAndValues::ProblemDetails problem_details; - problem_details.decode(UEidentityAPI__TypesAndValues::ProblemDetails_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); - msg.problemDetails__ue__identity() = problem_details; + + +// UEidentityAPI__TypesAndValues::ProblemDetails problem_details; +// problem_details.decode(UEidentityAPI__TypesAndValues::ProblemDetails_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); +// msg.problemDetails__ue__identity() = problem_details; + + RnisAPI__TypesAndValues::ProblemDetails problem_details; + problem_details.decode(RnisAPI__TypesAndValues::ProblemDetails_descr_, decoding_buffer, TTCN_EncDec::CT_JSON); + msg.problemDetails__rni() = problem_details; + + } else { loggers::get_instance().warning("json_codec::decode: Unsupported variant"); return -1; diff --git a/docker/Dockerfile b/docker/Dockerfile index 03766bb0d44c4d95bef02f0923b2bd0b6d7accbb..6d8506884899db1a827dfed6e9b80d2916c81af3 100644 --- a/docker/Dockerfile +++ b/docker/Dockerfile @@ -37,6 +37,7 @@ RUN DEBIAN_FRONTEND=noninteractive apt-get update \ libssl-dev \ libtool-bin \ libtool \ + libwebsockets-dev \ libwireshark-dev \ libxml2-dev \ lsof \ @@ -87,9 +88,9 @@ RUN cd /home/etsi \ # Seems that COPY does not work as expected, to be investaged #==> Fallback to more secured solution -#COPY [^.]* /home/etsi/dev/STF569_Mec/ +ADD . /home/etsi/dev/STF569_Mec #COPY home home/etsi -RUN git clone https://forge.etsi.org/gitlab/mec/gs032p3-ttcn-test-suite.git /home/etsi/dev/STF569_Mec +# RUN git clone https://forge.etsi.org/gitlab/mec/gs032p3-ttcn-test-suite.git /home/etsi/dev/STF569_Mec RUN chown -R etsi /home/etsi/dev/STF569_Mec/ && cd /home/etsi/dev/STF569_Mec USER etsi @@ -107,8 +108,6 @@ RUN cd /home/etsi/frameworks \ && rm -f ./eclipse-cpp-photon-R-linux-gtk-x86_64.tar.gz \ && cd /home/etsi/dev/STF569_Mec \ && cd /home/etsi/dev/STF569_Mec/ttcn \ - && git clone https://forge.etsi.org/gitlab/LIBS/LibSip.git ./LibSip \ - && git clone https://forge.etsi.org/gitlab/LIBS/LibIms.git ./LibIms \ && git clone https://forge.etsi.org/gitlab/LIBS/LibCommon.git ./LibCommon \ && git clone -bSTF525 https://forge.etsi.org/gitlab/LIBS/LibIts ./LibIts \ && cd /home/etsi/dev/STF569_Mec/ttcn/LibIts \ diff --git a/docker/build-container.sh b/docker/build-container.sh index 1425fa30d0f0150151a93b242ea67aac270a50d8..be8c683f7b5e7fac52c09f413b732b6ff3dd030e 100755 --- a/docker/build-container.sh +++ b/docker/build-container.sh @@ -3,20 +3,25 @@ # See: https://forge.etsi.org/etsi-forge-copyright-statement.txt #set -e -#set -vx +set -vx DOCKER_FILE=./docker/Dockerfile if [ -f ${DOCKER_FILE} ] then - docker rm --force stf569_Mec - docker build --tag stf569_Mec --force-rm -f ${DOCKER_FILE} . + #check and build stf569_mec image + DOCKER_ID=`docker ps -a | grep -e stf569_mec | awk '{ print $1 }'` + if [ ! -z "${DOCKER_ID}" ] + then + docker rm --force stf569_mec + fi + docker build --tag stf569_mec --force-rm -f ${DOCKER_FILE} . if [ "$?" != "0" ] then echo "Docker build failed: $?" exit -1 fi docker image ls -a - docker inspect stf569_Mec:latest + docker inspect stf569_mec:latest if [ "$?" != "0" ] then echo "Docker inspect failed: $?" diff --git a/docker/run-container.sh b/docker/run-container.sh index 4b41de3b9b04b5a4d9ac9c0d723eff6e8a5fe59a..9ad8ae98d817f77b3275ebaabc16e26ef896f832 100755 --- a/docker/run-container.sh +++ b/docker/run-container.sh @@ -5,9 +5,9 @@ #set -e #set -vx -docker run stf569_Mec:latest "/bin/bash" \ +docker run stf569_mec:latest "/bin/bash" \ -c "source /home/etsi/devenv.bash \ - && cd /home/etsi/dev/etsi_emcom/src/AtsMec/objs \ + && cd /home/etsi/dev/etsi_mec/src/AtsMec/objs \ && ../bin/run_all.bash \ && ls -ltr ../logs" diff --git a/etc/AtsMec/AtsMec.cfg b/etc/AtsMec/AtsMec.cfg index 879f749492f849c7be662efee95d33a244abf0cd..72661f999429d9660be7eb07fa7148a66c920270 100644 --- a/etc/AtsMec/AtsMec.cfg +++ b/etc/AtsMec/AtsMec.cfg @@ -7,21 +7,27 @@ LibCommon_Time.PX_TAC := 30.0 LibCommon_Sync.PX_TSYNC_TIME_LIMIT := 30.0; LibCommon_Sync.PX_TSHUT_DOWN_TIME_LIMIT := 30.0; -LibItsHttp_Pics.PICS_HEADER_HOST := "172.28.4.87" +LibItsHttp_Pics.PICS_HEADER_HOST := "192.168.56.1" +#LibItsHttp_Pics.PICS_HEADER_HOST := "172.28.4.87" #LibItsHttp_Pics.PICS_HEADER_HOST := "192.168.0.17" LibItsHttp_Pics.PICS_HEADER_CONTENT_TYPE := "application/json" -LibMec_Pics.PICS_MEC_PLAT := true -LibMec_Pics.PICS_SERVICES := true -LibMec_Pics.PICS_RNIS := false +LibMec_Pics.PICS_MEC_PLAT := true +LibMec_Pics.PICS_SERVICES := true +LibMec_Pics.PICS_RNIS := true +LibMec_Pics.PICS_RNIS_QUERY := true +LibMec_Pics.PICS_RNIS_ALL_SUBSCRIPTIONS := true LocationAPI_Pics.PICS_LOCATION_API_SUPPORTED := false -UEidentityAPI_Pics.PICS_UE_IDENTITY_API_SUPPORTED := true +UEidentityAPI_Pics.PICS_UE_IDENTITY_API_SUPPORTED := false BwManagementAPI_Pics.PICS_BWMANAGEMENT_API_SUPPORTED := false +AppEnablementAPI_Pics.PICS_ENABLE_APP_API_SUPPORTED := true + + [LOGGING] # In this section you can specify the name of the log file and the classes of events # you want to log into the file or display on console (standard error). @@ -38,7 +44,7 @@ LogEventTypes:= Yes [TESTPORT_PARAMETERS] # In this section you can specify parameters that are passed to Test Ports. -system.httpPort.params := "HTTP(codecs=json:json_codec)/TCP(debug=1,server=172.28.4.87,port=8081,use_ssl=0)" +system.httpPort.params := "HTTP(codecs=json:json_codec)/TCP(debug=1,server=192.168.56.1,port=8081,use_ssl=0)" [DEFINE] # In this section you can create macro definitions, @@ -69,7 +75,7 @@ system.httpPort.params := "HTTP(codecs=json:json_codec)/TCP(debug=1,server=172.2 #AtsMec_UEidentityAPI_TestCases.TC_MEC_SRV_UETAG_001_NF #AtsMec_UEidentityAPI_TestCases.TC_MEC_SRV_UETAG_002_OK #AtsMec_UEidentityAPI_TestCases.TC_MEC_SRV_UETAG_002_BR -AtsMec_UEidentityAPI_TestCases.TC_MEC_SRV_UETAG_002_PF +#AtsMec_UEidentityAPI_TestCases.TC_MEC_SRV_UETAG_002_PF #AtsMec_UEidentityAPI_TestCases.TC_MEC_SRV_UELOC_001_OK #AtsMec_UEidentityAPI_TestCases.TC_MEC_SRV_UELOC_001_BR @@ -94,6 +100,17 @@ AtsMec_UEidentityAPI_TestCases.TC_MEC_SRV_UETAG_002_PF #AtsMec_LocationAPI_TestCases.TC_MEC_SRV_UEINFSUB_002_OK #AtsMec_LocationAPI_TestCases.TC_MEC_SRV_UEINFSUB_002_NF +#AtsMec_RnisAPI_TestCases.TC_MEC_SRV_RNIS_011_OK +#AtsMec_RnisAPI_TestCases.TC_MEC_SRV_RNIS_012_OK +#AtsMec_RnisAPI_TestCases.TC_MEC_SRV_RNIS_011_BR +#AtsMec_RnisAPI_TestCases.TC_MEC_SRV_RNIS_012_BR +AtsMec_RnisAPI_TestCases.TC_MEC_SRV_RNIS_016_OK + +#AtsMec_AppEnablementAPI_TestCases.TC_MEC_SRV_TRANS_001_OK +#AtsMec_AppEnablementAPI_TestCases.TC_MEC_SRV_TRAF_001_OK +#AtsMec_AppEnablementAPI_TestCases.TC_MEC_SRV_TRAF_002_OK +#AtsMec_AppEnablementAPI_TestCases.TC_MEC_SRV_TRAF_001_NF + [GROUPS] # In this section you can specify groups of hosts. These groups can be used inside the # [COMPONENTS] section to restrict the creation of certain PTCs to a given set of hosts. diff --git a/simu/data/security.csv b/simu/data/security.csv new file mode 100644 index 0000000000000000000000000000000000000000..0347ad324659fd88381d08aa6b8652ed1539be26 --- /dev/null +++ b/simu/data/security.csv @@ -0,0 +1,2 @@ +id,grantTypes,tokenEndpoint +security0,OAUTH2_CLIENT_CREDENTIALS,/meMp1/security/TokenEndPoint diff --git a/simu/data/traffic_rules.csv b/simu/data/traffic_rules.csv new file mode 100644 index 0000000000000000000000000000000000000000..7bb9d8f09d15b84d3b81b62a64d14c417fe6476d --- /dev/null +++ b/simu/data/traffic_rules.csv @@ -0,0 +1 @@ +trafficRuleId,filterType,priority,trafficFilter,action,dstInterface,state diff --git a/simu/data/transport_info.csv b/simu/data/transport_info.csv new file mode 100644 index 0000000000000000000000000000000000000000..e5f71de4e0006b8e8e5d10149ea55fdb3114001e --- /dev/null +++ b/simu/data/transport_info.csv @@ -0,0 +1,2 @@ +transportId,name,description,type,protocol,version,endpoint,security,implSpecificInfo +TransId12345,REST,REST API,REST_HTTP,HTTP,2.0,{},security0,{} diff --git a/simu/data/ue_information_list.csv b/simu/data/ue_information_list.csv index fbd902cbd9072dd2ab7df011783833d7346bfda7..fae914230902eb231ba6549c8405e215f73346e0 100644 --- a/simu/data/ue_information_list.csv +++ b/simu/data/ue_information_list.csv @@ -1,6 +1,6 @@ appInst,ueTag,address,state appInst01,UeTagA,acr:192.0.0.1,UNREGISTERED -appInst01,UeTagC,acr:192.0.0.3,UNREGISTERED +appInst01,UeTagC,acr:192.0.0.3,INVALID_STATE appInst02,UeTagB,acr:192.0.0.2,UNREGISTERED appInst03,UeTagD,acr:192.0.0.4,UNREGISTERED appInst03,UeTagE,acr:192.0.0.5,UNREGISTERED diff --git a/simu/mec_database.py b/simu/mec_database.py index c4f5ce5c3eb10e034b8f75aa9e4f952ed16b8ff5..9fb2cda0a7bc1f1e4aec53c1470717bd37aa08b9 100644 --- a/simu/mec_database.py +++ b/simu/mec_database.py @@ -15,6 +15,9 @@ class mec_database: __cells__ = None __associated__ = None __subscribions__ = None + __transport_info__ = None + __security__ = None + __traffic_rules__ = None def __init__(self): """ Default ctor: Open Pandas database. """ @@ -26,7 +29,10 @@ class mec_database: self.__cells__ = pd.DataFrame(pd.read_csv(self.__path__ + 'cells.csv', encoding = 'utf-8', index_col = 'cellId')) self.__associated__ = pd.DataFrame(pd.read_csv(self.__path__ + 'associated.csv', encoding = 'utf-8', index_col = 'cellId')) self.__subscriptions__ = pd.DataFrame(pd.read_csv(self.__path__ + 'subscriptions.csv', encoding = 'utf-8', index_col = 'subscription_id')) - #self.dump() + self.__transport_info__ = pd.DataFrame(pd.read_csv(self.__path__ + 'transport_info.csv', encoding = 'utf-8', index_col = 'transportId')) + self.__security__ = pd.DataFrame(pd.read_csv(self.__path__ + 'security.csv', encoding = 'utf-8', index_col = 'id')) + self.__traffic_rules__ = pd.DataFrame(pd.read_csv(self.__path__ + 'traffic_rules.csv', encoding = 'utf-8', index_col = 'trafficRuleId')) +# self.dump() # End of __init__ def dump(self): @@ -38,7 +44,10 @@ class mec_database: print("LocationInfo: ", self.__location_info__.head()) print("Cells: ", self.__cells__.head()) print("Associated: ", self.__associated__.head()) - print("subscriptions: ", self.__subscribions__.head()) + print("subscriptions: ", self.__subscriptions__.head()) + print("transport_info: ", self.__transport_info__.head()) + print("security: ", self.__security__.head()) + print("traffic_rules: ", self.__traffic_rules__.head()) # End of dump def __to_accessPoint__(self, p_access_point, p_location): @@ -106,6 +115,53 @@ class mec_database: return resp # End of __to_subscriptions__ + def __to_transport_info__(self, p_transport_info): + """ + Build a TransportInfo Json message. + Keyword arguments: + -- p_transport_info: TransportInfo description + """ + print(">>> __to_transport_info__: ", p_transport_info) +# print("__to_transport_info__: security id: ", p_transport_info[7]) + resp = "{{\t\"id\": \"TransId12345\",\"name\": \"REST\",\"description\": \"REST API\",\"type\": \"REST_HTTP\",\"protocol\": \"HTTP\",\"version\": \"2.0\",\"endpoint\": {},\"security\": {\"oAuth2Info\": {\"grantTypes\": [\"OAUTH2_CLIENT_CREDENTIALS\"],\"tokenEndpoint\": \"/meMp1/security/TokenEndPoint\"}\"},\"implSpecificInfo\": {}}" +# resp = None +# try: +# security = self.__security__.loc[self.__security__['id'] == p_transport_info[7]] +# print("__to_transport_info__: security= ", security) +# +# resp = "{\t\"id\": \"" + p_transport_info[0] + "\",\t\"name\": \"" + p_transport_info[1] + "\",\t\"description\": \"" + p_transport_info[2] + "\",\t\"type\": \"" + p_transport_info[3] + "\",\t\"protocol\": \"" + p_transport_info[4] + "\",\t\"version\": \"" + str(p_transport_info[5]) + "\",\t\"endpoint\": \"" + p_transport_info[6] + "\",\t\"security\": \"" + security + "\",\t\"implSpecificInfo\": \"" + p_transport_info[8] + "\"}" +# print("__to_transport_info__: ", resp) +# except KeyError: +# print("__to_transport_info__: No security entry") + return resp + # End of method __to_transport_info__ + + def __to_traffic_rule__(self, p_traffic_rule): + """ + Build a TrafficRule Json message. + Keyword arguments: + -- p_traffic_rule: TrafficRule description + """ + print(">>> __to_traffic_rule__: ", p_traffic_rule) + resp = "{\"trafficRuleId\": \"TrafficRule1\",\"filterType\": \"FLOW\",\"priority\": 1,\"trafficFilter\": [{\"srcAddress\": [\"192.168.1.1\"],\"dstAddress\": [\"192.168.1.1\"],\"srcPort\": [\"8080\"],\"dstPort\": [\"8080\"],\"protocol\": [ \"?\"],\"token\": [\"?\"],\"srcTunnelAddress\": [\"?\"],\"tgtTunnelAddress\": [\"?\"],\"srcTunnelPort\": [\"?\"],\"dstTunnelPort\": [\"?\"],\"qCI\": 1,\"dSCP\": 0,\"tC\": 1}],\"action\": \"DROP\",\"dstInterface\": {\"interfaceType\": \"TUNNEL\",\"tunnelInfo\": {\"tunnelType\": \"GTP_U\",\"tunnelDstAddress\": \"?\",\"tunnelSrcAddress\": \"?\"},\"srcMacAddress\": \"02-00-00-00-00-00\",\"dstMacAddress\": \"02-00-00-00-00-00\",\"dstIpAddress\":\"192.0.2.0\"},\"state\":\"ACTIVE\"}" +# resp = None +# try: +# resp = "{\t\"id\": \"" + p_transport_info[0] + "\",\t\"name\": \"" + p_transport_info[1] + "\",\t\"description\": \"" + p_transport_info[2] + "\",\t\"type\": \"" + p_transport_info[3] + "\",\t\"protocol\": \"" + p_transport_info[4] + "\",\t\"version\": \"" + str(p_transport_info[5]) + "\",\t\"endpoint\": \"" + p_transport_info[6] + "\",\t\"security\": \"" + security + "\",\t\"implSpecificInfo\": \"" + p_transport_info[8] + "\"}" +# print("__to_transport_info__: ", resp) +# except KeyError: +# print("__to_transport_info__: No security entry") + return resp + # End of method __to_transport_info__ + + def __to_rni_subscriptions__(self, p_subscription, p_subscription_type): + """ Build a RNI subscription Json message. """ + print(">>> __to_rni_subscriptions__") + resp = "{\"CellChangeSubscription\": {\"subscriptionType\": \"" + p_subscription_type + "\",\"callbackReference\": \"http://meAppClient.example.com/rni/v2/notifications/cell_change/77777\", \"_links\": {\"self\": \"http://example.com/exampleAPI/rni/v2/subscriptions\"}, \"filterCriteria\": {\"appInsId\": \"01\", \"associateId\": [{\"type\": \"UE_IPV4_ADDRESS\", \"value\": 1}], \"plmn\": {\"mcc\": \"01\", \"mnc\": \"001\"}, \"cellId\": [\"0x800000A\"], \"hoStatus\": \"COMPLETED\"}, \"expiryDeadline\": {\"seconds\": 1577836800, \"nanoSeconds\": 0}}}" +# resp = "{\"CellChangeSubscription\": {\"callbackReference\": " + p_subscription['callbackReference'] + ", \"_links\": {\"self\": " + p_subscription['_links'] + "}, \"filterCriteria\": {\"appInsId\": " + p_subscription['filterCriteria']['appInsId'] + ", \"associateId\": [{\"type\": " + p_subscription['filterCriteria']['associateId']['type'] + ", \"value\": " + p_subscription['filterCriteria']['associateId']['value'] + "}], \"plmn\": {\"mcc\": " + p_subscription['filterCriteria']['plmn']['mcc'] + ", \"mnc\": " + p_subscription['filterCriteria']['plmn']['mnc'] + "}, \"cellId\": [" + p_subscription['filterCriteria']['cellId'] + "], 'hoStatus': " + p_subscription['filterCriteria']['hoStatus'] + "}, \"expiryDeadline\": {\"seconds\": " + p_subscription['expiryDeadline']['seconds'] + ", \"nanoSeconds\": \"" + p_subscription['expiryDeadline']['nanoSeconds'] + "}}" + print("__to_rni_subscriptions__: ", resp) + return resp + # end of __to_rni_subscriptions__ + def getSubscriberList(self, p_uri): """ Build a SubscriberList Json message. """ print(">>> getSubscriberList") @@ -145,7 +201,6 @@ class mec_database: print(">>> getAccessPointList") resp = None try: - r = self.__access_point_list__.loc[self.__access_point_list__['zoneId'] == p_zone_id] print("getAccessPointList: r= ", r) resp = "{\"accessPointList\": {\t\"zoneId\": \"" + p_zone_id + "\",\t\"accessPoint\": [\t" @@ -163,9 +218,61 @@ class mec_database: # End of method getAccessPointList def getSubscriptionLinkList(self, p_uri): - return "{\"SubscriptionLinkList\": {\"_links\": {\"self\": \"http://example.com" + p_uri + "\"},\"subscription\": [{\"href\": \"http://meAppClient.example.com/rni/v1/notifications/cell_change/77777\",\"subscriptionType\": \"CELL_CHANGE\"},{\"href\": \"http://meAppClient.example.com/rni/v1/notifications/MeasTa/77777\",\"subscriptionType\": \"MEAS_TIMING_ADVANCE\"}]}}" + s = p_uri.split('?') + return "{\"SubscriptionLinkList\": {\"_links\": {\"self\": \"http://example.com" + s[0] + "\"},\"subscription\": [{\"href\": \"http://meAppClient.example.com/rni/v1/notifications/cell_change/77777\",\"subscriptionType\": \"CELL_CHANGE\"},{\"href\": \"http://meAppClient.example.com/rni/v1/notifications/MeasTa/77777\",\"subscriptionType\": \"MEAS_TIMING_ADVANCE\"}]}}" # End of method getSubscriptionLinkList + def getMp1TransportInfoList(self): + print(">>> getMp1TransportInfoList") + resp = None + try: + resp = "{\"transportInfoList\": [\t" + for r in self.__transport_info__.itertuples(): + t = tuple(r) + resp += self.__to_transport_info__(t) + "," + # En of 'for' statement + resp = resp[: len(resp) - 1] + resp += "\t]}" + print("getMp1TransportInfoList: ", resp) + except KeyError: + print("getMp1TransportInfoList: No transportInfo list") + return resp + # End of method getMp1TransportInfo + + def getMp1TrafficRulesList(self): + print(">>> getMp1TrafficRulesList") + resp = None + try: + resp = "{\"TrafficRulesList\": [\t" + for r in self.__traffic_rules__.itertuples(): + t = tuple(r) + resp += self.__to_traffic_rule__(t) + "," + # En of 'for' statement + resp = resp[: len(resp) - 1] + resp += "\t]}" + print("getMp1TrafficRulesList: ", resp) + except KeyError: + print("getMp1TrafficRulesList: No TrafficRules list") + return resp + # End of method getMp1TrafficRules + + def getMp1TrafficRule(self): + print(">>> getMp1TrafficRule") + resp = None + try: + resp = "{\"TrafficRule\": [\t" + for r in self.__traffic_rule__.itertuples(): + t = tuple(r) + resp += self.__to_traffic_rule__(t) + "," + # En of 'for' statement + resp = resp[: len(resp) - 1] + resp += "\t]}" + print("getMp1TrafficRule: ", resp) + except KeyError: + print("getMp1TrafficRule: No TrafficRules list") + return resp + # End of method getMp1TrafficRules + def getSubscriberFromAddress(self, p_ue_address): print(">>> getSubscriberFromAddress: ", p_ue_address) result = None @@ -209,16 +316,26 @@ class mec_database: return resp # End of method getUEidentityTagInfo + def getBwAllocationAppInst(self, p_app_inst, p_ue_identity_tag): + print(">>> getBwAllocationAppInst: ", p_app_inst, ", ", p_ue_identity_tag) + resp = None + resp = "{\"bwInfo\": {\"timeStamp\": {\"seconds\": 0,\"nanoSeconds\": 0},\"appInsId\": \"string\",\"requestType\": \"APPLICATION_SPECIFIC_BW_ALLOCATION\",\"sessionFilter\": [{\"sourceIp\": \"string\",\"sourcePort\": [\"string\"],\"dstAddress\": \"string\",\"dstPort\": [\"string\"],\"protocol\": \"string\"}],\"fixedBWPriority\": \"not defined in the present document\",\"fixedAllocation\": \"string\",\"allocationDirection\": \"00 = Downlink (towards the UE)\"}}" + print("getBwAllocationAppInst: ", resp) + return resp + # End of method getBwAllocationAppInst + def registerUEidentity(self, p_app_inst, p_json_msg): print(">>> registerUEidentity", p_json_msg) if p_json_msg["state"] != "REGISTERED" and p_json_msg["state"] != "UNREGISTERED": - return None + return '400 Bad Request' resp = None try: # Check the record exists r = tuple(self.__ue_information_list__.loc[p_app_inst, p_json_msg["ueIdentityTag"]]) print("registerUEidentity: Find zoneId for appInst: ", p_app_inst, ", r= ", r) - self.__ue_information_list__.loc[p_app_inst, p_json_msg["ueIdentityTag"]]['state'] = p_json_msg["state"] + if self.__ue_information_list__.loc[p_app_inst, p_json_msg["ueIdentityTag"]]['state'] == 'INVALID_STATE': + return '412 Precondition Failed' + self.__ue_information_list__.loc[p_app_inst, p_json_msg["ueIdentityTag"]]['state'] = p_json_msg["state"] l = (p_json_msg["ueIdentityTag"], p_json_msg["state"]) resp = self.__to_ueIdentityTagInfo__(p_json_msg["ueIdentityTag"], l) except KeyError: @@ -263,12 +380,32 @@ class mec_database: return resp # End of unregisterSubscription - def getBwAllocationAppInst(self, p_app_inst, p_ue_identity_tag): - print(">>> getBwAllocationAppInst: ", p_app_inst, ", ", p_ue_identity_tag) + def registerRniSubscription(self, p_json_msg): + print(">>> registerRniSubscription: ", p_json_msg) resp = None - resp = "{\"bwInfo\": {\"timeStamp\": {\"seconds\": 0,\"nanoSeconds\": 0},\"appInsId\": \"string\",\"requestType\": \"APPLICATION_SPECIFIC_BW_ALLOCATION\",\"sessionFilter\": [{\"sourceIp\": \"string\",\"sourcePort\": [\"string\"],\"dstAddress\": \"string\",\"dstPort\": [\"string\"],\"protocol\": \"string\"}],\"fixedBWPriority\": \"not defined in the present document\",\"fixedAllocation\": \"string\",\"allocationDirection\": \"00 = Downlink (towards the UE)\"}}" - print("getBwAllocationAppInst: ", resp) + if p_json_msg['subscriptionType'] == 'CELL_CHANGE': + resp = self.__to_rni_subscriptions__(p_json_msg, 'CELL_CHANGE') return resp - # End of method getBwAllocationAppInst + # End of registerRniSubscription + + def getRabInfo(self, p_cell_id): + print(">>> getRabInfo: ", p_cell_id) + resp = None + if p_cell_id == '0xFFFFFFFF': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + else: + resp = "{ \"RabInfo\": { \"timeStamp\": { \"seconds\": 1577836800, \"nanoSeconds\": 0 }, \"appInsId\": \"01\", \"requestId\": \"01\", \"cellUserInfo\": { \"ecgi\": { \"plmn\": { \"mcc\": \"001\", \"mnc\": \"01\" }, \"cellId\": \"" + p_cell_id + "\" }, \"ueInfo\": { \"associateId\": null, \"type\": \"1\", \"value\": \"192.0.2.0\", \"erabInfo\": { \"erabId\": 10 }, \"erabQosParameters\": { \"qci\": 7, \"qosInformation\": { \"erabMbrDl\": 10, \"erabMbrUl\": 10, \"erabGbrDl\": 10, \"erabGbrUl\": 10 } } } } } }" + return resp + # End of getRabInfo + + def getPlmnInfo(self, p_app_inst): + print(">>> getPlmnInfo: ", p_app_inst) + resp = None + if p_app_inst == '99': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + else: + resp = "{ \"PlmnInfo\": { \"timeStamp\": { \"seconds\": 1577836800, \"nanoSeconds\": 0 }, \"appInsId\": \"" + p_app_inst + "\", \"ecgi\": { \"plmn\": { \"mcc\": \"001\", \"mnc\": \"01\" }, \"cellId\": \"0x800000A\" } } }" + return resp + # End of getPlmnInfo # End of class mec_database diff --git a/simu/mec_http_server.py b/simu/mec_http_server.py index 37c937aac7ae1ea48d67a1e207710c75d52cbd56..438871884bec4fbcc04a5c145725aa837ca36160 100644 --- a/simu/mec_http_server.py +++ b/simu/mec_http_server.py @@ -96,12 +96,21 @@ class myHandler(http.server.BaseHTTPRequestHandler): else: if resp.find('Not Found') != -1: self.send_response(404, 'Not Found') + resp = "" elif resp.find('Forbidden') != -1: self.send_response(403, 'Forbidden') - elif resp.find('Bad Request') != -1: + resp = "" + elif resp.find('Bad Request') != -1 or resp.find('Wrong parameters') != -1: self.send_response(400, 'Bad Request') + elif resp.find('Precondition Failed') != -1: + self.send_response(412, 'Precondition Failed') + resp = "{\"problemDetails\": {\t\"type\": \"Precondition Failed\",\t\"title\": \"N/A\",\t\"status\": 412,\t\"detail\": \"Wrong preconditions\",\t\"instance\": \"N/A\"}}" + content_type = 'application/problem+json' elif resp.find('userTrackingSubscription') != -1: self.send_response(201, 'Created') + resp = "" + elif resp.find('CellChangeSubscription') != -1: + self.send_response(201, 'Created') else: self.send_response(200, 'OK') self.send_header('Host', self.headers.get('Host')) # send_header() shall be after send_response() @@ -121,6 +130,68 @@ class myHandler(http.server.BaseHTTPRequestHandler): return # End of do_POST + # Handler for the PUT requests + def do_PUT(self): + print(">>> do_PUT: ", self.path) + self.protocol_version = self.request_version + # Check HTTP end_headers + if self.__check_http_headers__() == False: + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"N/A\",\t\"status\": 400,\t\"detail\": \"Wrong headers\",\t\"instance\": \"N/A\"}}" + self.protocol_version = self.request_version + self.send_response(400, 'Bad Request') + self.send_header('Host', self.headers.get('Host')) + self.send_header('Authorization', self.headers.get('Authorization')) + self.send_header('Connection', 'keep-alive') + self.send_header('Content-Type', 'application/problem+json') + l = len(resp) + self.send_header('Content-Length', str(l)) + self.end_headers() + self.wfile.write(bytes(resp, 'utf-8')) + return + + resp, content_type = self.__process__() + print('do_PUT: resp= ', resp, ', Content_Type= ', content_type) + if (resp == None): + self.send_response(404, 'Not Found') + self.send_header('Host', self.headers.get('Host')) # send_header() shall be after send_response() + self.send_header('Authorization', self.headers.get('Authorization')) + self.send_header('Connection', 'keep-alive') + self.send_header('Content-Type', content_type) + self.send_header('Content-Length', '0') + self.end_headers() + else: + if resp.find('Not Found') != -1: + self.send_response(404, 'Not Found') + resp = "" + elif resp.find('Forbidden') != -1: + self.send_response(403, 'Forbidden') + resp = "" + elif resp.find('Bad Request') != -1: + self.send_response(400, 'Bad Request') + resp = "" + elif resp.find('Precondition Failed') != -1: + self.send_response(412, 'Precondition Failed') + resp = "{\"problemDetails\": {\t\"type\": \"Precondition Failed\",\t\"title\": \"N/A\",\t\"status\": 412,\t\"detail\": \"Wrong preconditions\",\t\"instance\": \"N/A\"}}" + content_type = 'application/problem+json' + else: + self.send_response(200, 'OK') + self.send_header('Host', self.headers.get('Host')) # send_header() shall be after send_response() + self.send_header('Authorization', self.headers.get('Authorization')) + self.send_header('Connection', 'keep-alive') + self.send_header('Content-Type', content_type) + l = len(resp) + self.send_header('Content-Length', str(l)) + #self.end_headers() # Unable to bufferize wfile, so calling end_headers() headers and body are sent in 2 different TCP packets + self._headers_buffer.append(b"\r\n") + self._headers_buffer.append(bytes(resp, 'utf-8')) + self.wfile.write(b"".join(self._headers_buffer)) + self._headers_buffer = [] + #self.wfile.write(bytes(resp, 'utf-8')) + #self.wfile.flush() + print("<<< do_PUT") + return + # End of do_POST + # Handler for the DELETE requests def do_DELETE(self): print('>>> do_DELETE: ', self.path) @@ -209,6 +280,8 @@ class myHandler(http.server.BaseHTTPRequestHandler): return self.__process__rnis__api__(s) elif s[2] == 'bwm' and ((s[3] == 'v1') or (s[3] == 'v2')): return self.__process__bwm__api__(s) + elif s[2] == 'mec_app_support' and ((s[3] == 'v1') or (s[3] == 'v2')): + return self.__process__mp1__api__(s) else: return None, 'application/json' # End of __process__ @@ -302,8 +375,7 @@ class myHandler(http.server.BaseHTTPRequestHandler): content_type = 'application/problem+json' if (resp == None): resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"UEidentityAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" - content_type = 'application/problem+json' - elif resp.find('problemDetails') != -1: + if resp.find('problemDetails') != -1: content_type = 'application/problem+json' print ("<<< __process__ue__identity__api__: ", resp, ", ", content_type) @@ -316,11 +388,65 @@ class myHandler(http.server.BaseHTTPRequestHandler): resp = None content_type = 'application/json' if p_split[4].startswith('subscriptions'): - if p_split.__len__() == 6: + if p_split.__len__() == 5: + s = p_split[4].split('?') + if s.__len__() == 1: # Chek message body + # Register/Unregister operation + body = None + # Extract the body if any + content_len = int(self.headers.get('Content-Length')) + if (content_len != 0): + body = self.rfile.read(content_len) + json_msg = self.__decode__json__body__(body) + if (json_msg == None): + resp = "{\"problemDetails\": {\t\"type\": \"Body processing not supported\",\t\"title\": \"UEidentityAPI\",\t\"status\": 400,\t\"detail\": \"Unknown request\",\t\"instance\": \"string\"}}" + else: + resp = self.__db__.registerRniSubscription(json_msg) + elif s[0] != 'subscriptions': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + else: + s = s[1].split('=') + print('__process__rnis__api__: ', s) + if s[0] != 'subscription_type': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + elif s[1] == 'wrongSubscriptionType': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + else: + resp = self.__db__.getSubscriptionLinkList(self.path) + elif p_split.__len__() == 6: if p_split[5] == '': resp = self.__db__.getSubscriptionLinkList(self.path) + elif s[0] != 'subscriptions': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + else: + s = s[1].split('=') + print('__process__rnis__api__: ', s) + if s[0] != 'subscription_type': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + elif s[1] == 'wrongSubscriptionType': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + else: + resp = self.__db__.getSubscriptionLinkList(self.path) + elif p_split[4].startswith('queries'): + if p_split.__len__() == 5: + s = p_split[4].split('?') + if s.__len__() == 1: # Chek message body + pass + else: + if s[0] != 'queries': + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + else: + s = s[1].split('=') + print('__process__rnis__api__ (queries): ', s) + if s[0] == 'cell_id': + resp = self.__db__.getRabInfo(s[1]) + elif s[0] == 'plmn_info': + resp = self.__db__.getPlmnInfo(s[1]) + else: + resp = "{\"problemDetails\": {\t\"type\": \"Bad Request\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" if (resp == None): resp = "{\"problemDetails\": {\t\"type\": \"Not supported\",\t\"title\": \"RnisAPI\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + if resp.find('problemDetails') != -1: content_type = 'application/problem+json' print ("<<< __process__rnis__api__: ", resp, ", ", content_type) @@ -359,6 +485,28 @@ class myHandler(http.server.BaseHTTPRequestHandler): return resp, content_type # End of __process__bwm__api__ + # Process the MP1 request + def __process__mp1__api__(self, p_split): + print (">>> __process__mp1__api__: ", p_split) + resp = None + content_type = 'application/json' + if p_split[4].startswith('transports'): # E.g. /mp1/v1/transports + resp = self.__db__.getMp1TransportInfoList() + elif p_split[4].startswith('applications'): + if p_split[6].startswith('dns_rules'): # E.g. /mp1/v1/applications/appInstId01/dns_rules + pass + elif p_split[6].startswith('traffic_rules'): # E.g. GET/PUT /mp1/v1/applications/appInstId01/traffic_rules... + if length(p_split) == 7: # E.g. GET /mp1/v1/applications/appInstId01/traffic_rules + resp = self.__db__.getMp1TrafficRulesList() + else: # E.g. GET/PUT /mp1/v1/applications/appInstId01/traffic_rules/{trafficRuleId} + resp = self.__db__.getMp1TrafficRule(p_split[7]) + if (resp == None): + resp = "{\"problemDetails\": {\t\"type\": \"Not supported\",\t\"title\": \"Mp1\",\t\"status\": 400,\t\"detail\": \"Wrong parameters\",\t\"instance\": \"string\"}}" + content_type = 'application/problem+json' + print ("<<< __process__mp1__api__: ", resp, ", ", content_type) + return resp, content_type + # End of __process__bwm__api__ + # Decode a Json HTTP body message def __decode__json__body__(self, p_body): print(">>> __decode__json__body__: ", p_body) @@ -369,6 +517,8 @@ class myHandler(http.server.BaseHTTPRequestHandler): return json_msg.get("ueIdentityTags")[0] elif ("userTrackingSubscription" in json_msg.keys()) == True: return json_msg.get("userTrackingSubscription") + elif ("CellChangeSubscription" in json_msg.keys()) == True: + return json_msg.get("CellChangeSubscription") return None # End of __decode__json__body__ diff --git a/simu/mec_simulator.py b/simu/mec_simulator.py index 88b42a2a5f3ca789b77c6e5a394c8dcb3636e8ae..55a5b174bcfae02e9c9a34056749b979e1d14e82 100644 --- a/simu/mec_simulator.py +++ b/simu/mec_simulator.py @@ -10,7 +10,7 @@ import msvcrt # MEC simulator IPv4 address #ADDRESS_BINDING = '172.28.4.87' #ADDRESS_BINDING = '192.168.1.21' -ADDRESS_BINDING = '192.168.0.17' +ADDRESS_BINDING = '192.168.56.1' #ADDRESS_BINDING = '127.0.0.1' # MEC simulator IPv4 listening port PORT_NUMBER = 8081 diff --git a/ttcn/AtsMec/AtsMec_AppEnablementAPI_TestCases.ttcn b/ttcn/AtsMec/AtsMec_AppEnablementAPI_TestCases.ttcn new file mode 100644 index 0000000000000000000000000000000000000000..1719b34c9d79935be550b61214c2cfbad91f02c5 --- /dev/null +++ b/ttcn/AtsMec/AtsMec_AppEnablementAPI_TestCases.ttcn @@ -0,0 +1,341 @@ +/** + * @author ETSI / STF569 + * @version $URL:$ + * $ID:$ + * @desc This module provides the MEC test cases. + * @copyright ETSI Copyright Notification + * No part may be reproduced except as authorized by written permission. + * The copyright and the foregoing restriction extend to reproduction in all media. + * All rights reserved. + * @see ETSI GS MEC 003, Draft ETSI GS MEC 011 V2.0.9 (2018-10) + */ +module AtsMec_AppEnablementAPI_TestCases { + + // Libcommon + import from LibCommon_Time all; + import from LibCommon_VerdictControl all; + import from LibCommon_Sync all; + + // LibHttp + import from LibItsHttp_TypesAndValues all; + import from LibItsHttp_Functions all; + import from LibItsHttp_Templates all; + import from LibItsHttp_JsonTemplates all; + import from LibItsHttp_TestSystem all; + + // LibMec_AppEnablementAPI + import from AppEnablementAPI_Templates all; + import from AppEnablementAPI_Pics all; + import from AppEnablementAPI_Pixits all; + + // LibMec + import from LibMec_Functions all; + import from LibMec_Pics all; + import from LibMec_Pixits all; + + group transport_info { + + /** + * @desc Check that the IUT responds with a list of available transports when queried by a MEC Application + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/TRANS/PlatTransport.tplan2 + */ + testcase TC_MEC_SRV_TRANS_001_OK() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_MEC_PLAT) or not(PICS_SERVICES) or not(PICS_ENABLE_APP_API_SUPPORTED)) { + log("*** " & testcasename() & ": PICS_MEC_PLAT and PICS_SERVICES and PICS_ENABLE_APP_API_SUPPORTED required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_get( + "/" & PICS_ROOT_API & PX_SVC_MGMT_TRANS_URI, + v_headers + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_ok( + mw_http_message_body_json( + mw_body_json_transport_info_list + )))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a UeIdentityTag ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_TRANS_001_OK + + } // End of group transport_info + + group traffic_rules { + + /** + * @desc Check that the IUT responds with a list of available traffic rules when queried by a MEC Application + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/TRAF/TrafficRules.tplan2 + */ + testcase TC_MEC_SRV_TRAF_001_OK() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_MEC_PLAT) or not(PICS_SERVICES) or not(PICS_ENABLE_APP_API_SUPPORTED)) { + log("*** " & testcasename() & ": PICS_MEC_PLAT and PICS_SERVICES and PICS_ENABLE_APP_API_SUPPORTED required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_get( + "/" & PICS_ROOT_API & PX_SVC_MGMT_APP_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/traffic_rules", + v_headers + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_ok( + mw_http_message_body_json( + mw_body_json_traffic_rules_list + )))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a UeIdentityTag ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_TRAF_001_OK + + /** + * @desc Check that the IUT responds with the information on a specific traffic rule when queried by a MEC Application + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/TRAF/TrafficRules.tplan2 + */ + testcase TC_MEC_SRV_TRAF_002_OK() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_MEC_PLAT) or not(PICS_SERVICES) or not(PICS_ENABLE_APP_API_SUPPORTED)) { + log("*** " & testcasename() & ": PICS_MEC_PLAT and PICS_SERVICES and PICS_ENABLE_APP_API_SUPPORTED required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_get( + "/" & PICS_ROOT_API & PX_SVC_MGMT_APP_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/traffic_rules/" & oct2char(unichar2oct(PX_TRAFFIC_RULE_ID, "UTF-8")), + v_headers + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_ok( + mw_http_message_body_json( + mw_body_json_traffic_rule( + mw_traffic_rule( + PX_TRAFFIC_RULE_ID + )))))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a UeIdentityTag ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_TRAF_002_OK + + /** + * @desc Check that the IUT updates a specific traffic rule when commanded by a MEC Application + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/TRAF/TrafficRules.tplan2 + */ + testcase TC_MEC_SRV_TRAF_003_OK() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_MEC_PLAT) or not(PICS_SERVICES) or not(PICS_ENABLE_APP_API_SUPPORTED)) { + log("*** " & testcasename() & ": PICS_MEC_PLAT and PICS_SERVICES and PICS_ENABLE_APP_API_SUPPORTED required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_post( + "/" & PICS_ROOT_API & PX_SVC_MGMT_APP_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/traffic_rules/" & oct2char(unichar2oct(PX_TRAFFIC_RULE_ID, "UTF-8")), + v_headers, + m_http_message_body_json( + m_body_json_traffic_rule( + m_traffic_rule( + PX_TRAFFIC_RULE_ID, + -, + -, + -, + DROP + ) + ) + ) + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_ok( + mw_http_message_body_json( + mw_body_json_traffic_rule( + mw_traffic_rule( + PX_TRAFFIC_RULE_ID + )))))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a UeIdentityTag ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_TRAF_003_OK + + /** + * @desc Check that the IUT responds with an error when a request for an unknown URI is sent by a MEC Application + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/TRAF/TrafficRules.tplan2 + */ + testcase TC_MEC_SRV_TRAF_001_NF() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_MEC_PLAT) or not(PICS_SERVICES) or not(PICS_ENABLE_APP_API_SUPPORTED)) { + log("*** " & testcasename() & ": PICS_MEC_PLAT and PICS_SERVICES and PICS_ENABLE_APP_API_SUPPORTED required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_get( + "/" & PICS_ROOT_API & PX_SVC_MGMT_APP_URI & oct2char(unichar2oct(PX_NON_EXISTENT_APP_INSTANCE_ID, "UTF-8")) & "/traffic_rules", + v_headers + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_404_not_found( + mw_http_message_body_json( + mw_body_json_app_enablement_problem_details( + mw_problem_details( + -, -, 404 + )))))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a UeIdentityTag ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_TRAF_001_NF + + } // End of group traffic_rules + +} // End of module AtsMec_AppEnablementAPI_TestCases diff --git a/ttcn/AtsMec/AtsMec_RnisAPI_TestCases.ttcn b/ttcn/AtsMec/AtsMec_RnisAPI_TestCases.ttcn index 40768846e77c56d3bbb178cc23ce9330cfb4c525..30e65fae717a03708ea05fbe52905ffa5a90345c 100644 --- a/ttcn/AtsMec/AtsMec_RnisAPI_TestCases.ttcn +++ b/ttcn/AtsMec/AtsMec_RnisAPI_TestCases.ttcn @@ -7,7 +7,7 @@ * No part may be reproduced except as authorized by written permission. * The copyright and the foregoing restriction extend to reproduction in all media. * All rights reserved. - * @see ETSI GS MEC 003, Draft ETSI GS MEC 013 V2.0.3 (2018-10) + * @see ETSI GS MEC 003, Draft ETSI GS MEC 012 V2.0.3 (2018-10) */ module AtsMec_RnisAPI_TestCases { @@ -34,17 +34,25 @@ module AtsMec_RnisAPI_TestCases { import from LibMec_Pics all; import from LibMec_Pixits all; - group me_app_role { + group all_subscriptions { /** - * @desc Check that the RNIS service sends all RNIS subscriptions when requested - * @see https://forge.etsi.org/gitlab/mec/MEC-tests/blob/master/Test%20Purposes/App/Mp1/Rnis/RnisAllSubscriptions_BV.tplan2 - * @see + * @desc Check that the RNIS service sends the list of links to the relevant RNIS subscriptions when requested. + * Acceptable SUBSCRIPTION_TYPE are the following: + * - CellChangeSubscription + * - RabEstSubscription + * - RabModSubscription + * - RabRelSubscription + * - MeasRepUeSubscription + * - MeasTaSubscription + * - CaReconfSubscription + * - S1BearerSubscription + * - NrMeasRepUeSubscription" + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/RNIS/RnisSpecificSubscription_BV.tplan2 */ - testcase TC_MEC025_RNIS_SUBSCRIPTION_005() runs on HttpComponent system HttpTestAdapter { + testcase TC_MEC_SRV_RNIS_011_OK() runs on HttpComponent system HttpTestAdapter { // Local variables var HeaderLines v_headers; - var HttpMessage v_response; // Test control if (not(PICS_RNIS) or not(PICS_RNIS_ALL_SUBSCRIPTIONS)) { @@ -63,7 +71,7 @@ module AtsMec_RnisAPI_TestCases { httpPort.send( m_http_request( m_http_request_get( - PX_RNIS_SUBSCRITIONS_URI, + "/" & PICS_ROOT_API & PX_RNIS_SUBSCRITIONS_URI & "?subscription_type=" & oct2char(unichar2oct(PX_SUBSCRIPTION_HREF_VALUE, "UTF-8")), v_headers ) ) @@ -80,8 +88,8 @@ module AtsMec_RnisAPI_TestCases { mw_body_json_subscriptions_list( mw_subscriptions_list( PX_LINKS_SELF, - ? - )))))) -> value v_response { + { *, mw_subscription(-, PX_SUBSCRIPTION_TYPE), * } + )))))) { tc_ac.stop; log("*** " & testcasename() & ": PASS: IUT successfully responds with a cell subscription ***"); @@ -95,9 +103,360 @@ module AtsMec_RnisAPI_TestCases { // Postamble f_cf_01_http_down(); - } // End of testcase TC_MEC025_RNIS_SUBSCRIPTION_005 + } // End of testcase TC_MEC_SRV_RNIS_011_OK - } // End of group me_app_role + /** + * @desc Check that the RNIS service creates a new RNIS subscription. + * Acceptable SUBSCRIPTION_TYPE are the following: + * - CellChangeSubscription + * - RabEstSubscription + * - RabModSubscription + * - RabRelSubscription + * - MeasRepUeSubscription + * - MeasTaSubscription + * - CaReconfSubscription + * - S1BearerSubscription + * - NrMeasRepUeSubscription" + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/RNIS/RnisSpecificSubscription_BV.tplan2 + */ + testcase TC_MEC_SRV_RNIS_012_OK() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_RNIS) or not(PICS_RNIS_ALL_SUBSCRIPTIONS)) { + log("*** " & testcasename() & ": PICS_RNIS and PICS_RNIS_ALL_SUBSCRIPTIONS required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_post( + "/" & PICS_ROOT_API & PX_RNIS_SUBSCRITIONS_URI, + v_headers, + m_http_message_body_json( + m_body_json_cell_change_subscription( + m_cell_change_subscription( + PX_CALLBACK_REFERENCE, + PX_LINKS_SELF, + m_filter_criteria( + "01", + { m_associate_id(UE_IPV4_ADDRESS, PX_ASSOCIATE_ID_VALUE) }, + m_plmn("01", "001"), + PX_CELL_ID, + COMPLETED + ), + m_time_stamp(1577836800) + ) + ) + ) + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_201_created( + mw_http_message_body_json( + mw_body_json_cell_change_subscription( + mw_cell_change_subscription( + PX_CALLBACK_REFERENCE, + PX_LINKS_SELF + )))))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a cell subscription ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_RNIS_012_OK + + } // End of group all_subscriptions + + group allSubscription_bo_bi { + + /** + * @desc Check that the RNIS service responds with an error when it receives a request to get all RNIS subscriptions with a wrong subscription type + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/RNIS/RnisSpecificSubscription_BO_BI.tplan2 + */ + testcase TC_MEC_SRV_RNIS_011_BR() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_RNIS) or not(PICS_RNIS_ALL_SUBSCRIPTIONS)) { + log("*** " & testcasename() & ": PICS_RNIS and PICS_RNIS_ALL_SUBSCRIPTIONS required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_get( + "/" & PICS_ROOT_API & PX_RNIS_SUBSCRITIONS_URI & "?subscription_type=wrongSubscriptionType", + v_headers + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_400_bad_request( + mw_http_message_body_json( + mw_body_json_rni_problem_details( + mw_problem_details( + -, -, 400 + )))))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with HTTP error 400 Bad Request ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_RNIS_011_BR + + /** + * @desc Check that the RNIS service responds with an error when it receives a request to create a new RNIS subscription with a wrong format + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/RNIS/RnisSpecificSubscription_BV.tplan2 + */ + testcase TC_MEC_SRV_RNIS_012_BR() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_RNIS) or not(PICS_RNIS_ALL_SUBSCRIPTIONS)) { + log("*** " & testcasename() & ": PICS_RNIS and PICS_RNIS_ALL_SUBSCRIPTIONS required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_post( + "/" & PICS_ROOT_API & PX_RNIS_SUBSCRITIONS_URI, + v_headers, + m_http_message_body_json( + m_body_json_cell_change_subscription( + m_cell_change_subscription_wrong_subscription_type( + PX_CALLBACK_REFERENCE, + PX_LINKS_SELF, + m_filter_criteria( + "01", + { m_associate_id(UE_IPV4_ADDRESS, PX_ASSOCIATE_ID_VALUE) }, + m_plmn("01", "001"), + PX_CELL_ID, + COMPLETED + ), + m_time_stamp(1577836800) + ) + ) + ) + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_400_bad_request( + mw_http_message_body_json( + mw_body_json_rni_problem_details( + mw_problem_details( + -, -, 400 + )))))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a cell subscription ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_RNIS_012_BR + + } // End of group allSubscription_bo_bi + + group rnis_query { + + /** + * @desc Check that the RNIS service returns the RAB information when requested. + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/RNIS/RnisQuery_BV.tplan2 + */ + testcase TC_MEC_SRV_RNIS_016_OK() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_RNIS) or not(PICS_RNIS_QUERY)) { + log("*** " & testcasename() & ": PICS_RNIS and PICS_RNIS_QUERY required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_get( + "/" & PICS_ROOT_API & PX_RNIS_QUERIES_URI & "?cell_id=" & oct2char(unichar2oct(PX_CELL_ID, "UTF-8")), + v_headers + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_ok( + mw_http_message_body_json( + mw_body_json_rab_info( + mw_rab_info( + mw_time_stamp, + PX_APP_INS_ID, + -, + mw_cell_user_info( + mw_ecgi( + mw_plmn, + PX_CELL_ID + )))))))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a RAB information ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_RNIS_016_OK + + /** + * @desc Check that the RNIS service returns the PLMN information when requested. + * @see https://forge.etsi.org/gitlab/mec/gs032p2-test-purposes/blob/master/Test%20Purposes/SRV/RNIS/RnisQuery_BV.tplan2 + */ + testcase TC_MEC_SRV_RNIS_017_OK() runs on HttpComponent system HttpTestAdapter { + // Local variables + var HeaderLines v_headers; + + // Test control + if (not(PICS_RNIS) or not(PICS_RNIS_QUERY)) { + log("*** " & testcasename() & ": PICS_RNIS and PICS_RNIS_QUERY required for executing the TC ***"); + setverdict(inconc); + stop; + } + + // Test component configuration + f_cf_01_http_up(); + + // Test adapter configuration + + // Preamble + f_init_default_headers_list(-, -, v_headers); + httpPort.send( + m_http_request( + m_http_request_get( + "/" & PICS_ROOT_API & PX_RNIS_QUERIES_URI & "?cell_id=" & oct2char(unichar2oct(PX_CELL_ID, "UTF-8")), + v_headers + ) + ) + ); + f_selfOrClientSyncAndVerdict(c_prDone, e_success); + + // Test Body + tc_ac.start; + alt { + [] httpPort.receive( + mw_http_response( + mw_http_response_ok( + mw_http_message_body_json( + mw_body_json_plmn_info( + mw_plmn_info( + mw_time_stamp, + PX_APP_INS_ID, + mw_ecgi( + mw_plmn, + PX_CELL_ID + ))))))) { + tc_ac.stop; + + log("*** " & testcasename() & ": PASS: IUT successfully responds with a PLMN information ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_success); + } + [] tc_ac.timeout { + log("*** " & testcasename() & ": INCONC: Expected message not received ***"); + f_selfOrClientSyncAndVerdict(c_tbDone, e_timeout); + } + } // End of 'alt' statement + + // Postamble + f_cf_01_http_down(); + } // End of testcase TC_MEC_SRV_RNIS_017_OK + + } // End of group rnis_query } // End of module AtsMec_RnisAPI_TestCases diff --git a/ttcn/AtsMec/AtsMec_TestControl.ttcn b/ttcn/AtsMec/AtsMec_TestControl.ttcn index 5a1ce0b04d039d4a1592b98c6de9f2dcb468fa05..ddbcae6fd567d2d25ca3c47e0018160fa4046b02 100644 --- a/ttcn/AtsMec/AtsMec_TestControl.ttcn +++ b/ttcn/AtsMec/AtsMec_TestControl.ttcn @@ -8,6 +8,8 @@ module AtsMec_TestControl { import from RnisAPI_Pics all; // LibMec/BwManagementAPI import from BwManagementAPI_Pics all; + // LibMec/AppEnablementAPI + import from AppEnablementAPI_Pics all; // LibMec import from LibMec_Pics all; @@ -18,6 +20,7 @@ module AtsMec_TestControl { import from AtsMec_RadioNodeLocationAPI_TestCases all; import from AtsMec_RnisAPI_TestCases all; import from AtsMec_BwManagementAPI_TestCases all; + import from AtsMec_AppEnablementAPI_TestCases all; control { @@ -56,11 +59,26 @@ module AtsMec_TestControl { execute(TC_MEC_PLAT_RLOC_001_OK()); } + + if (PICS_ENABLE_APP_API_SUPPORTED) { + execute(TC_MEC_SRV_TRANS_001_OK()); + execute(TC_MEC_SRV_TRAF_001_OK()); + execute(TC_MEC_SRV_TRAF_002_OK()); + execute(TC_MEC_SRV_TRAF_003_OK()); + execute(TC_MEC_SRV_TRAF_001_NF()); + } } if (PICS_RNIS) { if (PICS_RNIS_ALL_SUBSCRIPTIONS) { - execute(TC_MEC025_RNIS_SUBSCRIPTION_005()); + execute(TC_MEC_SRV_RNIS_011_OK()); + execute(TC_MEC_SRV_RNIS_012_OK()); + execute(TC_MEC_SRV_RNIS_011_BR()); + execute(TC_MEC_SRV_RNIS_012_BR()); + } + if (PICS_RNIS_QUERY) { + execute(TC_MEC_SRV_RNIS_016_OK()); + } } diff --git a/ttcn/AtsMec/AtsMec_UEidentityAPI_TestCases.ttcn b/ttcn/AtsMec/AtsMec_UEidentityAPI_TestCases.ttcn index 669f019b397fe76fc522a889ea6f10668e9768b8..6e0ea09e309f8632d57e4c6dd4688be81f2f61ac 100644 --- a/ttcn/AtsMec/AtsMec_UEidentityAPI_TestCases.ttcn +++ b/ttcn/AtsMec/AtsMec_UEidentityAPI_TestCases.ttcn @@ -7,7 +7,7 @@ * No part may be reproduced except as authorized by written permission. * The copyright and the foregoing restriction extend to reproduction in all media. * All rights reserved. - * @see ETSI GS MEC 003, Draft ETSI GS MEC 013 V2.0.3 (2018-10) + * @see ETSI GS MEC 014 */ module AtsMec_UEidentityAPI_TestCases { @@ -43,7 +43,7 @@ module AtsMec_UEidentityAPI_TestCases { // Test control if (not(PICS_MEC_PLAT) or not(PICS_SERVICES) or not(PICS_UE_IDENTITY_API_SUPPORTED)) { - log("*** " & testcasename() & ": PICS_MEC_PLAT and PICS_SERVICES and PICS_LOCATION_API_SUPPORTED required for executing the TC ***"); + log("*** " & testcasename() & ": PICS_MEC_PLAT and PICS_SERVICES and PICS_UE_IDENTITY_API_SUPPORTED required for executing the TC ***"); setverdict(inconc); stop; } @@ -236,22 +236,22 @@ module AtsMec_UEidentityAPI_TestCases { } httpPort.send( m_http_request( - m_http_request_post( - "/" & PICS_ROOT_API & PX_ME_APP_Q_UE_IDENTITY_ID_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/ue_identity_tag_info", - v_headers, - m_http_message_body_json( - m_body_json_ue_identity_tag_info( - m_ue_identity_tag_info( - { - m_ue_identity_tag_item( - PX_UE_IDENTITY_TAG, - REGISTERED - ) - } - ) - ) - ) - ) + m_http_request_put( + "/" & PICS_ROOT_API & PX_ME_APP_Q_UE_IDENTITY_ID_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/ue_identity_tag_info", + v_headers, + m_http_message_body_json( + m_body_json_ue_identity_tag_info( + m_ue_identity_tag_info( + { + m_ue_identity_tag_item( + PX_UE_IDENTITY_TAG, + REGISTERED + ) + } + ) + ) + ) + ) ) ); f_selfOrClientSyncAndVerdict(c_prDone, e_success); @@ -316,22 +316,22 @@ module AtsMec_UEidentityAPI_TestCases { } httpPort.send( m_http_request( - m_http_request_post( - "/" & PICS_ROOT_API & PX_ME_APP_Q_UE_IDENTITY_ID_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/ue_identity_tag_info", - v_headers, - m_http_message_body_json( - m_body_json_ue_identity_tag_info( - m_ue_identity_tag_info( - { - m_ue_identity_tag_item( - PX_UE_IDENTITY_TAG, - INVALID_STATE - ) - } - ) - ) - ) - ) + m_http_request_put( + "/" & PICS_ROOT_API & PX_ME_APP_Q_UE_IDENTITY_ID_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/ue_identity_tag_info", + v_headers, + m_http_message_body_json( + m_body_json_ue_identity_tag_info( + m_ue_identity_tag_info( + { + m_ue_identity_tag_item( + PX_UE_IDENTITY_TAG, + INVALID_STATE + ) + } + ) + ) + ) + ) ) ); f_selfOrClientSyncAndVerdict(c_prDone, e_success); @@ -386,22 +386,22 @@ module AtsMec_UEidentityAPI_TestCases { f_init_default_headers_list(-, -, v_headers); httpPort.send( m_http_request( - m_http_request_post( - "/" & PICS_ROOT_API & PX_ME_APP_Q_UE_IDENTITY_ID_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/ue_identity_tag_info", - v_headers, - m_http_message_body_json( - m_body_json_ue_identity_tag_info( - m_ue_identity_tag_info( - { - m_ue_identity_tag_item( - PX_UE_IDENTITY_TAG_INVALID_STATE, - UNREGISTERED - ) - } - ) - ) - ) - ) + m_http_request_put( + "/" & PICS_ROOT_API & PX_ME_APP_Q_UE_IDENTITY_ID_URI & oct2char(unichar2oct(PX_APP_INSTANCE_ID, "UTF-8")) & "/ue_identity_tag_info", + v_headers, + m_http_message_body_json( + m_body_json_ue_identity_tag_info( + m_ue_identity_tag_info( + { + m_ue_identity_tag_item( + PX_UE_IDENTITY_TAG_INVALID_STATE, + UNREGISTERED + ) + } + ) + ) + ) + ) ) ); f_selfOrClientSyncAndVerdict(c_prDone, e_success); diff --git a/ttcn/LibMec/AppEna/json/AppEnablementAPI.json b/ttcn/LibMec/AppEna/json/AppEnablementAPI.json index c5ee3fcda73baa582e50733f936af0fb7c26a484..e6a39042a6583aaba17e7fc7fc5b1a9c500b8032 100644 --- a/ttcn/LibMec/AppEna/json/AppEnablementAPI.json +++ b/ttcn/LibMec/AppEna/json/AppEnablementAPI.json @@ -1,9 +1,17 @@ { "openapi": "3.0.2", + "servers": [ + { + "url": "http://127.0.0.1:8081/mp1/v1" + }, + { + "url": "https://127.0.0.1:8081/mp1/v1" + } + ], "info": { - "title": "UE Application Interface API", + "title": "Mp1 API", "version": "1.1.1", - "description": "The ETSI MEC ISG MEC016 UE Application Interface API described using OpenAPI", + "description": "The ETSI MEC ISG MEC011 Application Enablement API described using OpenAPI", "license": { "name": "ETSI Forge copyright notice", "url": "https://forge.etsi.org/etsi-forge-copyright-notice.txt" @@ -13,130 +21,204 @@ } }, "externalDocs": { - "description": "ETSI GS MEC016 UE Application Interface API, V1.1.1", - "url": "http://www.etsi.org/deliver/etsi_gs/MEC/001_099/016/01.01.01_60/gs_MEC016v010101p.pdf" + "description": "ETSI GS MEC011 Application Enablement API, V1.1.1", + "url": "http://www.etsi.org/deliver/etsi_gs/MEC/001_099/011/01.01.01_60/gs_mec011v010101p.pdf" }, - "security": [ + "tags": [ { - "OauthSecurity": [ - "all" - ] - } - ], - "servers": [ + "name": "trafficRules" + }, { - "url": "http://127.0.0.1:8081/mx2/v1" + "name": "dnsRules" }, { - "url": "https://127.0.0.1:8081/mx2/v1" - } - ], - "tags": [ + "name": "subscriptions" + }, + { + "name": "services" + }, + { + "name": "timing" + }, { - "name": "appList" + "name": "transports" }, { - "name": "appContext" + "name": "callbacks" } ], "paths": { - "/app_list": { + "/applications/{appInstanceId}/dns_rules": { + "parameters": [ + { + "$ref": "#/components/parameters/Path.AppInstanceId" + } + ], "get": { - "description": "Used to query information about the available MEC applications.", - "operationId": "AppList_GET", + "description": "This method retrieves information about all the DNS rules associated with a mobile edge application instance.", + "operationId": "ApplicationsDnsRules_GET", "tags": [ - "appList" + "trafficRules" ], - "parameters": [ - { - "$ref": "#/components/parameters/Query.AppName" - }, - { - "$ref": "#/components/parameters/Query.AppProvider" + "responses": { + "200": { + "$ref": "#/components/responses/ApplicationsDnsRules.200" }, - { - "$ref": "#/components/parameters/Query.AppSoftVersion" + "400": { + "$ref": "#/components/responses/Error.400" }, - { - "$ref": "#/components/parameters/Query.ServiceCont" + "403": { + "$ref": "#/components/responses/Error.403" }, - { - "$ref": "#/components/parameters/Query.VendorId" + "404": { + "$ref": "#/components/responses/Error.404" } + } + } + }, + "/applications/{appInstanceId}/dns_rules/{dnsRuleId}": { + "parameters": [ + { + "$ref": "#/components/parameters/Path.AppInstanceId" + }, + { + "$ref": "#/components/parameters/Path.DnsRuleId" + } + ], + "get": { + "description": "This method retrieves information about a DNS rule associated with a mobile edge application instance.", + "operationId": "ApplicationsDnsRule_GET", + "tags": [ + "dnsRules" ], "responses": { "200": { - "$ref": "#/components/responses/AppList" + "$ref": "#/components/responses/ApplicationsDnsRule.200" }, "400": { "$ref": "#/components/responses/Error.400" }, - "401": { - "$ref": "#/components/responses/Error.401" + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + }, + "put": { + "description": "This method activates, de-activates or updates a traffic rule.", + "operationId": "ApplicationsDnsRule_PUT", + "tags": [ + "dnsRules" + ], + "responses": { + "200": { + "$ref": "#/components/responses/ApplicationsDnsRule.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" }, "403": { "$ref": "#/components/responses/Error.403" }, "404": { "$ref": "#/components/responses/Error.404" + }, + "412": { + "$ref": "#/components/responses/Error.412" } + }, + "requestBody": { + "$ref": "#/components/requestBodies/ApplicationsDnsRule" } } }, - "/app_contexts": { + "/applications/{appInstanceId}/subscriptions": { + "parameters": [ + { + "$ref": "#/components/parameters/Path.AppInstanceId" + } + ], + "get": { + "description": "The GET method may be used to request information about all subscriptions for this requestor. Upon success, the response contains entity body with all the subscriptions for the requestor.", + "operationId": "ApplicationsSubscriptions_GET", + "tags": [ + "subscriptions" + ], + "responses": { + "200": { + "$ref": "#/components/responses/ApplicationsSubscriptions.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + }, "post": { - "description": "The POST method can be used to create a new application context. Upon success, the response contains entity body describing the created application context.", - "operationId": "AppContext_POST", + "description": "The POST method may be used to create a new subscription. One example use case is to create a new subscription to the mobile edge service availability notifications. Upon success, the response contains entity body describing the created subscription.", + "operationId": "ApplicationsSubscriptions_POST", "tags": [ - "appContext" + "subscriptions" ], - "requestBody": { - "$ref": "#/components/requestBodies/AppContext" - }, "responses": { "201": { - "$ref": "#/components/responses/AppContext" + "$ref": "#/components/responses/ApplicationsSubscriptions.201" }, "400": { "$ref": "#/components/responses/Error.400" }, - "401": { - "$ref": "#/components/responses/Error.401" - }, "403": { "$ref": "#/components/responses/Error.403" }, "404": { "$ref": "#/components/responses/Error.404" } + }, + "requestBody": { + "$ref": "#/components/requestBodies/ApplicationsSubscriptions" + }, + "callbacks": { + "appTerminationNotification": { + "$ref": "#/components/callbacks/AppTerminationNotification" + }, + "serviceAvailabilityNotification": { + "$ref": "#/components/callbacks/ServiceAvailabilityNotification" + } } } }, - "/app_contexts/{contextId}": { + "/applications/{appInstanceId}/subscriptions/{subscriptionType}/{subscriptionId}": { "parameters": [ { - "$ref": "#/components/parameters/Path.ContextId" + "$ref": "#/components/parameters/Path.AppInstanceId" + }, + { + "$ref": "#/components/parameters/Path.SubscriptionType" + }, + { + "$ref": "#/components/parameters/Path.SubscriptionId" } ], - "put": { - "description": "The PUT method is used to update the callback reference of the existing application context. Upon successful operation, the target resource is updated with new callback reference.", - "operationId": "AppContextId_PUT", + "get": { + "description": "The GET method requests information about a subscription for this requestor. Upon success, the response contains entity body with the subscription for the requestor.", + "operationId": "ApplicationsSubscription_GET", "tags": [ - "appContext" + "subscriptions" ], - "requestBody": { - "$ref": "#/components/requestBodies/AppContext" - }, "responses": { - "204": { - "description": "No Content." + "200": { + "$ref": "#/components/responses/ApplicationsSubscription.200" }, "400": { "$ref": "#/components/responses/Error.400" }, - "401": { - "$ref": "#/components/responses/Error.401" - }, "403": { "$ref": "#/components/responses/Error.403" }, @@ -146,155 +228,1874 @@ } }, "delete": { - "description": "The DELETE method is used to delete the resource that represents the existing application context.", - "operationId": "AppContextId_DEL", + "description": "This method deletes a meMp1Subscription. This method is typically used in \"Unsubscribing from service availability event notifications\" procedure.", + "operationId": "ApplicationsSubscription_DELETE", "tags": [ - "appContext" + "subscriptions" ], "responses": { "204": { "description": "No Content" }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + } + }, + "/applications/{appInstanceId}/traffic_rules": { + "parameters": [ + { + "$ref": "#/components/parameters/Path.AppInstanceId" + } + ], + "get": { + "description": "This method retrieves information about all the traffic rules associated with a mobile edge application instance.", + "operationId": "ApplicationsTrafficRules_GET", + "tags": [ + "trafficRules" + ], + "responses": { + "200": { + "$ref": "#/components/responses/ApplicationsTrafficRules.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + } + }, + "/applications/{appInstanceId}/traffic_rules/{trafficRuleId}": { + "parameters": [ + { + "$ref": "#/components/parameters/Path.AppInstanceId" + }, + { + "$ref": "#/components/parameters/Path.TrafficRuleId" + } + ], + "get": { + "description": "This method retrieves information about all the traffic rules associated with a mobile edge application instance.", + "operationId": "ApplicationsTrafficRule_GET", + "tags": [ + "trafficRules" + ], + "responses": { + "200": { + "$ref": "#/components/responses/ApplicationsTrafficRule.200" + }, "400": { "$ref": "#/components/responses/Error.400" }, - "401": { - "$ref": "#/components/responses/Error.401" + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + }, + "put": { + "description": "This method retrieves information about all the traffic rules associated with a mobile edge application instance.", + "operationId": "ApplicationsTrafficRule_PUT", + "tags": [ + "trafficRules" + ], + "responses": { + "200": { + "$ref": "#/components/responses/ApplicationsTrafficRule.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" }, "403": { "$ref": "#/components/responses/Error.403" }, "404": { "$ref": "#/components/responses/Error.404" + }, + "412": { + "$ref": "#/components/responses/Error.412" } + }, + "requestBody": { + "$ref": "#/components/requestBodies/ApplicationsTrafficRule" } } - } - }, - "components": { - "parameters": { - "Query.AppName": { - "name": "appName", - "in": "query", - "description": "Name to identify the MEC application", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" + }, + "/services": { + "get": { + "description": "This method retrieves information about a list of meService resources. This method is typically used in \"service availability query\" procedure", + "operationId": "Services_GET", + "tags": [ + "services" + ], + "parameters": [ + { + "$ref": "#/components/parameters/Query.Ser_instance_id" + }, + { + "$ref": "#/components/parameters/Query.Ser_name" + }, + { + "$ref": "#/components/parameters/Query.Ser_category_id" + } + ], + "responses": { + "200": { + "$ref": "#/components/responses/Services.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" } } }, - "Query.AppProvider": { - "name": "appProvider", - "in": "query", - "description": "Provider of the MEC application", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" + "post": { + "description": "This method is used to create a meService resource. This method is typically used in \"service availability update and new service registration\" procedure", + "operationId": "Services_POST", + "tags": [ + "services" + ], + "responses": { + "201": { + "$ref": "#/components/responses/Services.201" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + }, + "requestBody": { + "$ref": "#/components/requestBodies/Services.Post" + } + } + }, + "/services/{serviceId}": { + "parameters": [ + { + "$ref": "#/components/parameters/Path.ServiceId" + } + ], + "get": { + "description": "This method retrieves information about a meService resource. This method is typically used in \"service availability query\" procedure", + "operationId": "ServicesServiceId_GET", + "tags": [ + "services" + ], + "responses": { + "200": { + "$ref": "#/components/responses/ServicesServiceId.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" } } }, - "Query.AppSoftVersion": { - "name": "appSoftVersion", - "in": "query", - "description": "Software version of the MEC application", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" + "put": { + "description": "This method updates the information about a meService resource", + "operationId": "ServicesServiceId_PUT", + "tags": [ + "services" + ], + "responses": { + "200": { + "$ref": "#/components/responses/ServicesServiceId.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + }, + "412": { + "$ref": "#/components/responses/Error.412" + } + }, + "requestBody": { + "$ref": "#/components/requestBodies/ServicesServiceId" + } + } + }, + "/timing/current_time": { + "get": { + "description": "This method retrieves the information of the platform's current time which corresponds to the get platform time procedure", + "operationId": "TimingCurrentTime_GET", + "tags": [ + "timing" + ], + "responses": { + "200": { + "$ref": "#/components/responses/TimingCurrentTime.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + } + }, + "/timing/timing_caps": { + "get": { + "description": "This method retrieves the information of the platform's timing capabilities which corresponds to the timing capabilities query", + "operationId": "TimingCaps_GET", + "tags": [ + "timing" + ], + "responses": { + "200": { + "$ref": "#/components/responses/TimingCaps.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + } + }, + "/transports": { + "get": { + "description": "This method retrieves information about a list of available transports. This method is typically used by a service-producing application to discover transports provided by the mobile edge platform in the \"transport information query\" procedure", + "operationId": "Transports_GET", + "tags": [ + "transports" + ], + "responses": { + "200": { + "$ref": "#/components/responses/Transports.200" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + } + } + }, + "components": { + "schemas": { + "Empty": { + "description": "Empty schema" + }, + "AppTerminationNotification.MaxGracefulTimeout": { + "description": "Maximum timeout value in seconds for graceful termination or graceful stop of an application instance.", + "type": "integer", + "format": "uint32", + "example": 10 + }, + "AppTerminationNotification.NotificationType": { + "description": "Shall be set to AppTerminationNotification.", + "type": "string", + "example": "AppTerminationNotification" + }, + "AppTerminationNotification": { + "description": "This type represents the information that the mobile edge platform notifies the subscribed application instance about the corresponding application instance termination/stop.", + "type": "object", + "required": [ + "notificationType", + "maxGracefulTimeout", + "_links" + ], + "properties": { + "notificationType": { + "$ref": "#/components/schemas/AppTerminationNotification.NotificationType" + }, + "maxGracefulTimeout": { + "$ref": "#/components/schemas/AppTerminationNotification.MaxGracefulTimeout" + }, + "_links": { + "$ref": "#/components/schemas/Subscription" + } + } + }, + "AppTerminationNotificationSubscription.AppInstanceId": { + "description": "It is used as the filtering criterion for the subscribed events.", + "type": "string", + "example": "ID1" + }, + "AppTerminationNotificationSubscription.CallbackReference": { + "description": "URI selected by the mobile edge application instance to receive notifications on the subscribed mobile edge application instance management information. This shall be included in both the request and the response.", + "type": "string", + "format": "uri" + }, + "AppTerminationNotificationSubscription": { + "description": "This type represents the information that the mobile edge platform notifies the subscribed application instance about the corresponding application instance termination/stop.", + "type": "object", + "required": [ + "subscriptionType", + "callbackReference", + "_links", + "appInstanceId" + ], + "properties": { + "subscriptionType": { + "$ref": "#/components/schemas/AppTerminationNotificationSubscription.SubscriptionType" + }, + "callbackReference": { + "$ref": "#/components/schemas/AppTerminationNotificationSubscription.CallbackReference" + }, + "_links": { + "$ref": "#/components/schemas/Self" + }, + "appInstanceId": { + "$ref": "#/components/schemas/AppTerminationNotificationSubscription.AppInstanceId" + } + } + }, + "AppTerminationNotificationSubscription.SubscriptionType": { + "description": "Shall be set to AppTerminationNotificationSubscription.", + "type": "string", + "example": "AppTerminationNotificationSubscription" + }, + "CategoryRef.Href": { + "description": "Reference of the catalogue", + "type": "string", + "example": "catItem1" + }, + "CategoryRef.Id": { + "description": "Unique identifier of the category", + "type": "string", + "example": "id12345" + }, + "CategoryRef.Name": { + "description": "Name of the category", + "type": "string", + "example": "RNI" + }, + "CategoryRef.Version": { + "description": "Category version", + "type": "string", + "example": "version1" + }, + "CategoryRef": { + "description": "This type represents the category reference", + "type": "object", + "required": [ + "href", + "id", + "name", + "version" + ], + "properties": { + "href": { + "$ref": "#/components/schemas/CategoryRef.Href" + }, + "id": { + "$ref": "#/components/schemas/CategoryRef.Id" + }, + "name": { + "$ref": "#/components/schemas/CategoryRef.Name" + }, + "version": { + "$ref": "#/components/schemas/CategoryRef.Version" + } + } + }, + "CurrentTime": { + "description": "This type represents the information provided by the mobile edge platform in response to the Get Platform Time Request message.", + "type": "object", + "required": [ + "nanoSeconds", + "seconds", + "timeSourceStatus" + ], + "properties": { + "seconds": { + "type": "integer", + "format": "uint32", + "description": "The seconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC", + "example": 1577836800 + }, + "nanoSeconds": { + "type": "integer", + "format": "uint32", + "description": "The nanoseconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC", + "example": 0 + }, + "timeSourceStatus": { + "type": "string", + "enum": [ + "TRACEABLE", + "NONTRACEABLE" + ], + "description": "Platform Time Source status. 1 = TRACEABLE - time source is locked to the UTC time source. 2 = NONTRACEABLE - time source is not locked to the UTC time source", + "example": "TRACEABLE" + } + } + }, + "DestinationInterface.InterfaceType": { + "description": "Type of the interface", + "type": "string", + "enum": [ + "TUNNEL", + "MAC", + "IP" + ], + "example": "TUNNEL" + }, + "DestinationInterface.IpAddress": { + "description": "IP address of the remote destination", + "type": "string", + "example": "192.0.2.0" + }, + "DestinationInterface.MacAddress": { + "description": "Source address identifies the MAC address of the interface", + "type": "string", + "example": "02-00-00-00-00-00" + }, + "DestinationInterface": { + "description": "This type represents the destination interface.", + "type": "object", + "required": [ + "interfaceType" + ], + "properties": { + "interfaceType": { + "$ref": "#/components/schemas/DestinationInterface.InterfaceType" + }, + "tunnelInfo": { + "$ref": "#/components/schemas/TunnelInfo" + }, + "srcMacAddress": { + "$ref": "#/components/schemas/DestinationInterface.MacAddress" + }, + "dstMacAddress": { + "$ref": "#/components/schemas/DestinationInterface.MacAddress" + }, + "dstIpAddress": { + "$ref": "#/components/schemas/DestinationInterface.IpAddress" + } + } + }, + "DnsRule.DomainName": { + "description": "FQDN resolved by the DNS rule", + "type": "string", + "example": "www.example.com" + }, + "DnsRule.Id": { + "description": "Identifies the DNS Rule", + "type": "string", + "example": "dnsRule1" + }, + "DnsRule.IpAddress": { + "description": "IP address associated with the FQDN resolved by the DNS rule", + "type": "string", + "example": "192.0.2.0" + }, + "DnsRule.IpAddressType": { + "description": "IP address type", + "type": "string", + "enum": [ + "IP_V6", + "IP_V4" + ], + "example": "IP_V6" + }, + "DnsRule.State": { + "description": "DNS rule state", + "type": "string", + "enum": [ + "ACTIVE", + "INACTIVE" + ], + "example": "ACTIVE" + }, + "DnsRule.Ttl": { + "description": "Time to live value", + "type": "integer", + "format": "uint32", + "example": "?" + }, + "DnsRule": { + "description": "This type represents the general information of a DNS rule.", + "type": "object", + "required": [ + "dnsRuleId", + "domainName", + "ipAddressType", + "ipAddress", + "state" + ], + "properties": { + "dnsRuleId": { + "$ref": "#/components/schemas/DnsRule.Id" + }, + "domainName": { + "$ref": "#/components/schemas/DnsRule.DomainName" + }, + "ipAddressType": { + "$ref": "#/components/schemas/DnsRule.IpAddressType" + }, + "ipAddress": { + "$ref": "#/components/schemas/DnsRule.IpAddress" + }, + "ttl": { + "$ref": "#/components/schemas/DnsRule.Ttl" + }, + "state": { + "$ref": "#/components/schemas/DnsRule.State" + } + } + }, + "EndPointInfo.Address.Host": { + "description": "Host portion of the address", + "type": "string", + "example": "192.0.2.0" + }, + "EndPointInfo.Address_Port": { + "description": "Port portion of the address", + "type": "integer", + "format": "uint32", + "example": 8080 + }, + "EndPointInfo.Address": { + "description": "A IP address and port pair", + "type": "object", + "required": [ + "host", + "port" + ], + "properties": { + "host": { + "$ref": "#/components/schemas/EndPointInfo.Address.Host" + }, + "port": { + "$ref": "#/components/schemas/EndPointInfo.Address_Port" + } + } + }, + "EndPointInfo.Addresses": { + "description": "Entry point information of the service as one or more pairs of IP address and port", + "type": "object", + "required": [ + "addresses" + ], + "properties": { + "addresses": { + "type": "array", + "minItems": 0, + "items": { + "$ref": "#/components/schemas/EndPointInfo.Address" + } + } + } + }, + "EndPointInfo.Alternative": { + "description": "Entry point information of the service in a format defined by an implementation, or in an external specification.", + "type": "object", + "required": [ + "alternative" + ], + "properties": { + "alternative": { + "type": "object" + } + } + }, + "EndPointInfo.Uri": { + "description": "Entry point information of the service", + "type": "string", + "format": "uri", + "example": "/meMp1/service/EntryPoint" + }, + "EndPointInfo.Uris": { + "description": "Entry point information of the service as string, formatted according to URI syntax", + "type": "object", + "required": [ + "uris" + ], + "properties": { + "uris": { + "type": "array", + "minItems": 0, + "items": { + "$ref": "#/components/schemas/EndPointInfo.Uri" + } + } + } + }, + "LinkType": { + "description": "This type represents a type of link and may be referenced from data structures", + "type": "object", + "properties": { + "href": { + "$ref": "#/components/schemas/Href" + } + } + }, + "Href": { + "description": "URI referring to a resource", + "type": "string", + "format": "uri", + "example": "/meMp1/example" + }, + "Mp1SubscriptionLinkList.Links": { + "description": "Self-referring URI.", + "type": "object", + "required": [ + "self" + ], + "properties": { + "self": { + "$ref": "#/components/schemas/LinkType" + }, + "subscription": { + "description": "Subscription list", + "type": "array", + "items": { + "$ref": "#/components/schemas/Mp1SubscriptionLinkList.Subscription" + } + } + } + }, + "Mp1SubscriptionLinkList.Subscription": { + "description": "A link to a subscription.", + "type": "object", + "required": [ + "href", + "rel" + ], + "properties": { + "href": { + "$ref": "#/components/schemas/Href" + }, + "rel": { + "description": "The values are as defined in the \"subscriptionType\" attribute for each different Mp1 event subscription data type.", + "type": "string", + "enum": [ + "AppTerminationNotificationSubscription", + "SerAvailabilityNotificationSubscription" + ] + } + } + }, + "Mp1SubscriptionLinkList": { + "description": "This type represents a list of links related to currently existing subscriptions for a mobile edge application instance. This information is returned when sending a request to receive current subscriptions.", + "type": "object", + "required": [ + "_links" + ], + "properties": { + "_links": { + "$ref": "#/components/schemas/Mp1SubscriptionLinkList.Links" + } + } + }, + "ProblemDetails": { + "type": "object", + "properties": { + "type": { + "$ref": "#/components/schemas/Problem.type" + }, + "title": { + "$ref": "#/components/schemas/Problem.title" + }, + "status": { + "$ref": "#/components/schemas/Problem.status" + }, + "detail": { + "$ref": "#/components/schemas/Problem.detail" + }, + "instance": { + "$ref": "#/components/schemas/Problem.instance" + } + } + }, + "Problem.detail": { + "type": "string", + "description": "A human-readable explanation specific to this occurrence of the problem" + }, + "Problem.instance": { + "type": "string", + "format": "uri", + "description": "A URI reference that identifies the specific occurrence of the problem" + }, + "Problem.status": { + "type": "integer", + "format": "uint32", + "description": "The HTTP status code for this occurrence of the problem" + }, + "Problem.title": { + "type": "string", + "description": "A short, human-readable summary of the problem type" + }, + "Problem.type": { + "type": "string", + "format": "uri", + "description": "A URI reference according to IETF RFC 3986 that identifies the problem type" + }, + "SecurityInfo.OAuth2Info.GrantTypes": { + "description": "List of supported OAuth 2.0 grant types", + "type": "string", + "enum": [ + "OAUTH2_AUTHORIZATION_CODE", + "OAUTH2_IMPLICIT_GRANT", + "OAUTH2_RESOURCE_OWNER", + "OAUTH2_CLIENT_CREDENTIALS" + ], + "example": "OAUTH2_CLIENT_CREDENTIALS" + }, + "SecurityInfo.OAuth2Info.TokenEndpoint": { + "description": "The token endpoint", + "type": "string", + "format": "uri", + "example": "/meMp1/security/TokenEndPoint" + }, + "SecurityInfo.OAuth2Info": { + "description": "Parameters related to use of OAuth 2.0", + "required": [ + "grantTypes", + "tokenEndpoint" + ], + "properties": { + "grantTypes": { + "description": "List of supported OAuth 2.0 grant types.", + "type": "array", + "minItems": 1, + "maxItems": 4, + "items": { + "$ref": "#/components/schemas/SecurityInfo.OAuth2Info.GrantTypes" + } + }, + "tokenEndpoint": { + "$ref": "#/components/schemas/SecurityInfo.OAuth2Info.TokenEndpoint" + } + }, + "type": "object" + }, + "SecurityInfo": { + "description": "This type represents security information related to a transport", + "type": "object", + "properties": { + "oAuth2Info": { + "$ref": "#/components/schemas/SecurityInfo.OAuth2Info" + } + } + }, + "Self": { + "description": "Self-referring URI.", + "type": "object", + "required": [ + "self" + ], + "properties": { + "self": { + "$ref": "#/components/schemas/LinkType" + } + }, + "readOnly": true + }, + "SerAvailabilityNotificationSubscription.CallbackReference": { + "description": "URI selected by the mobile edge application instance to receive notifications on the subscribed mobile edge service availability information. This shall be included in both the request and the response.", + "type": "string", + "format": "uri" + }, + "SerAvailabilityNotificationSubscription": { + "description": "This type represents a subscription to the notifications from the mobile edge platform regarding the availability of a mobile edge service or a list of mobile edge services.", + "type": "object", + "required": [ + "subscriptionType", + "callbackReference", + "_links", + "filteringCriteria" + ], + "properties": { + "subscriptionType": { + "$ref": "#/components/schemas/SerAvailabilityNotificationSubscription.SubscriptionType" + }, + "callbackReference": { + "$ref": "#/components/schemas/SerAvailabilityNotificationSubscription.CallbackReference" + }, + "_links": { + "$ref": "#/components/schemas/Self" + }, + "filteringCriteria": { + "$ref": "#/components/schemas/ServiceInfo" + } + } + }, + "SerAvailabilityNotificationSubscription.SubscriptionType": { + "description": "Shall be set to SerAvailabilityNotificationSubscription.", + "type": "string", + "example": "SerAvailabilityNotificationSubscription" + }, + "ServiceAvailabilityNotification": { + "description": "This type represents the service availability information.", + "type": "object", + "required": [ + "notificationType", + "services", + "_links" + ], + "properties": { + "notificationType": { + "$ref": "#/components/schemas/SerAvailabilityNotificationSubscription.SubscriptionType" + }, + "services": { + "type": "array", + "items": { + "$ref": "#/components/schemas/ServiceInfo" + } + }, + "_links": { + "$ref": "#/components/schemas/Subscription" + } + } + }, + "SerializerTypes": { + "description": "The enumeration SerializerTypes represents types of serializers", + "type": "string", + "enum": [ + "JSON", + "XML", + "PROTOBUF3" + ], + "example": "JSON" + }, + "ServiceInfo.SerInstanceId": { + "description": "Identifier of the service instance assigned by the MEPM / mobile edge platform.", + "type": "string", + "readOnly": true, + "example": "ServiceInstance123" + }, + "ServiceInfo.SerName": { + "description": "The name of the service. This is how the service producing mobile edge application identifies the service instance it produces.", + "type": "string", + "example": "ExampleService" + }, + "ServiceInfo.State": { + "description": "Contains the state", + "type": "string", + "enum": [ + "ACTIVE", + "INACTIVE" + ], + "example": "ACTIVE" + }, + "ServiceInfo.TransportId": { + "description": "Identifier of the platform-provided transport to be used by the service. Valid identifiers may be obtained using the \"Transport information query\" procedure. May be present in POST requests to signal the use of a platform-provided transport for the service, and shall be absent otherwise.", + "type": "string", + "writeOnly": true, + "example": "Rest1" + }, + "ServiceInfo.Version": { + "description": "Service version", + "type": "string", + "example": "ServiceVersion1" + }, + "ServiceInfo.Post": { + "description": "This type represents the general information of a mobile edge service.", + "type": "object", + "required": [ + "serName", + "version", + "state", + "serializer" + ], + "oneOf": [ + { + "required": [ + "transportId" + ] + }, + { + "required": [ + "transportInfo" + ] + } + ], + "properties": { + "serInstanceId": { + "$ref": "#/components/schemas/ServiceInfo.SerInstanceId" + }, + "serName": { + "$ref": "#/components/schemas/ServiceInfo.SerName" + }, + "serCategory": { + "$ref": "#/components/schemas/CategoryRef" + }, + "version": { + "$ref": "#/components/schemas/ServiceInfo.Version" + }, + "state": { + "$ref": "#/components/schemas/ServiceInfo.State" + }, + "transportId": { + "$ref": "#/components/schemas/ServiceInfo.TransportId" + }, + "transportInfo": { + "$ref": "#/components/schemas/TransportInfo" + }, + "serializer": { + "$ref": "#/components/schemas/SerializerTypes" + } + } + }, + "ServiceInfo": { + "description": "This type represents the general information of a mobile edge service.", + "type": "object", + "required": [ + "serName", + "version", + "state", + "transportInfo", + "serializer" + ], + "properties": { + "serInstanceId": { + "$ref": "#/components/schemas/ServiceInfo.SerInstanceId" + }, + "serName": { + "$ref": "#/components/schemas/ServiceInfo.SerName" + }, + "serCategory": { + "$ref": "#/components/schemas/CategoryRef" + }, + "version": { + "$ref": "#/components/schemas/ServiceInfo.Version" + }, + "state": { + "$ref": "#/components/schemas/ServiceInfo.State" + }, + "transportInfo": { + "$ref": "#/components/schemas/TransportInfo" + }, + "serializer": { + "$ref": "#/components/schemas/SerializerTypes" + } + } + }, + "Subscription": { + "description": "A link to the related subscription", + "type": "object", + "required": [ + "subscription" + ], + "properties": { + "subscription": { + "$ref": "#/components/schemas/LinkType" + } + } + }, + "TimingCaps.NtpServers.AuthenticationKeyNum": { + "description": "Authentication key number", + "type": "integer", + "format": "uint32", + "example": 1 + }, + "TimingCaps.NtpServers.AuthenticationOption": { + "description": "NTP authentication option", + "type": "string", + "enum": [ + "NONE", + "SYMMETRIC_KEY", + "AUTO_KEY" + ], + "example": "NONE" + }, + "TimingCaps.NtpServers.DelayReqMaxRate": { + "description": "Acceptable maximum rate of the Delay_Req messages in packets per second", + "type": "integer", + "format": "uint32", + "example": 10 + }, + "TimingCaps.NtpServers.LocalPriority": { + "description": "NTP server local priority", + "type": "integer", + "format": "uint32", + "example": 1 + }, + "TimingCaps.NtpServers.MaxPollingInterval": { + "description": "Maximum poll interval for NTP messages, in seconds as a power of two. Range 3...17", + "type": "integer", + "format": "uint32", + "example": 17 + }, + "TimingCaps.NtpServers.MinPollingInterval": { + "description": "Minimum poll interval for NTP messages, in seconds as a power of two. Range 3...17", + "type": "integer", + "format": "uint32", + "example": 3 + }, + "TimingCaps.NtpServers.NtpServerAddr": { + "description": "NTP server address", + "type": "string", + "example": "192.0.2.0" + }, + "TimingCaps.NtpServers.NtpServerAddrType": { + "description": "Address type of NTP server", + "type": "string", + "enum": [ + "IP_ADDRESS", + "DNS_NAME" + ], + "example": "IP_ADDRESS" + }, + "TimingCaps.NtpServers_PtpMasterIpAddress": { + "description": "PTP Master IP Address", + "type": "string", + "example": "192.0.2.0" + }, + "TimingCaps.NtpServers_PtpMasterLocalPriority": { + "description": "PTP Master local priority", + "type": "integer", + "format": "uint32", + "example": 1 + }, + "TimingCaps.NtpServers": { + "description": "NTP server detail.", + "type": "object", + "required": [ + "ntpServerAddrType", + "ntpServerAddr", + "minPollingInterval", + "maxPollingInterval", + "localPriority", + "authenticationOption", + "authenticationKeyNum" + ], + "properties": { + "ntpServerAddrType": { + "$ref": "#/components/schemas/TimingCaps.NtpServers.NtpServerAddrType" + }, + "ntpServerAddr": { + "$ref": "#/components/schemas/TimingCaps.NtpServers.NtpServerAddr" + }, + "minPollingInterval": { + "$ref": "#/components/schemas/TimingCaps.NtpServers.MinPollingInterval" + }, + "maxPollingInterval": { + "$ref": "#/components/schemas/TimingCaps.NtpServers.MaxPollingInterval" + }, + "localPriority": { + "$ref": "#/components/schemas/TimingCaps.NtpServers.LocalPriority" + }, + "authenticationOption": { + "$ref": "#/components/schemas/TimingCaps.NtpServers.AuthenticationOption" + }, + "authenticationKeyNum": { + "$ref": "#/components/schemas/TimingCaps.NtpServers.AuthenticationKeyNum" + } + } + }, + "TimingCaps_PtpMasters": { + "description": "NTP server detail.", + "type": "object", + "required": [ + "ptpMasterIpAddress", + "ptpMasterLocalPriority", + "delayReqMaxRate" + ], + "properties": { + "ptpMasterIpAddress": { + "$ref": "#/components/schemas/TimingCaps.NtpServers_PtpMasterIpAddress" + }, + "ptpMasterLocalPriority": { + "$ref": "#/components/schemas/TimingCaps.NtpServers_PtpMasterLocalPriority" + }, + "delayReqMaxRate": { + "$ref": "#/components/schemas/TimingCaps.NtpServers.DelayReqMaxRate" + } + } + }, + "TimingCaps.TimeStamp": { + "description": "time", + "type": "object", + "required": [ + "nanoSeconds", + "seconds" + ], + "properties": { + "seconds": { + "type": "integer", + "format": "uint32", + "description": "The seconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC", + "example": 1577836800 + }, + "nanoSeconds": { + "type": "integer", + "format": "uint32", + "description": "The nanoseconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC", + "example": 0 + } + } + }, + "TimingCaps": { + "description": "This type represents the information provided by the mobile edge platform in response to the Timing capabilities Query message.", + "type": "object", + "properties": { + "timeStamp": { + "$ref": "#/components/schemas/TimingCaps.TimeStamp" + }, + "ntpServers": { + "description": "Available NTP servers", + "type": "array", + "items": { + "$ref": "#/components/schemas/TimingCaps.NtpServers" + } + }, + "ptpMasters": { + "description": "Available PTP Masters", + "type": "array", + "items": { + "$ref": "#/components/schemas/TimingCaps_PtpMasters" + } + } + } + }, + "TrafficFilter.Address": { + "description": "Identify the traffic ip address.", + "type": "string", + "example": "192.168.1.1" + }, + "TrafficFilter.DSCP": { + "description": "Used to match all IPv4 packets that have the same Differentiated Services Code Point (DSCP)", + "type": "integer", + "format": "uint32", + "example": 0 + }, + "TrafficFilter.Port": { + "description": "A port", + "type": "string", + "example": "8080" + }, + "TrafficFilter.Protocol": { + "description": "Protocol of the traffic filter", + "type": "string", + "example": "?" + }, + "TrafficFilter.QCI": { + "description": "Used to match all packets that have the same Quality Class Indicator (QCI).", + "type": "integer", + "format": "uint32", + "example": 1 + }, + "TrafficFilter.TC": { + "description": "Used to match all IPv6 packets that have the same Traffic Class.", + "type": "integer", + "format": "uint32", + "example": 1 + }, + "TrafficFilter.Token": { + "description": "Used for token based traffic rule", + "type": "string", + "example": "?" + }, + "TrafficFilter.TunnelAddress": { + "description": "Used for GTP tunnel based traffic rule", + "type": "string", + "example": "?" + }, + "TrafficFilter.TunnelPort": { + "description": "Used for GTP tunnel based traffic rule", + "type": "string", + "example": "?" + }, + "TrafficFilter": { + "description": "This type represents the traffic filter.", + "type": "object", + "properties": { + "srcAddress": { + "description": "An IP address or a range of IP address. For IPv4, the IP address could be an IP address plus mask, or an individual IP address, or a range of IP addresses. For IPv6, the IP address could be an IP prefix, or a range of IP prefixes.", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.Address" + } + }, + "dstAddress": { + "description": "An IP address or a range of IP address. For IPv4, the IP address could be an IP address plus mask, or an individual IP address, or a range of IP addresses. For IPv6, the IP address could be an IP prefix, or a range of IP prefixes.", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.Address" + } + }, + "srcPort": { + "description": "A port or a range of ports", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.Port" + } + }, + "dstPort": { + "description": "A port or a range of ports", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.Port" + } + }, + "protocol": { + "description": "Specify the protocol of the traffic filter", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.Protocol" + } + }, + "token": { + "description": "Used for token based traffic rule", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.Token" + } + }, + "srcTunnelAddress": { + "description": "Used for GTP tunnel based traffic rule", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.TunnelAddress" + } + }, + "tgtTunnelAddress": { + "description": "Used for GTP tunnel based traffic rule", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.TunnelAddress" + } + }, + "srcTunnelPort": { + "description": "Used for GTP tunnel based traffic rule", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.TunnelPort" + } + }, + "dstTunnelPort": { + "description": "Used for GTP tunnel based traffic rule", + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter.TunnelPort" + } + }, + "qCI": { + "$ref": "#/components/schemas/TrafficFilter.QCI" + }, + "dSCP": { + "$ref": "#/components/schemas/TrafficFilter.DSCP" + }, + "tC": { + "$ref": "#/components/schemas/TrafficFilter.TC" + } + } + }, + "TrafficRule.Action": { + "description": "The action of the ME host data plane when a packet matches the trafficFilter", + "type": "string", + "enum": [ + "DROP", + "FORWARD_DECAPSULATED", + "FORWARD_AS_IS", + "PASSTHROUGH", + "DUPLICATE_DECAPSULATED", + "DUPLICATE_AS_IS" + ], + "example": "DROP" + }, + "TrafficRule.FilterType": { + "description": "Definition of filter per FLOW or PACKET. If flow the filter match UE->EPC packet and the reverse packet is handled in the same context", + "type": "string", + "enum": [ + "FLOW", + "PACKET" + ], + "example": "FLOW" + }, + "TrafficRule.Id": { + "description": "Identify the traffic rule.", + "type": "string", + "example": "TrafficRule1" + }, + "TrafficRule_Priority": { + "description": "Priority of this traffic rule. If traffic rule conflicts, the one with higher priority take precedence", + "type": "integer", + "format": "uint32", + "example": 1 + }, + "TrafficRule.State": { + "description": "Contains the traffic rule state", + "type": "string", + "enum": [ + "ACTIVE", + "INACTIVE" + ], + "example": "ACTIVE" + }, + "TrafficRule": { + "description": "This type represents the general information of a traffic rule.", + "type": "object", + "required": [ + "trafficRuleId", + "filterType", + "priority", + "trafficFilter", + "action", + "state" + ], + "properties": { + "trafficRuleId": { + "$ref": "#/components/schemas/TrafficRule.Id" + }, + "filterType": { + "$ref": "#/components/schemas/TrafficRule.FilterType" + }, + "priority": { + "$ref": "#/components/schemas/TrafficRule_Priority" + }, + "trafficFilter": { + "type": "array", + "items": { + "$ref": "#/components/schemas/TrafficFilter" + } + }, + "action": { + "$ref": "#/components/schemas/TrafficRule.Action" + }, + "dstInterface": { + "$ref": "#/components/schemas/DestinationInterface" + }, + "state": { + "$ref": "#/components/schemas/TrafficRule.State" + } + } + }, + "TransportInfo.Description": { + "description": "Human-readable description of this transport", + "type": "string", + "example": "REST API" + }, + "TransportInfo.Id": { + "description": "The identifier of this transport", + "type": "string", + "example": "TransId12345" + }, + "TransportInfo.ImplSpecificInfo": { + "description": "Additional implementation specific details of the transport", + "type": "object" + }, + "TransportInfo.Name": { + "description": "The name of this transport", + "type": "string", + "example": "REST" + }, + "TransportInfo.Protocol": { + "description": "The name of the protocol used. Shall be set to HTTP for a REST API.", + "type": "string", + "example": "HTTP" + }, + "TransportInfo.Version": { + "description": "The version of the protocol used", + "type": "string", + "example": "2.0" + }, + "TransportInfo": { + "description": "This type represents the general information of a mobile edge service.", + "type": "object", + "required": [ + "id", + "name", + "type", + "protocol", + "version", + "endpoint", + "security" + ], + "properties": { + "id": { + "$ref": "#/components/schemas/TransportInfo.Id" + }, + "name": { + "$ref": "#/components/schemas/TransportInfo.Name" + }, + "description": { + "$ref": "#/components/schemas/TransportInfo.Description" + }, + "type": { + "$ref": "#/components/schemas/TransportTypes" + }, + "protocol": { + "$ref": "#/components/schemas/TransportInfo.Protocol" + }, + "version": { + "$ref": "#/components/schemas/TransportInfo.Version" + }, + "endpoint": { + "description": "This type represents information about a transport endpoint", + "type": "object", + "oneOf": [ + { + "$ref": "#/components/schemas/EndPointInfo.Uris" + }, + { + "$ref": "#/components/schemas/EndPointInfo.Addresses" + }, + { + "$ref": "#/components/schemas/EndPointInfo.Alternative" + } + ] + }, + "security": { + "$ref": "#/components/schemas/SecurityInfo" + }, + "implSpecificInfo": { + "$ref": "#/components/schemas/TransportInfo.ImplSpecificInfo" + } + } + }, + "TransportTypes": { + "description": "The enumeration TransportTypes represents types of transports", + "type": "string", + "enum": [ + "REST_HTTP", + "MB_TOPIC_BASED", + "MB_ROUTING", + "MB_PUBSUB", + "RPC", + "RPC_STREAMING", + "WEBSOCKET" + ], + "example": "REST_HTTP" + }, + "TunnelInfo.TunnelDstAddress": { + "description": "Destination address of the tunnel", + "type": "string", + "example": "?" + }, + "TunnelInfo.TunnelSrcAddress": { + "description": "Source address of the tunnel", + "type": "string", + "example": "?" + }, + "TunnelInfo.TunnelType": { + "description": "This type represents the tunnel information.", + "type": "string", + "enum": [ + "GTP_U", + "GRE" + ], + "example": "GTP_U" + }, + "TunnelInfo": { + "description": "This type represents the tunnel information.", + "type": "object", + "required": [ + "tunnelType" + ], + "properties": { + "tunnelType": { + "$ref": "#/components/schemas/TunnelInfo.TunnelType" + }, + "tunnelDstAddress": { + "$ref": "#/components/schemas/TunnelInfo.TunnelDstAddress" + }, + "tunnelSrcAddress": { + "$ref": "#/components/schemas/TunnelInfo.TunnelSrcAddress" + } + } + } + }, + "parameters": { + "Path.AppInstanceId": { + "name": "appInstanceId", + "description": "Represents a mobile edge application instance. Note that the appInstanceId is allocated by the mobile edge platform manager.", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + "Path.DnsRuleId": { + "name": "dnsRuleId", + "description": "Represents a DNS rule.", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + "Path.SubscriptionId": { + "name": "subscriptionId", + "description": "Represents a subscription to the notifications from the mobile edge platform.", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + "Path.SubscriptionType": { + "name": "subscriptionType", + "description": "Represents a subscription type to the notifications from the mobile edge platform.", + "in": "path", + "required": true, + "schema": { + "type": "string", + "enum": [ + "AppTerminationNotificationSubscription", + "SerAvailabilityNotificationSubscription" + ] + } + }, + "Path.ServiceId": { + "name": "serviceId", + "description": "Represents a mobile edge service instance.", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + "Path.TrafficRuleId": { + "name": "trafficRuleId", + "description": "Represents a traffic rule.", + "in": "path", + "required": true, + "schema": { + "type": "string" + } + }, + "Query.Ser_category_id": { + "name": "ser_category_id", + "description": "A mobile edge application instance may use ser_category_id as an input parameter to query the availability of a list of mobile edge service instances in a serCategory. Either \"ser_instance_id\" or \"ser_name\" or \"ser_category_id\" or none of them shall be present.", + "in": "query", + "required": false, + "schema": { + "type": "string" + } + }, + "Query.Ser_instance_id": { + "name": "ser_instance_id", + "description": "A mobile edge application instance may use multiple ser_instance_ids as an input parameter to query the availability of a list of mobile edge service instances. Either \"ser_instance_id\" or \"ser_name\" or \"ser_category_id\" or none of them shall be present.", + "in": "query", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + "Query.Ser_name": { + "name": "ser_name", + "description": "A mobile edge application instance may use multiple ser_names as an input parameter to query the availability of a list of mobile edge service instances. Either \"ser_instance_id\" or \"ser_name\" or \"ser_category_id\" or none of them shall be present.", + "in": "query", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + } + }, + "responses": { + "ApplicationsDnsRules.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", + "content": { + "application/json": { + "schema": { + "type": "array", + "minItems": 0, + "items": { + "$ref": "#/components/schemas/DnsRule" + } + }, + "examples": { + "DnsRules": { + "$ref": "#/components/examples/DnsRules" + } + } + } + }, + "links": { + "getIndividualMeDNSRule": { + "$ref": "#/components/links/GetIndividualMeDNSRule" + }, + "putIndividualMeDNSRule": { + "$ref": "#/components/links/PutIndividualMeDNSRule" + } + } + }, + "ApplicationsDnsRule.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DnsRule" + }, + "examples": { + "DnsRule": { + "$ref": "#/components/examples/DnsRule" + } + } + } + } + }, + "ApplicationsSubscriptions.200": { + "description": "Upon success, a response body containing the list of links to the requested subscriptions is returned.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/Mp1SubscriptionLinkList" + } + } + }, + "links": { + "getIndividualMeMp1SubscriptionLinkList": { + "$ref": "#/components/links/GetIndividualMeMp1SubscriptionLinkList" + }, + "delIndividualMeMp1SubscriptionLinkList": { + "$ref": "#/components/links/DelIndividualMeMp1SubscriptionLinkList" + } + } + }, + "ApplicationsSubscriptions.201": { + "description": "Entity body in the request contains a subscription to the mobile edge service availability notifications that is to be created.", + "headers": { + "location": { + "description": "The resource URI of the created resource", + "schema": { + "type": "string", + "format": "uri" + } + } + }, + "content": { + "application/json": { + "schema": { + "oneOf": [ + { + "$ref": "#/components/schemas/AppTerminationNotificationSubscription" + }, + { + "$ref": "#/components/schemas/SerAvailabilityNotificationSubscription" + } + ] + } + } + }, + "links": { + "getIndividualMeMp1Subscription": { + "$ref": "#/components/links/GetIndividualMeMp1Subscription" + }, + "delIndividualMeMp1Subscription": { + "$ref": "#/components/links/DelIndividualMeMp1Subscription" + } + } + }, + "ApplicationsSubscription.200": { + "description": "Upon success, a response body containing the requested subscription is returned.", + "content": { + "application/json": { + "schema": { + "oneOf": [ + { + "$ref": "#/components/schemas/AppTerminationNotificationSubscription" + }, + { + "$ref": "#/components/schemas/SerAvailabilityNotificationSubscription" + } + ] + } + } + } + }, + "ApplicationsTrafficRules.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", + "content": { + "application/json": { + "schema": { + "type": "array", + "minItems": 0, + "items": { + "$ref": "#/components/schemas/TrafficRule" + } + }, + "examples": { + "TrafficRules": { + "$ref": "#/components/examples/TrafficRules" + } + } + } + }, + "links": { + "getIndividualMeTrafficRule": { + "$ref": "#/components/links/GetIndividualMeTrafficRule" + }, + "putIndividualMeTrafficRule": { + "$ref": "#/components/links/PutIndividualMeTrafficRule" } } }, - "Query.ServiceCont": { - "name": "serviceCont", - "in": "query", - "description": "Required service continuity mode for this application", - "required": false, - "schema": { - "type": "string", - "enum": [ - "SERVICE_CONTINUITY_NOT_REQUIRED", - "SERVICE_CONTINUITY_REQUIRED" - ] + "ApplicationsTrafficRule.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/TrafficRule" + }, + "examples": { + "TrafficRule": { + "$ref": "#/components/examples/TrafficRule" + } + } + } } }, - "Query.VendorId": { - "name": "vendorId", - "in": "query", - "description": "Vendor identifier", - "required": false, - "schema": { - "type": "array", - "items": { - "type": "string" + "Services.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", + "content": { + "application/json": { + "schema": { + "type": "array", + "minItems": 0, + "items": { + "$ref": "#/components/schemas/ServiceInfo" + } + }, + "examples": { + "ServiceInfoList": { + "$ref": "#/components/examples/ServiceInfoList" + } + } + } + }, + "links": { + "getIndividualMeService": { + "$ref": "#/components/links/GetIndividualMeService" + }, + "putIndividualMeService": { + "$ref": "#/components/links/PutIndividualMeService" } } }, - "Path.ContextId": { - "name": "contextId", - "in": "path", - "description": "Uniquely identifies the application context in the MEC system. It is assigned by the MEC system and included in the response to an AppContext create.", - "required": true, - "schema": { - "type": "string" - } - } - }, - "requestBodies": { - "AppContext": { - "description": "Uniquely identifies the application context in the MEC system. It is assigned by the MEC system and included in the response to an AppContext create.", + "Services.201": { + "description": "Upon success, the HTTP response shall include a Location HTTP header that contains the resource URI of the created resource.", + "headers": { + "location": { + "description": "The resource URI of the created resource", + "schema": { + "type": "string", + "format": "uri" + } + } + }, "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AppContext" + "$ref": "#/components/schemas/ServiceInfo" + }, + "examples": { + "ServiceInfo": { + "$ref": "#/components/examples/ServiceInfo" + } } } }, - "required": true - } - }, - "responses": { - "AppContext": { - "description": "The response body contains the Application Context as it was created by the MEC system", + "links": { + "getIndividualMeService": { + "$ref": "#/components/links/GetIndividualMeService" + }, + "putIndividualMeService": { + "$ref": "#/components/links/PutIndividualMeService" + } + } + }, + "ServicesServiceId.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/AppContext" + "$ref": "#/components/schemas/ServiceInfo" + }, + "examples": { + "ServiceInfo": { + "$ref": "#/components/examples/ServiceInfo" + } } } } }, - "AppList": { - "description": "The response body contains the ApplicationList resource available for the querying UE application", + "TimingCurrentTime.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ApplicationList" + "$ref": "#/components/schemas/CurrentTime" } } } }, - "Error.400": { - "description": "Bad Request. It is used to indicate that incorrect parameters were passed to the request.", + "TimingCaps.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", "content": { - "application/problem+json": { + "application/json": { "schema": { - "$ref": "#/components/schemas/ProblemDetails" + "$ref": "#/components/schemas/TimingCaps" } - }, - "text/plain": { + } + } + }, + "Transports.200": { + "description": "It is used to indicate nonspecific success. The response body contains a representation of the resource.", + "content": { + "application/json": { "schema": { - "$ref": "#/components/schemas/Empty" + "type": "array", + "minItems": 0, + "items": { + "$ref": "#/components/schemas/TransportInfo" + } } } + }, + "links": { + "getTransportInfo": { + "$ref": "#/components/links/GetTransportInfo" + } } }, - "Error.401": { - "description": "Unauthorized. It is used when the client did not submit the appropriate credentials.", + "Error.400": { + "description": "Bad Request", "content": { "application/problem+json": { "schema": { @@ -309,7 +2110,7 @@ } }, "Error.403": { - "description": "Forbidden. The operation is not allowed given the current status of the resource. ", + "description": "Forbidden", "content": { "application/problem+json": { "schema": { @@ -319,7 +2120,7 @@ } }, "Error.404": { - "description": "Not Found. It is used when a client provided a URI that cannot be mapped to a valid resource URI.", + "description": "Not Found", "content": { "application/problem+json": { "schema": { @@ -332,286 +2133,396 @@ } } } - } - }, - "securitySchemes": { - "OauthSecurity": { - "type": "oauth2", - "flows": { - "clientCredentials": { - "tokenUrl": "https://oauth.exampleAPI/token", - "scopes": { - "all": "Single oauth2 scope for API" + }, + "Error.412": { + "description": "Precondition Failed", + "content": { + "application/problem+json": { + "schema": { + "$ref": "#/components/schemas/ProblemDetails" + } + }, + "text/plain": { + "schema": { + "$ref": "#/components/schemas/Empty" } } } } }, - "schemas": { - "Empty": { - "description": "Empty schema" - }, - "ProblemDetails": { - "type": "object", - "properties": { - "type": { - "$ref": "#/components/schemas/Problem.type" - }, - "title": { - "$ref": "#/components/schemas/Problem.title" - }, - "status": { - "$ref": "#/components/schemas/Problem.status" - }, - "detail": { - "$ref": "#/components/schemas/Problem.detail" - }, - "instance": { - "$ref": "#/components/schemas/Problem.instance" + "requestBodies": { + "ApplicationsDnsRule": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/DnsRule" + } } - } - }, - "Problem.type": { - "type": "string", - "format": "uri", - "description": "A URI reference according to IETF RFC 3986 that identifies the problem type" + }, + "description": "The updated state is included in the entity body of the request.", + "required": true }, - "Problem.title": { - "type": "string", - "description": "A short, human-readable summary of the problem type" + "ApplicationsSubscriptions": { + "content": { + "application/json": { + "schema": { + "oneOf": [ + { + "$ref": "#/components/schemas/AppTerminationNotificationSubscription" + }, + { + "$ref": "#/components/schemas/SerAvailabilityNotificationSubscription" + } + ] + } + } + }, + "description": "Entity body in the request contains a subscription to the mobile edge application termination notifications that is to be created.", + "required": true }, - "Problem.status": { - "type": "integer", - "format": "uint32", - "description": "The HTTP status code for this occurrence of the problem" + "ApplicationsTrafficRule": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/TrafficRule" + } + } + }, + "description": "One or more updated attributes that are allowed to be changed", + "required": true }, - "Problem.detail": { - "type": "string", - "description": "A human-readable explanation specific to this occurrence of the problem" + "Services": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ServiceInfo" + } + } + }, + "description": "New ServiceInfo with updated \"state\" is included as entity body of the request", + "required": true }, - "Problem.instance": { - "type": "string", - "format": "uri", - "description": "A URI reference that identifies the specific occurrence of the problem" + "Services.Post": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ServiceInfo.Post" + } + } + }, + "description": "New ServiceInfo with updated \"state\" is included as entity body of the request", + "required": true }, - "ApplicationList": { - "description": "Information on available applications", - "type": "object", - "properties": { - "appInfo": { - "$ref": "#/components/schemas/AppInfo" - }, - "vendorSpecificExt": { - "$ref": "#/components/schemas/VendorSpecificExt" + "ServicesServiceId": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ServiceInfo" + } } - } + }, + "description": "New ServiceInfo with updated \"state\" is included as entity body of the request", + "required": true }, - "AppContext": { - "description": "Information on application context created by the MEC system", - "type": "object", - "required": [ - "contextId", - "associateUeAppId", - "appInfo" - ], - "properties": { - "contextId": { - "$ref": "#/components/schemas/ContextId" - }, - "associateUeAppId": { - "$ref": "#/components/schemas/AssociateUeAppId" - }, - "callbackReference": { - "$ref": "#/components/schemas/CallbackReference" - }, - "appInfo": { - "$ref": "#/components/schemas/RequiredAppInfo" + "AppTerminationNotification": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AppTerminationNotification" + } } } }, - "NotificationEvent": { - "description": "The parameters used in the method \"Receiving notification events\".", - "type": "object", - "required": [ - "referenceURI" - ], - "properties": { - "referenceURI": { - "$ref": "#/components/schemas/ReferenceURL" + "ServiceAvailabilityNotification": { + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ServiceAvailabilityNotification" + } } } - }, - "VendorSpecificExtList": { - "description": "Extension for vendor specific information.", - "type": "array", - "minItems": 0, - "items": { - "$ref": "#/components/schemas/VendorSpecificExt" + } + }, + "callbacks": { + "AppTerminationNotification": { + "{$request.body#/callbackReference}": { + "post": { + "description": "Represents the information that the MEP notifies the subscribed application instance about the corresponding application instance termination/stop", + "operationId": "AppTerminationNotification_POST", + "tags": [ + "callback" + ], + "requestBody": { + "$ref": "#/components/requestBodies/AppTerminationNotification" + }, + "responses": { + "200": { + "description": "Expected responses from callback consumer, if it accepts the callback" + } + } + } } }, - "VendorSpecificExt": { - "description": "Extension for vendor-specific information", - "required": [ - "vendorId" - ], - "properties": { - "vendorId": { - "$ref": "#/components/schemas/VendorId" + "ServiceAvailabilityNotification": { + "{$request.body#/callbackReference}": { + "post": { + "description": "'Represents the service availability information that is used in the following cases - when the MEC platform announces the newly available\n services to the authorized relevant MEC applications (e.g. \n the applications that indicate the services as \"optional\" \n or \"required\") that are subscribed to the corresponding \n service availability notifications\n- when the MEC platform notifies the authorized relevant applications that are subscribed to the corresponding service availability notifications about the service availability changes.'", + "operationId": "ServiceAvailabilityNotification_POST", + "tags": [ + "callback" + ], + "requestBody": { + "$ref": "#/components/requestBodies/ServiceAvailabilityNotification" + }, + "responses": { + "200": { + "description": "Expected responses from callback consumer, if it accepts the callback" + } + } } } + } + }, + "links": { + "GetIndividualMeService": { + "operationId": "ServicesServiceId_GET", + "description": "The `serviceId` value returned in the response can be used as the `serviceId` parameter in `GET /services/{serviceId}`", + "parameters": { + "serviceId": "$response.body#/serviceId" + } }, - "ContextId": { - "description": "Uniquely identifies the application context in the MEC system. Assigned by the MEC system and included in the response. The length of the value shall not exceed 32 characters.", - "type": "string" - }, - "AssociateUeAppId": { - "description": "Uniquely identifies the UE application. Included in the request. The length of the value shall not exceed 32 characters.", - "type": "string" + "PutIndividualMeService": { + "operationId": "ServicesServiceId_PUT", + "description": "The `serviceId` value returned in the response can be used as the `serviceId` parameter in `PUT /services/{serviceId}`", + "parameters": { + "serviceId": "$response.body#/serviceId" + } }, - "VendorId": { - "description": "Vendor identifier. The length of the value shall not exceed 32 characters. The rest of the structure of this vendor specific extension is not defined", - "type": "string" + "GetIndividualMeDNSRule": { + "operationId": "ApplicationsDnsRule_GET", + "description": "The `dnsRuleId` value returned in the response can be used as the `dnsRuleId` parameter in `GET /applications/{appInstanceId}/dns_rules/{dnsRuleId}`", + "parameters": { + "dnsRuleId": "$response.body#/dnsRuleId" + } }, - "AppInfo": { - "description": "User applications available for the UE application", - "type": "array", - "items": { - "$ref": "#/components/schemas/AppInfoList" + "PutIndividualMeDNSRule": { + "operationId": "ApplicationsDnsRule_PUT", + "description": "The `dnsRuleId` value returned in the response can be used as the `dnsRuleId` parameter in `PUT /applications/{appInstanceId}/dns_rules/{dnsRuleId}`", + "parameters": { + "dnsRuleId": "$response.body#/dnsRuleId" } }, - "AppInfoList": { - "type": "object", - "required": [ - "appName", - "appProvider", - "appDescription" - ], - "properties": { - "appName": { - "$ref": "#/components/schemas/AppName" - }, - "appProvider": { - "$ref": "#/components/schemas/AppProvider" - }, - "appSoftVersion": { - "$ref": "#/components/schemas/AppSoftVersion" - }, - "appDescription": { - "$ref": "#/components/schemas/AppDescription" - }, - "appCharcs": { - "$ref": "#/components/schemas/AppCharcs" - } + "GetIndividualMeTrafficRule": { + "operationId": "ApplicationsTrafficRule_GET", + "description": "The `trafficRuleId` value returned in the response can be used as the `trafficRuleId` parameter in `GET /applications/{appInstanceId}/traffic_rules/{trafficRuleId}`", + "parameters": { + "trafficRuleId": "$response.body#/trafficRuleId" } }, - "RequiredAppInfo": { - "description": "Included in the request", - "type": "object", - "required": [ - "appName", - "appProvider", - "referenceURL" - ], - "properties": { - "appName": { - "$ref": "#/components/schemas/AppName" - }, - "appProvider": { - "$ref": "#/components/schemas/AppProvider" - }, - "appSoftVersion": { - "$ref": "#/components/schemas/AppSoftVersion" - }, - "appDescription": { - "$ref": "#/components/schemas/AppDescription" - }, - "referenceURL": { - "$ref": "#/components/schemas/ReferenceURL" - }, - "appPackageSource": { - "$ref": "#/components/schemas/AppPackageSource" - } + "PutIndividualMeTrafficRule": { + "operationId": "ApplicationsTrafficRule_PUT", + "description": "The `trafficRuleId` value returned in the response can be used as the `trafficRuleId` parameter in `PUT /applications/{appInstanceId}/traffic_rules/{trafficRuleId}`", + "parameters": { + "trafficRuleId": "$response.body#/trafficRuleId" } }, - "AppCharcs": { - "description": "The application characteristics relate to the system resources consumed by the application. UE application can use this information e.g., for estimating the cost of use of the application or for the expected user experience", - "type": "object", - "properties": { - "memory": { - "$ref": "#/components/schemas/Memory" - }, - "storage": { - "$ref": "#/components/schemas/Storage" - }, - "latency": { - "$ref": "#/components/schemas/Latency" - }, - "bandwidth": { - "$ref": "#/components/schemas/Bandwidth" - }, - "serviceCont": { - "$ref": "#/components/schemas/ServiceCont" - } + "GetTransportInfo": { + "operationId": "AppServices_POST", + "description": "The `id` value returned in the response can be used as the `transportId` parameter in `POST /applications/{appInstanceId}/services`. The first transport is provided as the link as wildcards are not supported", + "parameters": { + "transportId": "$response.body#/0/id" } }, - "Memory": { - "description": "The maximum size in Mbytes of the memory resource reserved for the MEC application instance in the MEC system", - "type": "integer", - "format": "uint32" + "GetIndividualMeMp1Subscription": { + "operationId": "ApplicationsSubscription_GET", + "description": "The `subscriptionId` value returned in the response can be used as the `subscriptionId` parameter in `GET /applications/{appInstanceId}/subscriptions/{subscriptionType}/{subscriptionId}`", + "parameters": { + "description": "regex = \\/mp1\\/v1\\/applications\\/.*\\/subscriptions\\/.*\\/(.*);subscriptionId = href.match(regex)[1];// where \"href\" is an attribute within the subscription attribute within the _links attribute", + "subscriptionId": "TBC" + } }, - "Storage": { - "description": "The maximum size in Mbytes of the storage resource expected to be used by the MEC application instance in the MEC system", - "type": "integer", - "format": "uint32" + "DelIndividualMeMp1Subscription": { + "operationId": "ApplicationsSubscription_DELETE", + "description": "The `subscriptionId` value returned in the response can be used as the `subscriptionId` parameter in `DELETE /applications/{appInstanceId}/subscriptions/{subscriptionType}/{subscriptionId}`", + "parameters": { + "description": "regex = \\/mp1\\/v1\\/applications\\/.*\\/subscriptions\\/.*\\/(.*);subscriptionId = href.match(regex)[1];// where \"href\" is an attribute within the subscription attribute within the _links attribute", + "subscriptionId": "TBC" + } }, - "Latency": { - "description": "The target round trip time in milliseconds supported by the MEC system for the MEC application instance", - "type": "integer", - "format": "uint32" + "GetIndividualMeMp1SubscriptionLinkList": { + "operationId": "ApplicationsSubscription_GET", + "description": "The `subscriptionId` value returned in the response can be used as the `subscriptionId` parameter in `GET /applications/{appInstanceId}/subscriptions/{subscriptionType}/{subscriptionId}`", + "parameters": { + "description": "regex = \\/mp1\\/v1\\/applications\\/.*\\/subscriptions\\/.*\\/(.*);subscriptionId = href.match(regex)[1];// where \"href\" is an attribute within the subscription attribute within the _links attribute", + "subscriptionId": "TBC" + } }, - "Bandwidth": { - "description": "The required connection bandwidth in kbit/s for the use of the mobile edge application instance", - "type": "integer", - "format": "uint32" + "DelIndividualMeMp1SubscriptionLinkList": { + "operationId": "ApplicationsSubscription_DELETE", + "description": "The `subscriptionId` value returned in the response can be used as the `subscriptionId` parameter in `DELETE /applications/{appInstanceId}/subscriptions/{subscriptionType}/{subscriptionId}`", + "parameters": { + "description": "regex = \\/mp1\\/v1\\/applications\\/.*\\/subscriptions\\/.*\\/(.*);subscriptionId = href.match(regex)[1];// where \"href\" is an attribute within the subscription attribute within the _links attribute", + "subscriptionId": "TBC" + } + } + }, + "examples": { + "DnsRule": { + "value": { + "dnsRuleId": "DnsRule1", + "domainName": "www.example.com", + "ipAddressType": "IP_V4", + "ipAddress": "146.241.7.3", + "ttl": 300, + "state": "ACTIVE" + } }, - "ServiceCont": { - "description": "Required service continuity mode for this application.", - "type": "string", - "enum": [ - "SERVICE_CONTINUITY_NOT_REQUIRED", - "SERVICE_CONTINUITY_REQUIRED" + "DnsRules": { + "value": [ + { + "dnsRuleId": "DnsRule1", + "domainName": "www.example.com", + "ipAddressType": "IP_V4", + "ipAddress": "146.241.7.3", + "ttl": 300, + "state": "ACTIVE" + } ] }, - "AppName": { - "description": "Name of the MEC application. The length of the value shall not exceed 32 characters.", - "type": "string" - }, - "AppProvider": { - "description": "Provider of the MEC application. The length of the value shall not exceed 32 characters.", - "type": "string" - }, - "AppSoftVersion": { - "description": "Software version of the MEC application. The length of the value shall not exceed 32 characters.", - "type": "string" - }, - "AppDescription": { - "description": "Human readable description of the MEC application. NOTE the language support may be limited. The length of the value shall not exceed 128 characters.", - "type": "string" + "ServiceInfo": { + "value": { + "serInstanceId": "ServiceInstance123", + "serName": "ExampleService", + "serCategory": { + "href": "catItem1", + "id": "id12345", + "name": "RNI", + "version": "version1" + }, + "version": "ServiceVersion1", + "state": "ACTIVE", + "transportInfo": { + "id": "TransId12345", + "name": "REST", + "description": "REST API", + "type": "REST_HTTP", + "protocol": "HTTP", + "version": "2.0", + "endpoint": { + "uris": [ + "/meMp1/service/EntryPoint" + ] + }, + "security": { + "oAuth2Info": { + "grantTypes": [ + "OAUTH2_CLIENT_CREDENTIALS" + ], + "tokenEndpoint": "/meMp1/security/TokenEndPoint" + } + } + }, + "serializer": "JSON" + } }, - "CallbackReference": { - "description": "URI assigned by the UE application to receive application lifecycle related notifications. Included in the request. This subscription stays alive for the lifetime of the application context.", - "type": "string", - "format": "uri" + "ServiceInfoList": { + "value": [ + { + "serInstanceId": "ServiceInstance123", + "serName": "ExampleService", + "serCategory": { + "href": "catItem1", + "id": "id12345", + "name": "RNI", + "version": "version1" + }, + "version": "ServiceVersion1", + "state": "ACTIVE", + "transportInfo": { + "id": "TransId12345", + "name": "REST", + "description": "REST API", + "type": "REST_HTTP", + "protocol": "HTTP", + "version": "2.0", + "endpoint": { + "addresses": [ + { + "host": "192.0.2.0", + "port": 8080 + } + ] + }, + "security": { + "oAuth2Info": { + "grantTypes": [ + "OAUTH2_CLIENT_CREDENTIALS" + ], + "tokenEndpoint": "/meMp1/security/TokenEndPoint" + } + } + }, + "serializer": "JSON" + } + ] }, - "ReferenceURL": { - "description": "Address of the user application. Used as the reference URL for the application. Assigned by the MEC system and included in the response", - "type": "string", - "format": "uri" + "TrafficRule": { + "value": { + "trafficRuleId": "TrafficRule123", + "serName": "ExampleService", + "filterType": "FLOW", + "priority": 1, + "trafficFilter": [ + { + "srcAddress": [ + "192.168.2.0/24", + "192.168.3.0/24" + ], + "dstAddress": [ + "192.127.4.100/32" + ], + "dstPort": [ + "80" + ] + } + ], + "action": "FORWARD_DECAPSULATED", + "dstInterface": { + "interfaceType": "IP", + "dstIpAddress": "20.1.1.1" + }, + "state": "ACTIVE" + } }, - "AppPackageSource": { - "description": "URI of the application package. Included in the request if the application is not one in the ApplicationList. appPackageSource enables on-boarding of the application package into the MEC system. The application package shall comply with the definitions in clause 6.2.1.2 of ETSI GS MEC 010-2", - "type": "string", - "format": "uri" + "TrafficRules": { + "value": [ + { + "trafficRuleId": "TrafficRule123", + "serName": "ExampleService", + "filterType": "FLOW", + "priority": 1, + "trafficFilter": [ + { + "srcAddress": [ + "192.168.2.0/24", + "192.168.3.0/24" + ], + "dstAddress": [ + "192.127.4.100/32" + ], + "dstPort": [ + "80" + ] + } + ], + "action": "FORWARD_DECAPSULATED", + "dstInterface": { + "interfaceType": "IP", + "dstIpAddress": "20.1.1.1" + }, + "state": "ACTIVE" + } + ] } } } diff --git a/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Pics.ttcn b/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Pics.ttcn new file mode 100644 index 0000000000000000000000000000000000000000..350ac05e2370c71b809f363a17fba20d7d858a8d --- /dev/null +++ b/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Pics.ttcn @@ -0,0 +1,5 @@ +module AppEnablementAPI_Pics { + + modulepar boolean PICS_ENABLE_APP_API_SUPPORTED := true; + +} // End of module AppEnablementAPI_Pics diff --git a/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Pixits.ttcn b/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Pixits.ttcn new file mode 100644 index 0000000000000000000000000000000000000000..e99f6994dea8e4b20a6fc4e97b860226527a6647 --- /dev/null +++ b/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Pixits.ttcn @@ -0,0 +1,19 @@ +module AppEnablementAPI_Pixits { + + // LibCommon + import from LibCommon_BasicTypesAndValues all; + + // LibMec/AppEnablementAPI + import from AppEnablementAPI_TypesAndValues all; + + modulepar universal charstring PX_APP_INSTANCE_ID := "appInst01"; + + modulepar universal charstring PX_NON_EXISTENT_APP_INSTANCE_ID := "appInst99"; + + modulepar universal charstring PX_TRAFFIC_RULE_ID := "trafficRuleId01"; + + modulepar universal charstring PX_UE_IDENTITY_TAG_INVALID_STATE := "UeTagC"; + + modulepar universal charstring PX_UE_IDENTITY_TAG_UNKNOWN := "UeTagW"; + +} // End of module AppEnablementAPI_Pixits diff --git a/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Templates.ttcn b/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Templates.ttcn index 144a57c1641e15503bf4920ae47c32ff96616512..fb7f280d8193f49936d613901c7f06aaf40fa4d6 100644 --- a/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Templates.ttcn +++ b/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_Templates.ttcn @@ -27,144 +27,78 @@ module AppEnablementAPI_Templates { instance := p_instance } // End of template mw_problem_details - template (value) ApplicationList m_application_list( - in template (value) AppInfo p_app_info, - in template (value) VendorSpecificExt p_vendor_specific_ext - ) := { - appInfo := p_app_info, - vendorSpecificExt := p_vendor_specific_ext - } // End of template m_application_list - - template (present) ApplicationList mw_application_list( - template (present) AppInfo p_app_info := ?, - template (present) VendorSpecificExt p_vendor_specific_ext := ? - ) := { - appInfo := p_app_info, - vendorSpecificExt := p_vendor_specific_ext - } // End of template mw_application_list - - template (value) AppContext m_app_context( - in template (value) ContextId p_context_id, - in template (value) AssociateUeAppId p_associate_ue_app_id, - in template (value) RequiredAppInfo p_app_info - ) := { - contextId := p_context_id, - associateUeAppId := p_associate_ue_app_id, - appInfo := p_app_info, - callbackReference := omit - } // End of template m_app_context - - template (present) AppContext mw_app_context( - template (present) ContextId p_context_id := ?, - template (present) AssociateUeAppId p_associate_ue_app_id := ?, - template (present) RequiredAppInfo p_app_info := ? - ) := { - contextId := p_context_id, - associateUeAppId := p_associate_ue_app_id, - appInfo := p_app_info, - callbackReference := * - } // End of template mw_app_context - - template (value) NotificationEvent m_notification_event( - in template (value) ReferenceURL p_reference_uri - ) := { - referenceURI := p_reference_uri - } // End of template m_notification_event - - template (present) NotificationEvent mw_notification_event( - template (present) ReferenceURL p_reference_uri := ? - ) := { - referenceURI := p_reference_uri - } // End of template mw_notification_event - - template (value) VendorSpecificExt m_vendor_specific_ext( - in template (value) VendorId p_vendor_id - ) := { - vendorId := p_vendor_id - } // End of template m_vendor_specific_ext - - template (present) VendorSpecificExt mw_vendor_specific_ext( - template (present) VendorId p_vendor_id := ? - ) := { - vendorId := p_vendor_id - } // End of template mw_vendor_specific_ext - - template (value) AppInfoList m_appInfo_list( - in template (value) AppName p_app_name, - in template (value) AppProvider p_app_provider, - in template (value) AppDescription p_app_description + template (value) TransportInfo m_transport_info( + in TransportInfo_Id p_id, + in TransportInfo_Name p_name, + in TransportTypes p_type_, + in TransportInfo_Protocol p_protocol, + in TransportInfo_Version p_version, + in template (value) TransportInfo_Endpoint p_endpoint, + in SecurityInfo p_security + ) := { + id := p_id, + name := p_name, + description := omit, + type_ := p_type_, + protocol := p_protocol, + version := p_version, + endpoint := p_endpoint, + security := p_security, + implSpecificInfo := omit + } // End of template m_transport_info + + template (present) TransportInfo mw_transport_info( + template (present) TransportInfo_Id p_id := ?, + template (present) TransportInfo_Name p_name := ?, + template (present) TransportTypes p_type_ := ?, + template (present) TransportInfo_Protocol p_protocol := ?, + template (present) TransportInfo_Version p_version := ?, + template (present) TransportInfo_Endpoint p_endpoint := ?, + template (present) SecurityInfo p_security := ? + ) := { + id := p_id, + name := p_name, + description := *, + type_ := p_type_, + protocol := p_protocol, + version := p_version, + endpoint := p_endpoint, + security := p_security, + implSpecificInfo := * + } // End of template mw_transport_info + + template (value) TrafficRule m_traffic_rule( + in TrafficRule_Id p_trafficRuleId, + in TrafficRule_FilterType p_filterType := FLOW, + in TrafficRule_Priority p_priority := 1, + in TrafficFilterList p_trafficFilter := {}, + in TrafficRule_Action p_action_, + in TrafficRule_State p_state := ACTIVE ) := { - appName := p_app_name, - appProvider := p_app_provider, - appDescription := p_app_description, - appSoftVersion := omit, - appCharcs := omit - } // End of template m_appInfo_list - - template (present) AppInfoList mw_appInfo_list( - template (present) AppName p_app_name := ?, - template (present) AppProvider p_app_provider := ?, - template (present) AppDescription p_app_description := ? + trafficRuleId := p_trafficRuleId, + filterType := p_filterType, + priority := p_priority, + trafficFilter := p_trafficFilter, + action_ := p_action_, + dstInterface := omit, + state := p_state + } // End of template m_traffic_rule + + template (present) TrafficRule mw_traffic_rule( + template (present) TrafficRule_Id p_trafficRuleId := ?, + template (present) TrafficRule_FilterType p_filterType := ?, + template (present) TrafficRule_Priority p_priority := ?, + template (present) TrafficFilterList p_trafficFilter := ?, + template (present) TrafficRule_Action p_action_ := ?, + template (present) TrafficRule_State p_state := ? ) := { - appName := p_app_name, - appProvider := p_app_provider, - appDescription := p_app_description, - appSoftVersion := *, - appCharcs := * - } // End of template mw_appInfo_list - - template (value) RequiredAppInfo m_required_app_info( - in template (value) AppName p_app_name, - in template (value) AppProvider p_app_provider, - in template (value) ReferenceURL p_reference_url - ) := { - appName := p_app_name, - appProvider := p_app_provider, - referenceURL := p_reference_url, - appSoftVersion := omit, - appDescription := omit, - appPackageSource := omit - } // End of template m_required_app_info - - template (present) RequiredAppInfo mw_required_app_info( - template (present) AppName p_app_name := ?, - template (present) AppProvider p_app_provider := ?, - template (present) ReferenceURL p_reference_url := ? - ) := { - appName := p_app_name, - appProvider := p_app_provider, - referenceURL := p_reference_url, - appSoftVersion := *, - appDescription := *, - appPackageSource := * - } // End of template mw_required_app_info - - template (value) AppCharcs m_app_charcs( - in template (value) Memory p_memory, - in template (value) Storage p_storage, - in template (value) Latency p_latency, - in template (value) Bandwidth p_bandwidth, - in template (value) ServiceCont p_service_cont - ) := { - memory := p_memory, - storage := p_storage, - latency := p_latency, - bandwidth := p_bandwidth, - serviceCont := p_service_cont - } // End of template m_app_charcs - - template (present) AppCharcs mw_app_charcs( - template (present) Memory p_memory := ?, - template (present) Storage p_storage := ?, - template (present) Latency p_latency := ?, - template (present) Bandwidth p_bandwidth := ?, - template (present) ServiceCont p_service_cont := ? - ) := { - memory := p_memory, - storage := p_storage, - latency := p_latency, - bandwidth := p_bandwidth, - serviceCont := p_service_cont - } // End of template mw_app_charcs - + trafficRuleId := p_trafficRuleId, + filterType := p_filterType, + priority := p_priority, + trafficFilter := p_trafficFilter, + action_ := p_action_, + dstInterface := *, + state := p_state + } // End of template mw_traffic_rule + } // End of module AppEnablementAPI_Templates diff --git a/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_TypesAndValues.ttcn b/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_TypesAndValues.ttcn index 02d388f3f3b4b500e36b8d0263bb1d9ee28b9115..75ed478fba1df9f0179b0ca2f8eaaf930aab748c 100644 --- a/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_TypesAndValues.ttcn +++ b/ttcn/LibMec/AppEna/ttcn/AppEnablementAPI_TypesAndValues.ttcn @@ -10,6 +10,289 @@ module AppEnablementAPI_TypesAndValues { // LibCommon import from LibCommon_BasicTypesAndValues all; + /** + * @desc Maximum timeout value in seconds for graceful termination or graceful stop of an application instance. + */ + type UInt32 MaxGracefulTimeout; + + /** + * @desc Shall be set to AppTerminationNotification. + */ + type JSON.String NotificationType; + + /** + * @desc This type represents the information that the mobile edge platform notifies the subscribed application instance about the corresponding application instance termination/stop. + */ + type record AppTerminationNotification { + NotificationType notificationType, + MaxGracefulTimeout maxGracefulTimeout, + Subscription links + } with { + variant (links) "name as '_links'"; + } + + /** + * @desc It is used as the filtering criterion for the subscribed events. + */ + type JSON.String AppInstanceId; + + /** + * @desc URI selected by the mobile edge application instance to receive notifications on the subscribed mobile edge application instance management information. + * This shall be included in both the request and the response." + */ + type JSON.String AppTerminationNotificationSubscription_CallbackReference; + + /** + * @desc This type represents the information that the mobile edge platform notifies the subscribed application instance about the corresponding application instance termination/stop. + */ + type record AppTerminationNotificationSubscription { + SubscriptionType subscriptionType, + AppTerminationNotificationSubscription_CallbackReference callbackReference, + Self links, + AppInstanceId appInstanceId + } with { + variant (links) "name as '_links'"; + } + + /** + * @desc Shall be set to AppTerminationNotificationSubscription. + */ + type JSON.String SubscriptionType; + + /** + * @desc Reference of the catalogue. + */ + type JSON.String CategoryRef_Href; + + /** + * @desc Unique identifier of the category. + */ + type JSON.String CategoryRef_Id; + + /** + * @desc Name of the category. + */ + type JSON.String Name; + + /** + * @desc Category version. + */ + type JSON.String CategoryRef_Version; + + /** + * @desc This type represents the category reference. + */ + type record CategoryRef { + CategoryRef_Href href, + CategoryRef_Id id, + Name name, + CategoryRef_Version version + } + + /** + * @desc The seconds part of the Time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC. + */ + type UInt32 Seconds; + + /** + * @desc The nanoseconds part of the Time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC. + */ + type UInt32 NanoSeconds; + + /** + * @desc Platform Time Source status. 1 = TRACEABLE - time source is locked to the UTC time source. 2 = NONTRACEABLE - time source is not locked to the UTC time source. + */ + type enumerated TimeSourceStatus { + TRACEABLE (1), + NONTRACEABLE (2) + } + + /** + * @desc This type represents the information provided by the mobile edge platform in response to the Get Platform Time Request message. + * @member seconds The seconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC. + * @member nanoSeconds The nanoseconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC. + * @member timeSourceStatus Platform Time Source status. 1 = TRACEABLE - time source is locked to the UTC time source. 2 = NONTRACEABLE - time source is not locked to the UTC time source. + */ + type record CurrentTime { + Seconds seconds, + NanoSeconds nanoSeconds, + TimeSourceStatus timeSourceStatus + } + + /** + * @desc Type of the interface. + */ + type enumerated InterfaceType { + TUNNEL, + MAC, + IP + } + + /** + * @desc IP address of the remote destination. + */ + type JSON.String DestinationInterface_IpAddress; + + /** + * @desc Source address identifies the MAC address of the interface. + */ + type JSON.String DestinationInterface_MacAddress; + + /** + * @desc This type represents the destination interface. + */ + type record DestinationInterface { + InterfaceType interfaceType, + TunnelInfo tunnelInfo optional, + DestinationInterface_MacAddress srcMacAddress optional, + DestinationInterface_MacAddress dstMacAddress optional, + DestinationInterface_IpAddress dstIpAddress optional + } + + /** + * @desc FQDN resolved by the DNS rule. + */ + type JSON.String DomainName; + + /** + * @desc Identifies the DNS Rule. + */ + type JSON.String DnsRule_Id; + + /** + * @desc IP address associated with the FQDN resolved by the DNS rule. + */ + type JSON.String DnsRule_IpAddress; + + /** + * @desc IP address type. + */ + type enumerated DnsRule_IpAddressType { + IP_V6, + IP_V4 + } + + /** + * @desc DNS rule state. + */ + type enumerated DnsRule_State { + ACTIVE, + INACTIVE + } + + /** + * @desc Time to live value. + */ + type UInt32 Ttl; + + /** + * @desc This type represents the general information of a DNS rule. + */ + type record DnsRule { + DnsRule_Id dnsRuleId, + DomainName domainName, + DnsRule_IpAddressType ipAddressType, + DnsRule_IpAddress ipAddress, + Ttl ttl, + DnsRule_State state + } + + /** + * @desc Host portion of the address. + */ + type JSON.String Host; + + /** + * @desc Port portion of the address. + */ + type UInt32 Address_Port; + + /** + * @desc A IP address and port pair. + */ + type record Address { + Host host, + Address_Port port_ + } with { + variant (port_) "name as 'port'"; + } + type record length(0..infinity) of Address AddressList; + + /** + * @desc Entry point information of the service as one or more pairs of IP address and port. + */ + type record Addresses { + AddressList addresses + } + + /** + * @desc Entry point information of the service in a format defined by an implementation, or in an external specification. + */ + type record Alternative { + anytype alternative + } + + /** + * @desc Entry point information of the service. + */ + type JSON.String EndPointInfo_Uri; + type record length(0..infinity) of EndPointInfo_Uri EndPointInfo_UriList; + + /** + * @desc Entry point information of the service as string, formatted according to URI syntax. + */ + type record Uris { + EndPointInfo_UriList uris + } + + /** + * @desc This type represents a type of link and may be referenced from data structures. + */ + type record LinkType { + Href href + } + + /** + * @desc URI referring to a resource. + */ + type JSON.String Href; + + /** + * @desc Self-referring URI. + */ + type record Mp1SubscriptionLinkList_Links { + LinkType self_, + Mp1SubscriptionLinkList_SubscriptionList subscription optional + } with { + variant (self_) "name as 'self'"; + } + + /** + * @desc The values are as defined in the \"subscriptionType\" attribute for each different Mp1 event subscription data type. + */ + type enumerated Rel { + AppTerminationNotificationSubscription, + SerAvailabilityNotificationSubscription + } + + /** + * @desc A link to a subscription. + */ + type record Mp1SubscriptionLinkList_Subscription { + Href href, + Rel rel + } + type record length(0..infinity) of Mp1SubscriptionLinkList_Subscription Mp1SubscriptionLinkList_SubscriptionList; + + /** + * @desc This type represents a list of links related to currently existing subscriptions for a mobile edge application instance. This information is returned when sending a request to receive current subscriptions. + */ + type record Mp1SubscriptionLinkList { + Mp1SubscriptionLinkList_Links links + } with { + variant (links) "name as '_links'"; + } + /** * @desc Problem Details for HTTP APIs * @member type_ A URI reference according to IETF RFC 3986 that identifies the problem type @@ -30,159 +313,455 @@ module AppEnablementAPI_TypesAndValues { } /** - * @desc Information on available applications. + * @desc List of supported OAuth 2.0 grant types. + */ + type enumerated GrantTypes { + OAUTH2_AUTHORIZATION_CODE, + OAUTH2_IMPLICIT_GRANT, + OAUTH2_RESOURCE_OWNER, + OAUTH2_CLIENT_CREDENTIALS + } + type record length(1..4) of GrantTypes GrantTypesList; + + /** + * @desc The token endpoint. */ - type record ApplicationList { - AppInfo appInfo, - VendorSpecificExt vendorSpecificExt + type JSON.String TokenEndpoint; + + /** + * @desc Parameters related to use of OAuth 2.0. + */ + type record OAuth2Info { + GrantTypesList grantTypes, + TokenEndpoint tokenEndpoint } /** - * @desc Information on application context created by the MEC system. + * @desc This type represents security information related to a transport. */ - type record AppContext { - ContextId contextId, - AssociateUeAppId associateUeAppId, - RequiredAppInfo appInfo, - CallbackReference callbackReference optional + type record SecurityInfo { + OAuth2Info oAuth2Info } /** - * @desc The parameters used in the method "Receiving notification events". + * @desc Self-referring URI. */ - type record NotificationEvent { - ReferenceURL referenceURI + type record Self { + LinkType self_, + JSON.Bool readOnly optional + } with { + variant (self_) "name as 'self'"; } /** - * @desc Extension for vendor specific information. + * @desc URI selected by the mobile edge application instance to receive notifications on the subscribed mobile edge service availability information. This shall be included in both the request and the response. */ - type record length(0..infinity) of VendorSpecificExt VendorSpecificExtList; + type JSON.String SerAvailabilityNotificationSubscription_CallbackReference; /** - * @desc Extension for vendor-specific information. + * @desc This type represents a subscription to the notifications from the mobile edge platform regarding the availability of a mobile edge service or a list of mobile edge services. */ - type record VendorSpecificExt { - VendorId vendorId + type record SerAvailabilityNotificationSubscription { + SerAvailabilityNotificationSubscription_SubscriptionType subscriptionType, + SerAvailabilityNotificationSubscription_CallbackReference callbackReference, + Self links, + ServiceInfo filteringCriteria } /** - * @desc Uniquely identifies the application context in the MEC system. Assigned by the MEC system and included in the response. The length of the value shall not exceed 32 characters. + * @desc Shall be set to SerAvailabilityNotificationSubscription. */ - type JSON.String ContextId length(1..32) with {encode "length(1..32)"}; + type JSON.String SerAvailabilityNotificationSubscription_SubscriptionType; /** - * @desc Uniquely identifies the UE application. Included in the request. The length of the value shall not exceed 32 characters. + * @desc This type represents the service availability information. */ - type JSON.String AssociateUeAppId length(1..32) with {encode "length(1..32)"}; + type record ServiceAvailabilityNotification { + SerAvailabilityNotificationSubscription_SubscriptionType notificationType, + ServiceInfos services, + Subscription links + } /** - * @desc Vendor identifier. The length of the value shall not exceed 32 characters. The rest of the structure of this vendor specific extension is not defined. + * @desc The enumeration SerializerTypes represents types of serializers. */ - type JSON.String VendorId; + type enumerated SerializerTypes { + JSON, + XML, + PROTOBUF3 + } + + /** + * @desc Identifier of the service instance assigned by the MEPM / mobile edge platform. + */ + type JSON.String SerInstanceId; /** - * @desc User applications available for the UE application. + * @desc The name of the service. This is how the service producing mobile edge application identifies the service instance it produces. */ - type record of AppInfoList AppInfo; + type JSON.String SerName; /** - * @desc User applications available for the UE application. + * @desc Contains the state. */ - type record AppInfoList { - AppName appName, - AppProvider appProvider, - AppDescription appDescription, - AppSoftVersion appSoftVersion optional, - AppCharcs appCharcs optional + type enumerated ServiceInfo_State { + ACTIVE, + INACTIVE } /** - * @desc Included in the request. + * @desc Identifier of the platform-provided transport to be used by the service. Valid identifiers may be obtained using the \"Transport information query\" procedure. May be present in POST requests to signal the use of a platform-provided transport for the service, and shall be absent otherwise. */ - type record RequiredAppInfo { - AppName appName, - AppProvider appProvider, - ReferenceURL referenceURL, - AppSoftVersion appSoftVersion optional, - AppDescription appDescription optional, - AppPackageSource appPackageSource optional + type JSON.String TransportId; + + /** + * @desc Service version. + */ + type JSON.String ServiceInfo_Version; + + /** + * @desc This type represents the general information of a mobile edge service. + */ + type record ServiceInfo { + SerInstanceId serInstanceId optional, + SerName serName, + CategoryRef serCategory optional, + ServiceInfo_Version version, + ServiceInfo_State state, + TransportInfo transportInfo, + SerializerTypes serializer } + type record of ServiceInfo ServiceInfos; /** - * @desc The application characteristics relate to the system resources consumed by the application. UE application can use this information e.g., for estimating the cost of use of the application or for the expected user experience. + * @desc A link to the related subscription. */ - type record AppCharcs { - Memory memory, - Storage storage, - Latency latency, - Bandwidth bandwidth, - ServiceCont serviceCont + type record Subscription { + LinkType subscription } /** - * @desc The maximum size in Mbytes of the memory resource reserved for the MEC application instance in the MEC system. + * @desc Authentication key number. + */ + type UInt32 AuthenticationKeyNum; + + /** + * @desc NTP authentication option. + */ + type enumerated AuthenticationOption { + NONE, + SYMMETRIC_KEY, + AUTO_KEY + } + + /** + * @desc Acceptable maximum rate of the Delay_Req messages in packets per second. + */ + type UInt32 DelayReqMaxRate; + + /** + * @desc NTP server local priority. */ - type UInt32 Memory; + type UInt32 LocalPriority; /** - * @desc The maximum size in Mbytes of the storage resource expected to be used by the MEC application instance in the MEC system. + * @desc Maximum poll interval for NTP messages, in seconds as a power of two. Range 3...17. */ - type UInt32 Storage; + type integer MaxPollingInterval (3..17) with {variant "unsigned 32 bit"} ; /** - * @desc The target round trip time in milliseconds supported by the MEC system for the MEC application instance. + * @desc Minimum poll interval for NTP messages, in seconds as a power of two. Range 3...17. */ - type UInt32 Latency; + type integer MinPollingInterval (3..17) with {variant "unsigned 32 bit"} ; /** - * @desc The required connection bandwidth in kbit/s for the use of the mobile edge application instance. + * @desc NTP server address. */ - type UInt32 Bandwidth; + type JSON.String NtpServerAddr; /** - * @desc Required service continuity mode for this application. + * @desc Address type of NTP server. */ - type enumerated ServiceCont { - SERVICE_CONTINUITY_NOT_REQUIRED, - SERVICE_CONTINUITY_REQUIRED + type enumerated NtpServerAddrType { + IP_ADDRESS, + DNS_NAME } /** - * @desc Name of the MEC application. The length of the value shall not exceed 32 characters. + * @desc PTP Master IP Address. */ - type JSON.String AppName length(1..32) with {encode "length(1..32)"}; + type JSON.String NtpServers_PtpMasterIpAddress; /** - * @desc Provider of the MEC application. The length of the value shall not exceed 32 characters. + * @desc PTP Master local priority. */ - type JSON.String AppProvider length(1..32) with {encode "length(1..32)"}; + type UInt32 NtpServers_PtpMasterLocalPriority; /** - * @desc Software version of the MEC application. The length of the value shall not exceed 32 characters. + * @desc NTP server detail. */ - type JSON.String AppSoftVersion length(1..32) with {encode "length(1..32)"}; + type record NtpServers { + NtpServerAddrType ntpServerAddrType, + NtpServerAddr ntpServerAddr, + MinPollingInterval minPollingInterval, + MaxPollingInterval maxPollingInterval, + LocalPriority localPriority, + AuthenticationOption authenticationOption, + AuthenticationKeyNum authenticationKeyNum + } + type record of NtpServers NtpServersList; /** - * @desc Human readable description of the MEC application. NOTE the language support may be limited. The length of the value shall not exceed 128 characters. + * @desc NTP server detail. */ - type JSON.String AppDescription length(1..128) with {encode "length(1..128)"}; + type record TimingCaps_PtpMasters { + NtpServers_PtpMasterIpAddress ptpMasterIpAddress, + NtpServers_PtpMasterLocalPriority ptpMasterLocalPriority, + DelayReqMaxRate delayReqMaxRate + } + type record of TimingCaps_PtpMasters TimingCaps_PtpMastersList; /** - * @desc URI assigned by the UE application to receive application lifecycle related notifications. Included in the request. This subscription stays alive for the lifetime of the application context. + * @desc Time. + * @member seconds The seconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC. + * @member nanoSeconds The nanoseconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC. + * @member timeSourceStatus Platform Time Source status. 1 = TRACEABLE - time source is locked to the UTC time source. 2 = NONTRACEABLE - time source is not locked to the UTC time source. */ - type JSON.String CallbackReference; + type record TimeStamp { + Seconds seconds, + NanoSeconds nanoSeconds + } /** - * @desc Address of the user application. Used as the reference URL for the application. Assigned by the MEC system and included in the response. + * @desc This type represents the information provided by the mobile edge platform in response to the Timing capabilities Query message. */ - type JSON.AnyURI ReferenceURL; + type record TimingCaps { + TimeStamp timeStamp, + NtpServersList ntpServers, + TimingCaps_PtpMastersList ptpMasters + } /** - * @desc URI of the application package. Included in the request if the application is not one in the ApplicationList. appPackageSource enables on-boarding of the application package into the MEC system. The application package shall comply with the definitions in clause 6.2.1.2 of ETSI GS MEC 010-2. + * @desc Identify the traffic ip address. */ - type JSON.AnyURI AppPackageSource; - + type JSON.String TrafficFilter_Address; + type record of TrafficFilter_Address TrafficFilter_AddressList; + + /** + * @desc Used to match all IPv4 packets that have the same Differentiated Services Code Point (DSCP). + */ + type UInt32 TrafficFilter_DSCP; + + /** + * @desc Identify the traffic ip address. + */ + type JSON.String TrafficFilter_Port; + + /** + * @desc Protocol of the traffic filter. + */ + type JSON.String TrafficFilter_Protocol; + type record of TrafficFilter_Protocol TrafficFilter_ProtocolList; + + /** + * @desc Used to match all packets that have the same Quality Class Indicator (QCI). + */ + type UInt32 TrafficFilter_QCI; + + /** + * @desc Used to match all IPv6 packets that have the same Traffic Class. + */ + type UInt32 TrafficFilter_TC; + + /** + * @desc Used for token based traffic rule. + */ + type JSON.String TrafficFilter_Token; + type record of TrafficFilter_Token TrafficFilter_TokenList; + + /** + * @desc Used for GTP tunnel based traffic rule. + */ + type JSON.String TrafficFilter_TunnelAddress; + type record of TrafficFilter_TunnelAddress TrafficFilter_TunnelAddressList; + + /** + * @desc Used for GTP tunnel based traffic rule. + */ + type JSON.String TrafficFilter_TunnelPort; + type record of TrafficFilter_TunnelPort TrafficFilter_TunnelPortList; + + /** + * @desc This type represents the traffic filter. + */ + type record TrafficFilter { + TrafficFilter_Address srcAddress, + TrafficFilter_AddressList dstAddress, + TrafficFilter_Port srcPort, + TrafficFilter_Port dstPort, + TrafficFilter_ProtocolList protocol, + TrafficFilter_TokenList token, + TrafficFilter_TunnelAddressList srcTunnelAddress, + TrafficFilter_TunnelAddressList tgtTunnelAddress, + TrafficFilter_TunnelPortList srcTunnelPort, + TrafficFilter_TunnelPortList dstTunnelPort, + TrafficFilter_QCI qCI, + TrafficFilter_DSCP dSCP, + TrafficFilter_TC tC + } + type record of TrafficFilter TrafficFilterList; + + /** + * @desc The action of the ME host data plane when a packet matches the trafficFilter. + */ + type enumerated TrafficRule_Action { + DROP, + FORWARD_DECAPSULATED, + FORWARD_AS_IS, + PASSTHROUGH, + DUPLICATE_DECAPSULATED, + DUPLICATE_AS_IS + } + + /** + * @desc Definition of filter per FLOW or PACKET. If flow the filter match UE->EPC packet and the reverse packet is handled in the same context. + */ + type enumerated TrafficRule_FilterType { + FLOW, + PACKET + } + + /** + * @desc Identify the traffic rule. + */ + type JSON.String TrafficRule_Id; + + /** + * @desc Priority of this traffic rule. If traffic rule conflicts, the one with higher priority take precedence. + */ + type UInt32 TrafficRule_Priority; + + /** + * @desc Contains the traffic rule state. + */ + type enumerated TrafficRule_State { + ACTIVE, + INACTIVE + } + + /** + * @desc This type represents the general information of a traffic rule. + */ + type record TrafficRule { + TrafficRule_Id trafficRuleId, + TrafficRule_FilterType filterType, + TrafficRule_Priority priority, + TrafficFilterList trafficFilter, + TrafficRule_Action action_, + DestinationInterface dstInterface optional, + TrafficRule_State state + } with { + variant (action_) "name as 'action'"; + } + type record of TrafficRule TrafficRuleList + + /** + * @desc Human-readable description of this transport. + */ + type JSON.String TransportInfo_Description; + + /** + * @desc The identifier of this transport. + */ + type JSON.String TransportInfo_Id; + + /** + * @desc Additional implementation specific details of the transport. + */ + type anytype TransportInfo_ImplSpecificInfo; + + /** + * @desc The name of this transport. + */ + type JSON.String TransportInfo_Name; + + /** + * @desc The name of the protocol used. Shall be set to HTTP for a REST API. + */ + type JSON.String TransportInfo_Protocol; + + /** + * @desc The version of the protocol used. + */ + type JSON.String TransportInfo_Version; + + /** + * @desc This type represents information about a transport endpoint. + */ + type union TransportInfo_Endpoint { // JSON oneOf ??? + Uris uris, + Addresses addresses, + Alternative alternative + } + + /** + * @desc This type represents the general information of a mobile edge service. + */ + type record TransportInfo { + TransportInfo_Id id, + TransportInfo_Name name, + TransportInfo_Description description optional, + TransportTypes type_, + TransportInfo_Protocol protocol, + TransportInfo_Version version, + TransportInfo_Endpoint endpoint, + SecurityInfo security, + TransportInfo_ImplSpecificInfo implSpecificInfo optional + } with { + variant (type_) "name as 'type'"; + } + type record of TransportInfo TransportInfoList; + + /** + * @desc The enumeration TransportTypes represents types of transports. + */ + type enumerated TransportTypes { + REST_HTTP, + MB_TOPIC_BASED, + MB_ROUTING, + MB_PUBSUB, + RPC, + RPC_STREAMING, + WEBSOCKET + } + + /** + * @desc Destination address of the tunnel. + */ + type JSON.String TunnelInfo_TunnelDstAddress; + + /** + * @desc Source address of the tunnel. + */ + type JSON.String TunnelInfo_TunnelSrcAddress; + + /** + * @desc This type represents the tunnel information. + */ + type enumerated TunnelInfo_TunnelType { + GTP_U, + GRE + } + + /** + * @desc This type represents the tunnel information. + */ + type record TunnelInfo { + TunnelInfo_TunnelType tunnelType, + TunnelInfo_TunnelDstAddress tunnelDstAddress optional, + TunnelInfo_TunnelSrcAddress tunnelSrcAddress optional + } + } with { encode "JSON" } // End of module AppEnablementAPI_TypesAndValues diff --git a/ttcn/LibMec/LocationAPI/ttcn/LocationAPI_TypesAndValues.ttcn b/ttcn/LibMec/LocationAPI/ttcn/LocationAPI_TypesAndValues.ttcn index ca39738e31f9c7de2c2f328a2bbc9e7f82ba340c..bc795f22a85b6a3e47dd9b7b3d6fffa8a6a296cc 100644 --- a/ttcn/LibMec/LocationAPI/ttcn/LocationAPI_TypesAndValues.ttcn +++ b/ttcn/LibMec/LocationAPI/ttcn/LocationAPI_TypesAndValues.ttcn @@ -6,6 +6,16 @@ module LocationAPI_TypesAndValues { // LibCommon import from LibCommon_BasicTypesAndValues all; + /** + * @desc The seconds part of the Time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC + */ + type UInt32 Seconds; + + /** + * @desc The nanoseconds part of the Time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC + */ + type UInt32 NanoSeconds; + /** * @desc * @member seconds The seconds part of the time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC @@ -376,16 +386,6 @@ REST_NetAPI_Common]. OperationStatus operationStatus optional } - /** - * @desc The seconds part of the Time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC - */ - type UInt32 Seconds; - - /** - * @desc The nanoseconds part of the Time. Time is defined as Unix-time since January 1, 1970, 00:00:00 UTC - */ - type UInt32 NanoSeconds; - } with { encode "JSON" } diff --git a/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_Pixits.ttcn b/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_Pixits.ttcn index cb6d0604c8afb41e3a68d44fd0ea72a8a20b7349..f4302fb535bc480f739124dcca4d7c1bc18e4af8 100644 --- a/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_Pixits.ttcn +++ b/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_Pixits.ttcn @@ -3,11 +3,25 @@ module RnisAPI_Pixits { // JSON import from JSON all; + // LibCommon + import from LibCommon_BasicTypesAndValues all; + // LibMec/Rnis import from RnisAPI_TypesAndValues all; + modulepar JSON.String PX_SUBSCRIPTION_HREF_VALUE := "cell_change"; + modulepar SubscriptionType PX_SUBSCRIPTION_TYPE := CELL_CHANGE; + modulepar JSON.String PX_SUBSCRIPTION_ID := "7777"; - modulepar Link PX_LINKS_SELF := { self_ := "http://example.com/exampleAPI/rni/v2/subscriptions/" }; + modulepar Link PX_LINKS_SELF := { self_ := "http://example.com/exampleAPI/rni/v2/subscriptions" }; + + modulepar CallbackReference PX_CALLBACK_REFERENCE := "http://meAppClient.example.com/rni/v2/notifications/cell_change/77777"; + + modulepar UInt32 PX_ASSOCIATE_ID_VALUE := 1; + + modulepar CellId PX_CELL_ID := "0x0800000A"; + + modulepar AppInsId PX_APP_INS_ID := "01"; } // End of module RnisAPI_Pixits diff --git a/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_Templates.ttcn b/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_Templates.ttcn index 16ef75716a8786878c3b6a9b75da8e3439ca2bbc..8c29fd5e2fb537d75d9ce70f0e13f411b7988081 100644 --- a/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_Templates.ttcn +++ b/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_Templates.ttcn @@ -9,6 +9,34 @@ module RnisAPI_Templates { // LibMec/RnisAPI import from RnisAPI_TypesAndValues all; + template (value) ProblemDetails m_problem_details( + in JSON.String p_type, + in JSON.String p_title, + in UInt32 p_status, + in JSON.String p_detail, + in JSON.String p_instance + ) := { + type_ := p_type, + title := p_title, + status := p_status, + detail := p_detail, + instance := p_instance + } // End of template m_problem_details + + template (present) ProblemDetails mw_problem_details( + template (present) JSON.String p_type := ?, + template (present) JSON.String p_title := ?, + template (present) UInt32 p_status := ?, + template (present) JSON.String p_detail := ?, + template (present) JSON.String p_instance := ? + ) := { + type_ := p_type, + title := p_title, + status := p_status, + detail := p_detail, + instance := p_instance + } // End of template mw_problem_details + group subscriptions { template (omit) SubscriptionLinkList m_subscriptions_list( @@ -28,6 +56,82 @@ module RnisAPI_Templates { subscription := p_subscription } // End of template mw_subscriptions_list + template (value) Subscription_ m_subscription( + in LinkType p_href, + in SubscriptionType p_subscriptionType + ) := { + href := p_href, + subscriptionType := p_subscriptionType + } // End of temlate m_subscription + + template (present) Subscription_ mw_subscription( + template (present) LinkType p_href := ?, + template (present) SubscriptionType p_subscriptionType := ? + ) := { + href := p_href, + subscriptionType := p_subscriptionType + } // End of temlate mw_subscription + + template (value) RabInfo m_rab_info( + in template (value) TimeStamp p_timeStamp, + in AppInsId p_appInsId, + in RequestId p_requestId, + in template (value) CellUserInfo p_cellUserInfo + ) := { + timeStamp := p_timeStamp, + appInsId := p_appInsId, + requestId := p_requestId, + cellUserInfo := p_cellUserInfo + } // End of temlate m_rab_info + + template (present) RabInfo mw_rab_info( + template (present) TimeStamp p_timeStamp := ?, + template (present) AppInsId p_appInsId := ?, + template (present) RequestId p_requestId := ?, + template (present) CellUserInfo p_cellUserInfo := ? + ) := { + timeStamp := p_timeStamp, + appInsId := p_appInsId, + requestId := p_requestId, + cellUserInfo := p_cellUserInfo + } // End of temlate mw_rab_info + + template (value) PlmnInfo m_plmn_info( + in template (value) TimeStamp p_timeStamp, + in AppInsId p_appInsId, + in template (value) Ecgi p_ecgi + ) := { + timeStamp := p_timeStamp, + appInsId := p_appInsId, + ecgi := p_ecgi + } // End of temlate m_plmn_info + + template (present) PlmnInfo mw_plmn_info( + template (present) TimeStamp p_timeStamp := ?, + template (present) AppInsId p_appInsId := ?, + template (present) Ecgi p_ecgi := ? + ) := { + timeStamp := p_timeStamp, + appInsId := p_appInsId, + ecgi := p_ecgi + } // End of temlate mw_plmn_info + + template (value) TimeStamp m_time_stamp( + in UInt32 p_seconds, + in UInt32 p_nanoSeconds := 0 + ) := { + seconds := p_seconds, + nanoSeconds := p_nanoSeconds + } // End of temlate m_time_stamp + + template (present) TimeStamp mw_time_stamp( + template (present) UInt32 p_seconds := ?, + template (present) UInt32 p_nanoSeconds := ? + ) := { + seconds := p_seconds, + nanoSeconds := p_nanoSeconds + } // End of temlate mw_time_stamp + group cell { template (omit) CellChangeSubscription m_cell_change_subscription( @@ -36,26 +140,130 @@ module RnisAPI_Templates { in template (value) FilterCriteriaAssocHo p_filterCriteria, in template (omit) TimeStamp p_expiryDeadline := omit ) := { + subscriptionType := CELL_CHANGE, callbackReference := p_callbackReference, links := p_links, filterCriteria := p_filterCriteria, expiryDeadline := p_expiryDeadline } // End of template m_cell_change_subscription + template (omit) CellChangeSubscription m_cell_change_subscription_wrong_subscription_type( + in template (value) CallbackReference p_callbackReference, + in template (value) Link p_links, + in template (value) FilterCriteriaAssocHo p_filterCriteria, + in template (omit) TimeStamp p_expiryDeadline := omit + ) modifies m_cell_change_subscription := { + subscriptionType := WRONG_PARAMETER + } // End of template m_cell_change_subscription_wrong_subscription_type + template CellChangeSubscription mw_cell_change_subscription( template (present) CallbackReference p_callbackReference := ?, template (present) Link p_links := ?, template (present) FilterCriteriaAssocHo p_filterCriteria := ?, template TimeStamp p_expiryDeadline := * ) := { + subscriptionType := CELL_CHANGE, callbackReference := p_callbackReference, links := p_links, filterCriteria := p_filterCriteria, expiryDeadline := p_expiryDeadline } // End of template mw_cell_change_subscription + template (value) FilterCriteriaAssocHo m_filter_criteria( + in AppInsId p_appInsId, + in template (value) AssociateId p_associateId, + in template (value) Plmn p_plmn, + in template (value) CellId p_cellId, + in HoStatus p_hoStatus + ) := { + appInsId := p_appInsId, + associateId := p_associateId, + plmn := p_plmn, + cellId := p_cellId, + hoStatus := p_hoStatus + } // End of template m_filter_criteria + + template (present) FilterCriteriaAssocHo mw_filter_criteria( + template (present) AppInsId p_appInsId := ?, + template (present) AssociateId p_associateId := ?, + template (present) Plmn p_plmn := ?, + template (present) CellId p_cellId := ?, + template (present) HoStatus p_hoStatus := ? + ) := { + appInsId := p_appInsId, + associateId := p_associateId, + plmn := p_plmn, + cellId := p_cellId, + hoStatus := p_hoStatus + } // End of template mw_filter_criteria + + template (value) CellUserInfo m_cell_user_info( + in template (value) Ecgi p_ecgi, + in template (value) UeInfo p_ueInfo + ) := { + ecgi := p_ecgi, + ueInfo := p_ueInfo + } // End of template m_cell_user_info + + template (present) CellUserInfo mw_cell_user_info( + template (present) Ecgi p_ecgi := ?, + template (present) UeInfo p_ueInfo := ? + ) := { + ecgi := p_ecgi, + ueInfo := p_ueInfo + } // End of template mw_cell_user_info + + template (value) AssociateId_ m_associate_id( + in AssociateId_type p_type_, + in UInt32 p_value_ + ) := { + type_ := p_type_, + value_ := p_value_ + } // End of template m_associate_id + + template (present) AssociateId_ mw_associate_id( + template (present) AssociateId_type p_type_ := ?, + template (present) UInt32 p_value_ := ? + ) := { + type_ := p_type_, + value_ := p_value_ + } // End of template mw_associate_id + + template (value) Ecgi m_ecgi( + in template (value) Plmn p_plmn, + in template (value) CellId p_cellId + ) := { + plmn := p_plmn, + cellId := p_cellId + } // End of template m_ecgi + + template (present) Ecgi mw_ecgi( + in template (present) Plmn p_plmn := ?, + in template (present) CellId p_cellId := ? + ) := { + plmn := p_plmn, + cellId := p_cellId + } // End of template mw_ecgi + + template (value) Plmn m_plmn( + in JSON.String p_mcc, + in JSON.String p_mnc + ) := { + mcc := p_mcc, + mnc := p_mnc + } // End of template m_plmn + + template (present) Plmn mw_plmn( + template (present) JSON.String p_mcc := ?, + template (present) JSON.String p_mnc := ? + ) := { + mcc := p_mcc, + mnc := p_mnc + } // End of template mw_plmn + } // End of group cell } // End of group subscriptions + } // End of module RnisAPI_Templates diff --git a/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_TypesAndValues.ttcn b/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_TypesAndValues.ttcn index 9be42ff309c53550cef4683337c95f742b64529d..2e0442db2f2122f81a5fc719031c6d35930b476a 100644 --- a/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_TypesAndValues.ttcn +++ b/ttcn/LibMec/RnisAPI/ttcn/RnisAPI_TypesAndValues.ttcn @@ -183,7 +183,7 @@ module RnisAPI_TypesAndValues { /** * @desc The E-UTRAN Cell Identity as a bit string (size (28)), as defined in 3GPP TS 36.413 */ - type record of octetstring CellId; + type JSON.String CellId; /** * @desc Information on UEs in the specific cell @@ -455,6 +455,7 @@ module RnisAPI_TypesAndValues { * @member expiryDeadline */ type record CellChangeSubscription { + SubscriptionType subscriptionType, CallbackReference callbackReference, Link links, FilterCriteriaAssocHo filterCriteria, @@ -540,7 +541,8 @@ module RnisAPI_TypesAndValues { MEAS_REPORT_UE, MEAS_TIMING_ADVANCE, CA_RECONF, - S1_BEARE + S1_BEARE, + WRONG_PARAMETER } /** diff --git a/ttcn/LibMec/UEAppInterfaceAPI/json/UEAppInterfaceAPI.json b/ttcn/LibMec/UEAppInterfaceAPI/json/UEAppInterfaceAPI.json new file mode 100644 index 0000000000000000000000000000000000000000..c5ee3fcda73baa582e50733f936af0fb7c26a484 --- /dev/null +++ b/ttcn/LibMec/UEAppInterfaceAPI/json/UEAppInterfaceAPI.json @@ -0,0 +1,618 @@ +{ + "openapi": "3.0.2", + "info": { + "title": "UE Application Interface API", + "version": "1.1.1", + "description": "The ETSI MEC ISG MEC016 UE Application Interface API described using OpenAPI", + "license": { + "name": "ETSI Forge copyright notice", + "url": "https://forge.etsi.org/etsi-forge-copyright-notice.txt" + }, + "contact": { + "email": "cti_support@etsi.org" + } + }, + "externalDocs": { + "description": "ETSI GS MEC016 UE Application Interface API, V1.1.1", + "url": "http://www.etsi.org/deliver/etsi_gs/MEC/001_099/016/01.01.01_60/gs_MEC016v010101p.pdf" + }, + "security": [ + { + "OauthSecurity": [ + "all" + ] + } + ], + "servers": [ + { + "url": "http://127.0.0.1:8081/mx2/v1" + }, + { + "url": "https://127.0.0.1:8081/mx2/v1" + } + ], + "tags": [ + { + "name": "appList" + }, + { + "name": "appContext" + } + ], + "paths": { + "/app_list": { + "get": { + "description": "Used to query information about the available MEC applications.", + "operationId": "AppList_GET", + "tags": [ + "appList" + ], + "parameters": [ + { + "$ref": "#/components/parameters/Query.AppName" + }, + { + "$ref": "#/components/parameters/Query.AppProvider" + }, + { + "$ref": "#/components/parameters/Query.AppSoftVersion" + }, + { + "$ref": "#/components/parameters/Query.ServiceCont" + }, + { + "$ref": "#/components/parameters/Query.VendorId" + } + ], + "responses": { + "200": { + "$ref": "#/components/responses/AppList" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "401": { + "$ref": "#/components/responses/Error.401" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + } + }, + "/app_contexts": { + "post": { + "description": "The POST method can be used to create a new application context. Upon success, the response contains entity body describing the created application context.", + "operationId": "AppContext_POST", + "tags": [ + "appContext" + ], + "requestBody": { + "$ref": "#/components/requestBodies/AppContext" + }, + "responses": { + "201": { + "$ref": "#/components/responses/AppContext" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "401": { + "$ref": "#/components/responses/Error.401" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + } + }, + "/app_contexts/{contextId}": { + "parameters": [ + { + "$ref": "#/components/parameters/Path.ContextId" + } + ], + "put": { + "description": "The PUT method is used to update the callback reference of the existing application context. Upon successful operation, the target resource is updated with new callback reference.", + "operationId": "AppContextId_PUT", + "tags": [ + "appContext" + ], + "requestBody": { + "$ref": "#/components/requestBodies/AppContext" + }, + "responses": { + "204": { + "description": "No Content." + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "401": { + "$ref": "#/components/responses/Error.401" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + }, + "delete": { + "description": "The DELETE method is used to delete the resource that represents the existing application context.", + "operationId": "AppContextId_DEL", + "tags": [ + "appContext" + ], + "responses": { + "204": { + "description": "No Content" + }, + "400": { + "$ref": "#/components/responses/Error.400" + }, + "401": { + "$ref": "#/components/responses/Error.401" + }, + "403": { + "$ref": "#/components/responses/Error.403" + }, + "404": { + "$ref": "#/components/responses/Error.404" + } + } + } + } + }, + "components": { + "parameters": { + "Query.AppName": { + "name": "appName", + "in": "query", + "description": "Name to identify the MEC application", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + "Query.AppProvider": { + "name": "appProvider", + "in": "query", + "description": "Provider of the MEC application", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + "Query.AppSoftVersion": { + "name": "appSoftVersion", + "in": "query", + "description": "Software version of the MEC application", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + "Query.ServiceCont": { + "name": "serviceCont", + "in": "query", + "description": "Required service continuity mode for this application", + "required": false, + "schema": { + "type": "string", + "enum": [ + "SERVICE_CONTINUITY_NOT_REQUIRED", + "SERVICE_CONTINUITY_REQUIRED" + ] + } + }, + "Query.VendorId": { + "name": "vendorId", + "in": "query", + "description": "Vendor identifier", + "required": false, + "schema": { + "type": "array", + "items": { + "type": "string" + } + } + }, + "Path.ContextId": { + "name": "contextId", + "in": "path", + "description": "Uniquely identifies the application context in the MEC system. It is assigned by the MEC system and included in the response to an AppContext create.", + "required": true, + "schema": { + "type": "string" + } + } + }, + "requestBodies": { + "AppContext": { + "description": "Uniquely identifies the application context in the MEC system. It is assigned by the MEC system and included in the response to an AppContext create.", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AppContext" + } + } + }, + "required": true + } + }, + "responses": { + "AppContext": { + "description": "The response body contains the Application Context as it was created by the MEC system", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/AppContext" + } + } + } + }, + "AppList": { + "description": "The response body contains the ApplicationList resource available for the querying UE application", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ApplicationList" + } + } + } + }, + "Error.400": { + "description": "Bad Request. It is used to indicate that incorrect parameters were passed to the request.", + "content": { + "application/problem+json": { + "schema": { + "$ref": "#/components/schemas/ProblemDetails" + } + }, + "text/plain": { + "schema": { + "$ref": "#/components/schemas/Empty" + } + } + } + }, + "Error.401": { + "description": "Unauthorized. It is used when the client did not submit the appropriate credentials.", + "content": { + "application/problem+json": { + "schema": { + "$ref": "#/components/schemas/ProblemDetails" + } + }, + "text/plain": { + "schema": { + "$ref": "#/components/schemas/Empty" + } + } + } + }, + "Error.403": { + "description": "Forbidden. The operation is not allowed given the current status of the resource. ", + "content": { + "application/problem+json": { + "schema": { + "$ref": "#/components/schemas/ProblemDetails" + } + } + } + }, + "Error.404": { + "description": "Not Found. It is used when a client provided a URI that cannot be mapped to a valid resource URI.", + "content": { + "application/problem+json": { + "schema": { + "$ref": "#/components/schemas/ProblemDetails" + } + }, + "text/plain": { + "schema": { + "$ref": "#/components/schemas/Empty" + } + } + } + } + }, + "securitySchemes": { + "OauthSecurity": { + "type": "oauth2", + "flows": { + "clientCredentials": { + "tokenUrl": "https://oauth.exampleAPI/token", + "scopes": { + "all": "Single oauth2 scope for API" + } + } + } + } + }, + "schemas": { + "Empty": { + "description": "Empty schema" + }, + "ProblemDetails": { + "type": "object", + "properties": { + "type": { + "$ref": "#/components/schemas/Problem.type" + }, + "title": { + "$ref": "#/components/schemas/Problem.title" + }, + "status": { + "$ref": "#/components/schemas/Problem.status" + }, + "detail": { + "$ref": "#/components/schemas/Problem.detail" + }, + "instance": { + "$ref": "#/components/schemas/Problem.instance" + } + } + }, + "Problem.type": { + "type": "string", + "format": "uri", + "description": "A URI reference according to IETF RFC 3986 that identifies the problem type" + }, + "Problem.title": { + "type": "string", + "description": "A short, human-readable summary of the problem type" + }, + "Problem.status": { + "type": "integer", + "format": "uint32", + "description": "The HTTP status code for this occurrence of the problem" + }, + "Problem.detail": { + "type": "string", + "description": "A human-readable explanation specific to this occurrence of the problem" + }, + "Problem.instance": { + "type": "string", + "format": "uri", + "description": "A URI reference that identifies the specific occurrence of the problem" + }, + "ApplicationList": { + "description": "Information on available applications", + "type": "object", + "properties": { + "appInfo": { + "$ref": "#/components/schemas/AppInfo" + }, + "vendorSpecificExt": { + "$ref": "#/components/schemas/VendorSpecificExt" + } + } + }, + "AppContext": { + "description": "Information on application context created by the MEC system", + "type": "object", + "required": [ + "contextId", + "associateUeAppId", + "appInfo" + ], + "properties": { + "contextId": { + "$ref": "#/components/schemas/ContextId" + }, + "associateUeAppId": { + "$ref": "#/components/schemas/AssociateUeAppId" + }, + "callbackReference": { + "$ref": "#/components/schemas/CallbackReference" + }, + "appInfo": { + "$ref": "#/components/schemas/RequiredAppInfo" + } + } + }, + "NotificationEvent": { + "description": "The parameters used in the method \"Receiving notification events\".", + "type": "object", + "required": [ + "referenceURI" + ], + "properties": { + "referenceURI": { + "$ref": "#/components/schemas/ReferenceURL" + } + } + }, + "VendorSpecificExtList": { + "description": "Extension for vendor specific information.", + "type": "array", + "minItems": 0, + "items": { + "$ref": "#/components/schemas/VendorSpecificExt" + } + }, + "VendorSpecificExt": { + "description": "Extension for vendor-specific information", + "required": [ + "vendorId" + ], + "properties": { + "vendorId": { + "$ref": "#/components/schemas/VendorId" + } + } + }, + "ContextId": { + "description": "Uniquely identifies the application context in the MEC system. Assigned by the MEC system and included in the response. The length of the value shall not exceed 32 characters.", + "type": "string" + }, + "AssociateUeAppId": { + "description": "Uniquely identifies the UE application. Included in the request. The length of the value shall not exceed 32 characters.", + "type": "string" + }, + "VendorId": { + "description": "Vendor identifier. The length of the value shall not exceed 32 characters. The rest of the structure of this vendor specific extension is not defined", + "type": "string" + }, + "AppInfo": { + "description": "User applications available for the UE application", + "type": "array", + "items": { + "$ref": "#/components/schemas/AppInfoList" + } + }, + "AppInfoList": { + "type": "object", + "required": [ + "appName", + "appProvider", + "appDescription" + ], + "properties": { + "appName": { + "$ref": "#/components/schemas/AppName" + }, + "appProvider": { + "$ref": "#/components/schemas/AppProvider" + }, + "appSoftVersion": { + "$ref": "#/components/schemas/AppSoftVersion" + }, + "appDescription": { + "$ref": "#/components/schemas/AppDescription" + }, + "appCharcs": { + "$ref": "#/components/schemas/AppCharcs" + } + } + }, + "RequiredAppInfo": { + "description": "Included in the request", + "type": "object", + "required": [ + "appName", + "appProvider", + "referenceURL" + ], + "properties": { + "appName": { + "$ref": "#/components/schemas/AppName" + }, + "appProvider": { + "$ref": "#/components/schemas/AppProvider" + }, + "appSoftVersion": { + "$ref": "#/components/schemas/AppSoftVersion" + }, + "appDescription": { + "$ref": "#/components/schemas/AppDescription" + }, + "referenceURL": { + "$ref": "#/components/schemas/ReferenceURL" + }, + "appPackageSource": { + "$ref": "#/components/schemas/AppPackageSource" + } + } + }, + "AppCharcs": { + "description": "The application characteristics relate to the system resources consumed by the application. UE application can use this information e.g., for estimating the cost of use of the application or for the expected user experience", + "type": "object", + "properties": { + "memory": { + "$ref": "#/components/schemas/Memory" + }, + "storage": { + "$ref": "#/components/schemas/Storage" + }, + "latency": { + "$ref": "#/components/schemas/Latency" + }, + "bandwidth": { + "$ref": "#/components/schemas/Bandwidth" + }, + "serviceCont": { + "$ref": "#/components/schemas/ServiceCont" + } + } + }, + "Memory": { + "description": "The maximum size in Mbytes of the memory resource reserved for the MEC application instance in the MEC system", + "type": "integer", + "format": "uint32" + }, + "Storage": { + "description": "The maximum size in Mbytes of the storage resource expected to be used by the MEC application instance in the MEC system", + "type": "integer", + "format": "uint32" + }, + "Latency": { + "description": "The target round trip time in milliseconds supported by the MEC system for the MEC application instance", + "type": "integer", + "format": "uint32" + }, + "Bandwidth": { + "description": "The required connection bandwidth in kbit/s for the use of the mobile edge application instance", + "type": "integer", + "format": "uint32" + }, + "ServiceCont": { + "description": "Required service continuity mode for this application.", + "type": "string", + "enum": [ + "SERVICE_CONTINUITY_NOT_REQUIRED", + "SERVICE_CONTINUITY_REQUIRED" + ] + }, + "AppName": { + "description": "Name of the MEC application. The length of the value shall not exceed 32 characters.", + "type": "string" + }, + "AppProvider": { + "description": "Provider of the MEC application. The length of the value shall not exceed 32 characters.", + "type": "string" + }, + "AppSoftVersion": { + "description": "Software version of the MEC application. The length of the value shall not exceed 32 characters.", + "type": "string" + }, + "AppDescription": { + "description": "Human readable description of the MEC application. NOTE the language support may be limited. The length of the value shall not exceed 128 characters.", + "type": "string" + }, + "CallbackReference": { + "description": "URI assigned by the UE application to receive application lifecycle related notifications. Included in the request. This subscription stays alive for the lifetime of the application context.", + "type": "string", + "format": "uri" + }, + "ReferenceURL": { + "description": "Address of the user application. Used as the reference URL for the application. Assigned by the MEC system and included in the response", + "type": "string", + "format": "uri" + }, + "AppPackageSource": { + "description": "URI of the application package. Included in the request if the application is not one in the ApplicationList. appPackageSource enables on-boarding of the application package into the MEC system. The application package shall comply with the definitions in clause 6.2.1.2 of ETSI GS MEC 010-2", + "type": "string", + "format": "uri" + } + } + } +} \ No newline at end of file diff --git a/ttcn/LibMec/UEAppInterfaceAPI/ttcn/UEAppInterfaceAPI_Templates.ttcn b/ttcn/LibMec/UEAppInterfaceAPI/ttcn/UEAppInterfaceAPI_Templates.ttcn new file mode 100644 index 0000000000000000000000000000000000000000..af1b7f97bd65c6a48571ec0e80b83b8aae98b551 --- /dev/null +++ b/ttcn/LibMec/UEAppInterfaceAPI/ttcn/UEAppInterfaceAPI_Templates.ttcn @@ -0,0 +1,170 @@ +/** + * @desc The ETSI MEC ISG MEC011 Application Enablement API described using OpenAPI + * @see http://www.etsi.org/deliver/etsi_gs/MEC/001_099/011/01.01.01_60/gs_mec011v010101p.pdf + */ +module UEAppInterfaceAPI_Templates { + + // JSON + import from JSON all; + + // LibCommon + import from LibCommon_BasicTypesAndValues all; + + // LibMec/AppEna + import from UEAppInterfaceAPI_TypesAndValues all; + + template (present) ProblemDetails mw_problem_details( + template (present) JSON.String p_type := ?, + template (present) JSON.String p_title := ?, + template (present) UInt32 p_status := ?, + template (present) JSON.String p_detail := ?, + template (present) JSON.String p_instance := ? + ) := { + type_ := p_type, + title := p_title, + status := p_status, + detail := p_detail, + instance := p_instance + } // End of template mw_problem_details + + template (value) ApplicationList m_application_list( + in template (value) AppInfo p_app_info, + in template (value) VendorSpecificExt p_vendor_specific_ext + ) := { + appInfo := p_app_info, + vendorSpecificExt := p_vendor_specific_ext + } // End of template m_application_list + + template (present) ApplicationList mw_application_list( + template (present) AppInfo p_app_info := ?, + template (present) VendorSpecificExt p_vendor_specific_ext := ? + ) := { + appInfo := p_app_info, + vendorSpecificExt := p_vendor_specific_ext + } // End of template mw_application_list + + template (value) AppContext m_app_context( + in template (value) ContextId p_context_id, + in template (value) AssociateUeAppId p_associate_ue_app_id, + in template (value) RequiredAppInfo p_app_info + ) := { + contextId := p_context_id, + associateUeAppId := p_associate_ue_app_id, + appInfo := p_app_info, + callbackReference := omit + } // End of template m_app_context + + template (present) AppContext mw_app_context( + template (present) ContextId p_context_id := ?, + template (present) AssociateUeAppId p_associate_ue_app_id := ?, + template (present) RequiredAppInfo p_app_info := ? + ) := { + contextId := p_context_id, + associateUeAppId := p_associate_ue_app_id, + appInfo := p_app_info, + callbackReference := * + } // End of template mw_app_context + + template (value) NotificationEvent m_notification_event( + in template (value) ReferenceURL p_reference_uri + ) := { + referenceURI := p_reference_uri + } // End of template m_notification_event + + template (present) NotificationEvent mw_notification_event( + template (present) ReferenceURL p_reference_uri := ? + ) := { + referenceURI := p_reference_uri + } // End of template mw_notification_event + + template (value) VendorSpecificExt m_vendor_specific_ext( + in template (value) VendorId p_vendor_id + ) := { + vendorId := p_vendor_id + } // End of template m_vendor_specific_ext + + template (present) VendorSpecificExt mw_vendor_specific_ext( + template (present) VendorId p_vendor_id := ? + ) := { + vendorId := p_vendor_id + } // End of template mw_vendor_specific_ext + + template (value) AppInfoList m_appInfo_list( + in template (value) AppName p_app_name, + in template (value) AppProvider p_app_provider, + in template (value) AppDescription p_app_description + ) := { + appName := p_app_name, + appProvider := p_app_provider, + appDescription := p_app_description, + appSoftVersion := omit, + appCharcs := omit + } // End of template m_appInfo_list + + template (present) AppInfoList mw_appInfo_list( + template (present) AppName p_app_name := ?, + template (present) AppProvider p_app_provider := ?, + template (present) AppDescription p_app_description := ? + ) := { + appName := p_app_name, + appProvider := p_app_provider, + appDescription := p_app_description, + appSoftVersion := *, + appCharcs := * + } // End of template mw_appInfo_list + + template (value) RequiredAppInfo m_required_app_info( + in template (value) AppName p_app_name, + in template (value) AppProvider p_app_provider, + in template (value) ReferenceURL p_reference_url + ) := { + appName := p_app_name, + appProvider := p_app_provider, + referenceURL := p_reference_url, + appSoftVersion := omit, + appDescription := omit, + appPackageSource := omit + } // End of template m_required_app_info + + template (present) RequiredAppInfo mw_required_app_info( + template (present) AppName p_app_name := ?, + template (present) AppProvider p_app_provider := ?, + template (present) ReferenceURL p_reference_url := ? + ) := { + appName := p_app_name, + appProvider := p_app_provider, + referenceURL := p_reference_url, + appSoftVersion := *, + appDescription := *, + appPackageSource := * + } // End of template mw_required_app_info + + template (value) AppCharcs m_app_charcs( + in template (value) Memory p_memory, + in template (value) Storage p_storage, + in template (value) Latency p_latency, + in template (value) Bandwidth p_bandwidth, + in template (value) ServiceCont p_service_cont + ) := { + memory := p_memory, + storage := p_storage, + latency := p_latency, + bandwidth := p_bandwidth, + serviceCont := p_service_cont + } // End of template m_app_charcs + + template (present) AppCharcs mw_app_charcs( + template (present) Memory p_memory := ?, + template (present) Storage p_storage := ?, + template (present) Latency p_latency := ?, + template (present) Bandwidth p_bandwidth := ?, + template (present) ServiceCont p_service_cont := ? + ) := { + memory := p_memory, + storage := p_storage, + latency := p_latency, + bandwidth := p_bandwidth, + serviceCont := p_service_cont + } // End of template mw_app_charcs + +} // End of module UEAppInterfaceAPI_Templates diff --git a/ttcn/LibMec/UEAppInterfaceAPI/ttcn/UEAppInterfaceAPI_TypesAndValues.ttcn b/ttcn/LibMec/UEAppInterfaceAPI/ttcn/UEAppInterfaceAPI_TypesAndValues.ttcn new file mode 100644 index 0000000000000000000000000000000000000000..abbfd34433774887fc5822ccc0ac46fea4707f5d --- /dev/null +++ b/ttcn/LibMec/UEAppInterfaceAPI/ttcn/UEAppInterfaceAPI_TypesAndValues.ttcn @@ -0,0 +1,188 @@ +/** + * @desc The ETSI MEC ISG MEC011 Application Enablement API described using OpenAPI + * @see http://www.etsi.org/deliver/etsi_gs/MEC/001_099/011/01.01.01_60/gs_mec011v010101p.pdf + */ +module UEAppInterfaceAPI_TypesAndValues { + + // JSON + import from JSON all; + + // LibCommon + import from LibCommon_BasicTypesAndValues all; + + /** + * @desc Problem Details for HTTP APIs + * @member type_ A URI reference according to IETF RFC 3986 that identifies the problem type + * @member title A short, human-readable summary of the problem type + * @member status The HTTP status code for this occurrence of the problem + * @member detail A human-readable explanation specific to this occurrence of the problem + * @member instance A URI reference that identifies the specific occurrence of the problem + * @see IETF RFC 7807 Clause 3. The Problem Details JSON Object + */ + type record ProblemDetails { + JSON.String type_, + JSON.String title, + UInt32 status, + JSON.String detail, + JSON.String instance + } with { + variant (type_) "name as 'type'"; + } + + /** + * @desc Information on available applications. + */ + type record ApplicationList { + AppInfo appInfo, + VendorSpecificExt vendorSpecificExt + } + + /** + * @desc Information on application context created by the MEC system. + */ + type record AppContext { + ContextId contextId, + AssociateUeAppId associateUeAppId, + RequiredAppInfo appInfo, + CallbackReference callbackReference optional + } + + /** + * @desc The parameters used in the method "Receiving notification events". + */ + type record NotificationEvent { + ReferenceURL referenceURI + } + + /** + * @desc Extension for vendor specific information. + */ + type record length(0..infinity) of VendorSpecificExt VendorSpecificExtList; + + /** + * @desc Extension for vendor-specific information. + */ + type record VendorSpecificExt { + VendorId vendorId + } + + /** + * @desc Uniquely identifies the application context in the MEC system. Assigned by the MEC system and included in the response. The length of the value shall not exceed 32 characters. + */ + type JSON.String ContextId length(1..32) with {encode "length(1..32)"}; + + /** + * @desc Uniquely identifies the UE application. Included in the request. The length of the value shall not exceed 32 characters. + */ + type JSON.String AssociateUeAppId length(1..32) with {encode "length(1..32)"}; + + /** + * @desc Vendor identifier. The length of the value shall not exceed 32 characters. The rest of the structure of this vendor specific extension is not defined. + */ + type JSON.String VendorId; + + /** + * @desc User applications available for the UE application. + */ + type record of AppInfoList AppInfo; + + /** + * @desc User applications available for the UE application. + */ + type record AppInfoList { + AppName appName, + AppProvider appProvider, + AppDescription appDescription, + AppSoftVersion appSoftVersion optional, + AppCharcs appCharcs optional + } + + /** + * @desc Included in the request. + */ + type record RequiredAppInfo { + AppName appName, + AppProvider appProvider, + ReferenceURL referenceURL, + AppSoftVersion appSoftVersion optional, + AppDescription appDescription optional, + AppPackageSource appPackageSource optional + } + + /** + * @desc The application characteristics relate to the system resources consumed by the application. UE application can use this information e.g., for estimating the cost of use of the application or for the expected user experience. + */ + type record AppCharcs { + Memory memory, + Storage storage, + Latency latency, + Bandwidth bandwidth, + ServiceCont serviceCont + } + + /** + * @desc The maximum size in Mbytes of the memory resource reserved for the MEC application instance in the MEC system. + */ + type UInt32 Memory; + + /** + * @desc The maximum size in Mbytes of the storage resource expected to be used by the MEC application instance in the MEC system. + */ + type UInt32 Storage; + + /** + * @desc The target round trip time in milliseconds supported by the MEC system for the MEC application instance. + */ + type UInt32 Latency; + + /** + * @desc The required connection bandwidth in kbit/s for the use of the mobile edge application instance. + */ + type UInt32 Bandwidth; + + /** + * @desc Required service continuity mode for this application. + */ + type enumerated ServiceCont { + SERVICE_CONTINUITY_NOT_REQUIRED, + SERVICE_CONTINUITY_REQUIRED + } + + /** + * @desc Name of the MEC application. The length of the value shall not exceed 32 characters. + */ + type JSON.String AppName length(1..32) with {encode "length(1..32)"}; + + /** + * @desc Provider of the MEC application. The length of the value shall not exceed 32 characters. + */ + type JSON.String AppProvider length(1..32) with {encode "length(1..32)"}; + + /** + * @desc Software version of the MEC application. The length of the value shall not exceed 32 characters. + */ + type JSON.String AppSoftVersion length(1..32) with {encode "length(1..32)"}; + + /** + * @desc Human readable description of the MEC application. NOTE the language support may be limited. The length of the value shall not exceed 128 characters. + */ + type JSON.String AppDescription length(1..128) with {encode "length(1..128)"}; + + /** + * @desc URI assigned by the UE application to receive application lifecycle related notifications. Included in the request. This subscription stays alive for the lifetime of the application context. + */ + type JSON.String CallbackReference; + + /** + * @desc Address of the user application. Used as the reference URL for the application. Assigned by the MEC system and included in the response. + */ + type JSON.AnyURI ReferenceURL; + + /** + * @desc URI of the application package. Included in the request if the application is not one in the ApplicationList. appPackageSource enables on-boarding of the application package into the MEC system. The application package shall comply with the definitions in clause 6.2.1.2 of ETSI GS MEC 010-2. + */ + type JSON.AnyURI AppPackageSource; + +} with { + encode "JSON" +} // End of module UEAppInterfaceAPI_TypesAndValues diff --git a/ttcn/LibMec/ttcn/LibMec_Pixits.ttcn b/ttcn/LibMec/ttcn/LibMec_Pixits.ttcn index ac20b00f919895ee1bcdfc660f03ade32b401dc9..73e9d7ecacc2ebac618fedda9737725f2db94241 100644 --- a/ttcn/LibMec/ttcn/LibMec_Pixits.ttcn +++ b/ttcn/LibMec/ttcn/LibMec_Pixits.ttcn @@ -14,7 +14,13 @@ module LibMec_Pixits { modulepar charstring PX_ME_APP_Q_UE_IDENTITY_ID_URI := "/ui/v2/"; - modulepar charstring PX_RNIS_SUBSCRITIONS_URI := "/rni/v2/subscriptions/"; + modulepar charstring PX_SVC_MGMT_TRANS_URI := "/mec_app_support/v2/transports"; + + modulepar charstring PX_SVC_MGMT_APP_URI := "/mec_service_mgmt/v2/application"; + + modulepar charstring PX_RNIS_SUBSCRITIONS_URI := "/rni/v2/subscriptions"; + + modulepar charstring PX_RNIS_QUERIES_URI := "/rni/v2/queries"; modulepar charstring PX_ME_BWM_URI := "/bwm/v2/bw_allocations"; diff --git a/ttcn/patch_lib_http/LibItsHttp_JsonMessageBodyTypes.ttcn b/ttcn/patch_lib_http/LibItsHttp_JsonMessageBodyTypes.ttcn index b060cb49bc9682a15b596b9dbc61041dfb442480..58f757c93de882d7ae62a9b58b36255be4c704a8 100644 --- a/ttcn/patch_lib_http/LibItsHttp_JsonMessageBodyTypes.ttcn +++ b/ttcn/patch_lib_http/LibItsHttp_JsonMessageBodyTypes.ttcn @@ -8,9 +8,15 @@ module LibItsHttp_JsonMessageBodyTypes { import from RnisAPI_TypesAndValues all; // LibMec/BwManagementApi import from BwManagementAPI_TypesAndValues all; +<<<<<<< HEAD // LibMec/Ams import from Ams_TypesAndValues all; +======= + // LibMec/AppEnablementAPI + import from AppEnablementAPI_TypesAndValues all; + +>>>>>>> b55fa1944c45eb362e0dd6ad00f2cda74f727b50 /** * This file volontary contains a trivial declaration of the type JsonBody. * In accordance with your TTCN-3 module LibItsHttp_JSONTypes, you have to change the JsonBody typing. @@ -19,6 +25,7 @@ module LibItsHttp_JsonMessageBodyTypes { type union JsonBody { // TODO Add here your custom variants +<<<<<<< HEAD UserInfo userInfo, UserList userList, ZoneInfo zoneInfo, @@ -36,6 +43,27 @@ module LibItsHttp_JsonMessageBodyTypes { Ams_TypesAndValues.ProblemDetails problemDetails_ams, Ams_TypesAndValues.RegistrationRequest registrationRequest_ams, Ams_TypesAndValues.AmsSubscriptionLinkLists subscriptionLinkList_ams, +======= + UserInfo userInfo, + UserList userList, + ZoneInfo zoneInfo, + AccessPointList accessPointList, + UserTrackingSubscription userTrackingSubscription, + ZonalTrafficSubscription zonalTrafficSubscription, + UEidentityAPI_TypesAndValues.ProblemDetails problemDetails_ue_identity, + UeIdentityTagInfo ueIdentityTagInfo, + SubscriptionLinkList subscriptionLinkList, + CellChangeSubscription cellChangeSubscription, + RabInfo rabInfo, + PlmnInfo plmnInfo, + RnisAPI_TypesAndValues.ProblemDetails problemDetails_rni, + BwInfo bwInfo, + BwManagementAPI_TypesAndValues.ProblemDetails problemDetails_bw_management, + TransportInfoList transportInfoList, + TrafficRuleList trafficRuleList, + TrafficRule trafficRule, + AppEnablementAPI_TypesAndValues.ProblemDetails problemDetails_svc_mgmt, +>>>>>>> b55fa1944c45eb362e0dd6ad00f2cda74f727b50 universal charstring raw } with { variant "" diff --git a/ttcn/patch_lib_http/LibItsHttp_JsonTemplates.ttcn b/ttcn/patch_lib_http/LibItsHttp_JsonTemplates.ttcn index b0986e508106a6ab62a14d91fb46cd4e0400ee0c..20c1676376e2a784e259c80ba3443bab2e57c282 100644 --- a/ttcn/patch_lib_http/LibItsHttp_JsonTemplates.ttcn +++ b/ttcn/patch_lib_http/LibItsHttp_JsonTemplates.ttcn @@ -9,6 +9,7 @@ * All rights reserved. */ module LibItsHttp_JsonTemplates { +<<<<<<< HEAD // LibMec/LocationAPI import from LocationAPI_TypesAndValues all; @@ -253,4 +254,277 @@ group bw_management_api { } // End of group bw_management_api +======= + + // LibMec/LocationAPI + import from LocationAPI_TypesAndValues all; + import from LocationAPI_Templates all; + // LibMec/UEidentityAPI + import from UEidentityAPI_TypesAndValues all; + import from UEidentityAPI_Templates all; + // LibMec/RnisAPI + import from RnisAPI_TypesAndValues all; + import from RnisAPI_Templates all; + // LibMec/BwManagementAPI + import from BwManagementAPI_TypesAndValues all; + import from BwManagementAPI_Templates all; + // LibMec/AppEnablementAPI + import from AppEnablementAPI_TypesAndValues all; + import from AppEnablementAPI_Templates all; + + // TODO Add here your custom RFCs import + + // LibItsHttp + import from LibItsHttp_JsonMessageBodyTypes all; + import from LibItsHttp_JSONTypes all; + + template (value) JsonBody m_json_body_raw( + in template (value) charstring p_raw + ) := { + raw := p_raw + } // End of template m_json_body_raw + + template (present) JsonBody mw_json_body_raw( + template (present) charstring p_raw := ? + ) := { + raw := p_raw + } // End of template mw_json_body_raw + + group locarion_api { + + template (value) JsonBody m_body_json_user_info( + in template (value) UserInfo p_user_info + ) := { + userInfo := p_user_info + } // End of template m_body_json_user_info + + template (present) JsonBody mw_body_json_user_info( + template (present) UserInfo p_user_info := ? + ) := { + userInfo := p_user_info + } // End of template mw_body_json_user_info + + template (value) JsonBody m_body_json_user_list( + in template (value) UserList p_user_list + ) := { + userList := p_user_list + } // End of template m_body_json_user_list + + template (present) JsonBody mw_body_json_user_list( + template (present) UserList p_user_list := ? + ) := { + userList := p_user_list + } // End of template mw_body_json_user_list + + template (value) JsonBody m_body_json_zone_info( + in template (value) ZoneInfo p_zone_info + ) := { + zoneInfo := p_zone_info + } // End of template m_body_json_zone_info + + template (present) JsonBody mw_body_json_zone_info( + template (present) ZoneInfo p_zone_info := ? + ) := { + zoneInfo := p_zone_info + } // End of template mw_body_json_zone_info + + template (value) JsonBody m_body_json_access_point_list( + in template (value) AccessPointList p_access_point_list + ) := { + accessPointList := p_access_point_list + } // End of template m_body_json_access_point_list + + template (present) JsonBody mw_body_json_access_point_list( + template (present) AccessPointList p_access_point_list := ? + ) := { + accessPointList := p_access_point_list + } // End of template mw_body_json_access_point_list + + template (value) JsonBody m_body_json_user_tracking_subscription( + in template (value) UserTrackingSubscription p_user_tracking_subscription + ) := { + userTrackingSubscription := p_user_tracking_subscription + } // End of template m_body_json_user_tracking_subscription + + template (present) JsonBody mw_body_json_user_tracking_subscription( + template (present) UserTrackingSubscription p_user_tracking_subscription := ? + ) := { + userTrackingSubscription := p_user_tracking_subscription + } // End of template mw_body_json_user_rtracking_subscription + + template (value) JsonBody m_body_json_zonal_traffic_subscription( + in template (value) ZonalTrafficSubscription p_zonal_traffic_subscription + ) := { + zonalTrafficSubscription := p_zonal_traffic_subscription + } // End of template m_body_json_zonal_traffic_subscription + + template (present) JsonBody mw_body_json_zonal_traffic_subscription( + template (present) ZonalTrafficSubscription p_zonal_traffic_subscription := ? + ) := { + zonalTrafficSubscription := p_zonal_traffic_subscription + } // End of template mw_body_json_zonal_traffic_subscription + + } // End of group locarion_api + + group ue_identity_api { + + template (value) JsonBody m_body_json_ue_identity_tag_info( + in template (value) UeIdentityTagInfo p_ueIdentityTagInfo + ) := { + ueIdentityTagInfo := p_ueIdentityTagInfo + } // End of template m_body_json_ue_identity_tag_info + + template (present) JsonBody mw_body_json_ue_identity_tag_info( + template (present) UeIdentityTagInfo p_ueIdentityTagInfo := ? + ) := { + ueIdentityTagInfo := p_ueIdentityTagInfo + } // End of template mw_body_json_ue_identity_tag_info + + template (value) JsonBody m_body_json_ue_identity_problem_details( + in template (value) UEidentityAPI_TypesAndValues.ProblemDetails p_problemDetails + ) := { + problemDetails_ue_identity := p_problemDetails + } // End of template m_body_json_ue_identity_problem_details + + template (present) JsonBody mw_body_json_ue_identity_problem_details( + template (present) UEidentityAPI_TypesAndValues.ProblemDetails p_problemDetails := ? + ) := { + problemDetails_ue_identity := p_problemDetails + } // End of template mw_body_json_ue_identity_problem_details + + } // End of group ue_identity_api + + group rnis_subscriptions { + + template (value) JsonBody m_body_json_subscriptions_list( + in template (value) SubscriptionLinkList p_subscriptionLinkList + ) := { + subscriptionLinkList := p_subscriptionLinkList + } // End of template m_body_json_subscriptions_list + + template (present) JsonBody mw_body_json_subscriptions_list( + template (present) SubscriptionLinkList p_subscriptionLinkList := ? + ) := { + subscriptionLinkList := p_subscriptionLinkList + } // End of template mw_body_json_subscriptions_list + + template (value) JsonBody m_body_json_cell_change_subscription( + in template (value) CellChangeSubscription p_cellChangeSubscription + ) := { + cellChangeSubscription := p_cellChangeSubscription + } // End of template m_body_json_cell_change_subscription + + template (present) JsonBody mw_body_json_cell_change_subscription( + template (present) CellChangeSubscription p_cellChangeSubscription := ? + ) := { + cellChangeSubscription := p_cellChangeSubscription + } // End of template mw_body_json_cell_change_subscription + + template (value) JsonBody m_body_json_rab_info( + in template (value) RabInfo p_rabInfo + ) := { + rabInfo := p_rabInfo + } // End of template m_body_json_rab_info + + template (present) JsonBody mw_body_json_rab_info( + template (present) RabInfo p_rabInfo := ? + ) := { + rabInfo := p_rabInfo + } // End of template mw_body_json_rab_info + + template (value) JsonBody m_body_json_plmn_info( + in template (value) PlmnInfo p_plmnInfo + ) := { + plmnInfo := p_plmnInfo + } // End of template m_body_json_plmn_info + + template (present) JsonBody mw_body_json_plmn_info( + template (present) PlmnInfo p_plmnInfo := ? + ) := { + plmnInfo := p_plmnInfo + } // End of template mw_body_json_plmn_info + + template (value) JsonBody m_body_json_rni_problem_details( + in template (value) RnisAPI_TypesAndValues.ProblemDetails p_problemDetails + ) := { + problemDetails_rni := p_problemDetails + } // End of template m_body_json_rni_problem_details + + template (present) JsonBody mw_body_json_rni_problem_details( + template (present) RnisAPI_TypesAndValues.ProblemDetails p_problemDetails := ? + ) := { + problemDetails_rni := p_problemDetails + } // End of template mw_body_json_rni_problem_details + + } // End of group rnis_subscriptions + + group bw_management_api { + + template (value) JsonBody m_body_json_bw_info( + in template (value) BwInfo p_bwInfo + ) := { + bwInfo := p_bwInfo + } // End of template m_body_json_bw_info + + template (present) JsonBody mw_body_json_bw_info( + template (present) BwInfo p_bwInfo := ? + ) := { + bwInfo := p_bwInfo + } // End of template mw_body_json_bw_info + + } // End of group bw_management_api + + group svc_mgmt { + + template (value) JsonBody m_body_json_transport_info_list( + in template (value) TransportInfoList p_transportInfoList + ) := { + transportInfoList := p_transportInfoList + } // End of template m_body_json_transport_info_list + + template (present) JsonBody mw_body_json_transport_info_list( + template (present) TransportInfoList p_transportInfoList := ? + ) := { + transportInfoList := p_transportInfoList + } // End of template mw_body_json_transport_info_list + + template (value) JsonBody m_body_json_traffic_rule( + in template (value) TrafficRule p_trafficRule + ) := { + trafficRule := p_trafficRule + } // End of template m_body_json_traffic_rule + + template (present) JsonBody mw_body_json_traffic_rule( + template (present) TrafficRule p_trafficRule := ? + ) := { + trafficRule := p_trafficRule + } // End of template mw_body_json_traffic_rule + + template (value) JsonBody m_body_json_traffic_rules_list( + in template (value) TrafficRuleList p_trafficRuleList + ) := { + trafficRuleList := p_trafficRuleList + } // End of template m_body_json_traffic_rules_list + + template (present) JsonBody mw_body_json_traffic_rules_list( + template (present) TrafficRuleList p_trafficRuleList := ? + ) := { + trafficRuleList := p_trafficRuleList + } // End of template mw_body_json_traffic_rules_list + + template (value) JsonBody m_body_json_app_enablement_problem_details( + in template (value) AppEnablementAPI_TypesAndValues.ProblemDetails p_problemDetails + ) := { + problemDetails_svc_mgmt := p_problemDetails + } // End of template m_body_json_app_enablement_problem_details + + template (present) JsonBody mw_body_json_app_enablement_problem_details( + template (present) AppEnablementAPI_TypesAndValues.ProblemDetails p_problemDetails := ? + ) := { + problemDetails_svc_mgmt := p_problemDetails + } // End of template mw_body_json_app_enablement_problem_details + + } // End of group svc_mgmt + +>>>>>>> b55fa1944c45eb362e0dd6ad00f2cda74f727b50 } // End of module LibItsHttp_JsonTemplates