Commit 592f594d authored by Tien-Thinh Nguyen's avatar Tien-Thinh Nguyen

Send notification for an event to the subscribers (NF)

parent c240e30e
......@@ -1135,7 +1135,7 @@ evsub_id_t smf_app::handle_event_exposure_subscription(
std::shared_ptr<itti_sbi_event_exposure_request> msg) {
Logger::smf_app().info(
"Handle an Event Exposure Subscription Request from an AMF (HTTP version %d)",
"Handle an Event Exposure Subscription Request from a NF (HTTP version %d)",
msg->http_version);
// Generate a subscription ID Id and store the corresponding information in a map (subscription id, info)
......@@ -1703,6 +1703,7 @@ void smf_app::get_ee_subscriptions(evsub_id_t sub_id, std::vector<std::shared_pt
}
//---------------------------------------------------------------------------------------------
//std::vector<std::shared_ptr<smf_subscription>> subscriptions
void smf_app::get_ee_subscriptions(smf_event_t ev, supi64_t supi, pdu_session_id_t pdu_session_id, std::shared_ptr<smf_subscription> subscription) {
for (auto const& i : smf_event_subscriptions) {
if ((i.first.second == ev) && (i.second->supi == supi) && (i.second->pdu_session_id == pdu_session_id)){
......
......@@ -118,29 +118,35 @@ void smf_event::send_ee_pdu_session_release(supi64_t supi,
uint8_t http_version) {
Logger::smf_app().debug("Send request to N11 to triger PDU Session Release Notification, SUPI " SUPI_64_FMT " , PDU Session ID %d, HTTP version %d", supi, pdu_session_id, http_version);
//std::vector < std::shared_ptr < smf_subscription >> subscriptions;
std::shared_ptr<smf_subscription> subscription = {};
smf_app_inst->get_ee_subscriptions(smf_event_t::SMF_EVENT_PDU_SES_REL, supi,
pdu_session_id, subscription);
std::vector < std::shared_ptr < smf_subscription >> subscriptions;
smf_app_inst->get_ee_subscriptions(smf_event_t::SMF_EVENT_PDU_SES_REL, subscriptions);
if (subscription.get() != nullptr) {
if (subscriptions.size() > 0) {
//Send request to N11 to trigger the notification to the subscribed event
Logger::smf_app().debug(
"Send ITTI msg to SMF N11 to trigger the event notification");
"Send ITTI msg to SMF N11 to trigger the event notification");
std::shared_ptr<itti_n11_notify_subscribed_event> itti_msg = std::make_shared
< itti_n11_notify_subscribed_event > (TASK_SMF_APP, TASK_SMF_N11);
< itti_n11_notify_subscribed_event > (TASK_SMF_APP, TASK_SMF_N11);
for (auto i: subscriptions) {
event_notification ev_notif = { };
ev_notif.set_supi(supi);
ev_notif.set_pdu_session_id(pdu_session_id);
ev_notif.set_smf_event(smf_event_t::SMF_EVENT_PDU_SES_REL);
ev_notif.set_supi(supi);
ev_notif.set_notif_uri(i.get()->notif_uri);
ev_notif.set_notif_id(i.get()->notif_id);
itti_msg->event_notifs.push_back(ev_notif);
}
event_notification ev_notif = { };
ev_notif.set_pdu_session_id(pdu_session_id);
itti_msg->notif_id = std::to_string(subscription->sub_id);
itti_msg->event_notifs.push_back(ev_notif);
//itti_msg->notif_id = std::to_string(subscription->sub_id);
itti_msg->http_version = http_version;
int ret = itti_inst->send_msg(itti_msg);
if (RETURNok != ret) {
Logger::smf_app().error(
"Could not send ITTI message %s to task TASK_SMF_N11",
itti_msg->get_msg_name());
"Could not send ITTI message %s to task TASK_SMF_N11",
itti_msg->get_msg_name());
}
}
}
......@@ -813,12 +813,12 @@ smf_event_t event_notification::get_smf_event() const {
}
//-----------------------------------------------------------------------------
supi_t event_notification::get_supi() const {
supi64_t event_notification::get_supi() const {
return m_supi;
}
//-----------------------------------------------------------------------------
void event_notification::set_supi(const supi_t &value) {
void event_notification::set_supi(const supi64_t &value) {
m_supi = value;
m_supi_is_set = true;
}
......@@ -877,4 +877,24 @@ bool event_notification::is_psi_is_set() const {
}
//-----------------------------------------------------------------------------
void event_notification::set_notif_uri(std::string const &value){
m_notif_uri = value;
}
//-----------------------------------------------------------------------------
std::string event_notification::get_notif_uri() const {
return m_notif_uri;
}
//-----------------------------------------------------------------------------
void event_notification::set_notif_id(std::string const &value) {
m_notif_id = value;
}
//-----------------------------------------------------------------------------
std::string event_notification::get_notif_id() const {
return m_notif_id;
}
......@@ -584,8 +584,8 @@ class event_notification {
void set_smf_event(const smf_event_t &ev);
smf_event_t get_smf_event() const;
void set_supi(const supi_t &supi);
supi_t get_supi() const;
void set_supi(const supi64_t &supi);
supi64_t get_supi() const;
bool is_supi_is_set() const;
//m_AdIpv4Addr
void set_ad_ipv4_addr(std::string const &value);
......@@ -600,11 +600,19 @@ class event_notification {
pdu_session_id_t get_pdu_session_id() const;
bool is_psi_is_set() const;
void set_notif_uri(std::string const &value);
std::string get_notif_uri() const;
void set_notif_id(std::string const &value);
std::string get_notif_id() const;
private:
std::string m_notif_uri; //m_NotifUri;
std::string m_notif_id; //m_NotifId;
smf_event_t m_event; //SmfEvent
//std::string m_TimeStamp;
supi_t m_supi;
supi64_t m_supi;
bool m_supi_is_set;
//for a UE IP address change
......
......@@ -57,6 +57,7 @@ using json = nlohmann::json;
extern itti_mw *itti_inst;
extern smf_n11 *smf_n11_inst;
extern smf_config smf_cfg;
extern smf_app *smf_app_inst;
void smf_n11_task(void*);
// To read content of the response from AMF
......@@ -101,6 +102,12 @@ void smf_n11_task(void *args_p) {
shared_msg));
break;
case N11_NOTIFY_SUBSCRIBED_EVENT:
smf_n11_inst->notify_subscribed_event(
std::static_pointer_cast<itti_n11_notify_subscribed_event>(
shared_msg));
break;
case TERMINATE:
if (itti_msg_terminate *terminate =
dynamic_cast<itti_msg_terminate*>(msg)) {
......@@ -499,3 +506,116 @@ void smf_n11::send_sm_context_status_notification(
curl_global_cleanup();
}
void smf_n11::notify_subscribed_event(
std::shared_ptr<itti_n11_notify_subscribed_event> msg) {
Logger::smf_n11().debug("Send notification for the subscribed event to the subscription");
int still_running = 0, numfds = 0, res = 0;
CURLMsg *curl_msg = nullptr;
CURL *curl = nullptr;
CURLcode return_code;
int http_status_code = 0, msgs_left = 0;
CURLM* m_curl_multi;
char *url = nullptr;
std::unique_ptr<std::string> httpData(new std::string());
std::string data;
//init curl
curl_global_init(CURL_GLOBAL_ALL);
m_curl_multi = curl_multi_init();
//init header
struct curl_slist *headers = NULL;
headers = curl_slist_append(headers, "Accept: application/json");
headers = curl_slist_append(headers, "Content-Type: application/json");
headers = curl_slist_append(headers, "charsets: utf-8");
//create and add an easy handle to a multi curl request
for (auto i: msg->event_notifs) {
//CURL *temp = curl_create_handle(i.get_notif_uri(), &data );
//CURL *temp = curl_create_handle(i, &data );
//curl_multi_add_handle(m_curl_multi, temp);
CURL *curl = curl_easy_init();
if (curl){
std::string url = i.get_notif_uri() ;
Logger::smf_n11().debug("Send notification to NF with URI: %s", url);
curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
curl_easy_setopt(curl, CURLOPT_URL, url.c_str() );
curl_easy_setopt(curl, CURLOPT_HTTPGET,1);
curl_easy_setopt(curl, CURLOPT_TIMEOUT_MS, 100L);
// Hook up data handling function.
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, &callback);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, data);
curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
}
curl_multi_add_handle(m_curl_multi, curl);
}
curl_multi_perform(m_curl_multi, &still_running);
//block until activity is detected on at least one of the handles or MAX_WAIT_MSECS has passed.
do {
res = curl_multi_wait(m_curl_multi, NULL, 0, 1000, &numfds);
if(res != CURLM_OK) {
Logger::smf_n11().debug("Error: curl_multi_wait() returned %d!", res);
}
curl_multi_perform(m_curl_multi, &still_running);
} while(still_running);
//process multiple curl
//read the messages
while ((curl_msg = curl_multi_info_read(m_curl_multi, &msgs_left))) {
if (curl_msg->msg == CURLMSG_DONE) {
curl = curl_msg->easy_handle;
return_code = curl_msg->data.result;
res = curl_easy_getinfo(curl, CURLINFO_EFFECTIVE_URL, &url);
if(return_code != CURLE_OK) {
Logger::smf_n11().debug("Error: CURL error code %d!", curl_msg->data.result);
continue;
}
// Get HTTP status code
curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &http_status_code);
Logger::smf_n11().info("HTTP status code %d!", http_status_code);
//remove this handle from the multi session and end this handle
curl_multi_remove_handle(m_curl_multi, curl);
curl_easy_cleanup(curl);
} else {
Logger::smf_n11().debug("error after curl_multi_info_read(), CURLMsg %s", curl_msg->msg);
}
}
}
CURL * smf_n11::curl_create_handle (event_notification &ev_notif, std::string *httpData){
//create handle for a curl request
struct curl_slist *headers = NULL;
headers = curl_slist_append(headers, "Accept: application/json");
headers = curl_slist_append(headers, "Content-Type: application/json");
headers = curl_slist_append(headers, "charsets: utf-8");
CURL *curl = curl_easy_init();
if (curl){
std::string url = ev_notif.get_notif_uri() ;
Logger::smf_n11().debug("Send notification to NF with URI: %s", url);
curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
curl_easy_setopt(curl, CURLOPT_URL, url.c_str() );
//curl_easy_setopt(curl, CURLOPT_PRIVATE, str);
//curl_easy_setopt(curl, CURLOPT_VERBOSE, 0L);
curl_easy_setopt(curl, CURLOPT_HTTPGET,1);
curl_easy_setopt(curl, CURLOPT_TIMEOUT_MS, 100L);
// Hook up data handling function.
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, &callback);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, httpData);
curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
}
return curl;
}
......@@ -33,6 +33,7 @@
#include <map>
#include "smf.h"
#include <curl/curl.h>
#include "3gpp_29.503.h"
#include "smf_context.hpp"
#include "SmContextCreatedData.h"
......@@ -83,6 +84,22 @@ class smf_n11 {
void send_sm_context_status_notification(
std::shared_ptr<itti_n11_notify_sm_context_status> sm_context_status);
/*
* Send Notification for the associated event to the subscribers
* @param [std::shared_ptr<itti_n11_notify_subscribed_event>] msg: Content of message to be sent
* @return void
*/
void notify_subscribed_event(
std::shared_ptr<itti_n11_notify_subscribed_event> msg);
/*
* Create Curl handle for multi curl
* @param [event_notification&] ev_notif: content of the event notification
* @param [std::string *] data: data
* @return pointer to the created curl
*/
CURL * curl_create_handle (event_notification &ev_notif, std::string *data);
};
}
#endif /* FILE_SMF_N11_HPP_SEEN */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment