Page MenuHomePhabricator

opensips.cfg
No OneTemporary

opensips.cfg

# OpenSIPS configuration
This is a configuration example for handling push notifications for Linphone
and Sylk Mobile applications.
The token data generated by the device is sent as parameters to the Contact
header. Later, when an INVITE comes in, if a token is found for the called
party, a push notification is sent to each mobile device which will wake up
and register while the call is in progress. These late registrations will
cause OpenSIPS to fork the initial request to the newly registered contacts.
## SQL storage
The token is saved into a MySQL table.
```
CREATE TABLE `push_tokens` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`username` char(64) NOT NULL DEFAULT '',
`domain` char(64) NOT NULL DEFAULT '',
`platform` char(64) NOT NULL DEFAULT '',
`app` char(255) NOT NULL DEFAULT '',
`token` char(255) NOT NULL DEFAULT '',
`sip_instance` char(255) NOT NULL DEFAULT '',
`user_agent` char(255) NOT NULL DEFAULT '',
`last_modified` datetime NOT NULL DEFAULT current_timestamp(),
`silent` char(1) NOT NULL DEFAULT '0',
PRIMARY KEY (`id`),
UNIQUE KEY `token_idx` (`username`,`domain`,`sip_instance`,`app`)
);
```
## Loaded modules
```
loadmodule "event_routing.so"
```
## Handle REGISTER route
```
route[REGISTER] {
...
# parse the Contact header paramaters or the Contact uri parameters of
# the register and save the push token to the database
$avp(sip_instance) = $(ct.fields(params){param.value,+sip.instance});
if (!$avp(sip_instance)) {
$avp(sip_instance) = $(ct.fields(uri){uri.param,pn-device});
}
if ($avp(sip_instance)) {
# try to find if the device is mobile
$avp(pn_type) = $(ct.fields(uri){uri.param,pn-type});
if (!$avp(pn_type)) {
$avp(pn_type) = $(ct.fields(uri){uri.param,pn-type});
}
$avp(pn_app) = $(ct.fields(uri){uri.param,app-id});
if (!$avp(pn_app)) {
$avp(pn_app) = $(ct.fields(uri){uri.param,pn-app});
}
$avp(pn_token) = $(ct.fields(uri){uri.param,pn-tok});
if (!$avp(pn_token)) {
$avp(pn_token) = $(ct.fields(uri){uri.param,pn-tok});
}
$avp(pn_silent) = $(ct.fields(uri){uri.param,pn-silent});
if (!$avp(pn_silent)) {
$avp(pn_silent) = $(ct.fields(uri){uri.param,pn-silent});
}
if (!$avp(pn_silent)) {
$avp(pn_silent) = "0";
}
}
if (save("location")) {
# save data required later for push notifications
if ($avp(pn_type) and $avp(pn_token) and $avp(pn_app)) {
$avp(query) = "SELECT token from push_tokens where username = '" + $(tU{s.escape.common}) + "' and domain = '" + $(td{s.escape.common}) + "' and app
xlog("L_DBG", "[CONFIG] REGISTER push SQL query: $avp(query)\n");
avp_db_query($avp(query), "$avp(old_pn_token)");
if (not $avp(old_pn_token)) {
$avp(query) = "INSERT into push_tokens (username, domain, platform, app, token, sip_instance, user_agent, silent) values ('" + $(tU{s.escape.comm
xlog("L_DBG", "[CONFIG] REGISTER push SQL query: $avp(query)\n");
avp_db_query($avp(query));
} else {
$avp(query) = "UPDATE push_tokens set silent = '" + $(avp(pn_silent){s.escape.common}) + "', last_modified = NOW(), token = '" + $(avp(pn_token){
xlog("L_DBG", "[CONFIG] REGISTER push SQL query: $avp(query)\n");
avp_db_query($avp(query));
}
}
}
}
```
## Handle INVITE route
```
route[INVITE] {
...
$avp(sip_application_type) = "audio";
if (has_body("application/sdp")) {
if (search_body("m=audio")) {
$avp(sip_application_type) = "audio";
}
if (search_body("m=video")) {
if (is_avp_set("$avp(sip_application_type)")) {
pv_printf($avp(sip_application_type), "$avp(sip_application_type), video");
} else {
$avp(sip_application_type) = "video";
}
}
if (search_body("(m=message).*?(MSRP)")) {
if (search_body("a=file-selector")) {
if (is_avp_set("$avp(sip_application_type)")) {
pv_printf($avp(sip_application_type), "$avp(sip_application_type), file-transfer");
} else {
$avp(sip_application_type) = "file-transfer";
}
} else {
if (is_avp_set("$avp(sip_application_type)")) {
pv_printf($avp(sip_application_type), "$avp(sip_application_type), chat");
} else {
$avp(sip_application_type) = "chat";
}
}
}
}
# load push notifications tokens saved during register and wake up the devices
$avp(query) = "SELECT token, app, platform, sip_instance from push_tokens WHERE username='" + $(var(user){s.escape.common}) + "' AND domain='" + $(var(domain){s.escape.common}) + "'";
xlog("L_DBG", "[CONFIG] $avp(query)\n");
$var(i) = 0;
store_dlg_value("late_forking","0");
if (avp_db_query($avp(query), "$avp(pn_token);$avp(pn_app);$avp(pn_platform);$avp(sip_instance)")) {
$var(pn_event) = 'incoming_session';
$var(from) = $fU + "@" + $fd;
$var(to) = $tU + "@" + $td;
$var(ci) = $ci;
for ($var(pn_token) in $(avp(pn_token)[*])) {
$var(pn_app) = $(avp(pn_app)[$var(i)]);
$var(pn_platform) = $(avp(pn_platform)[$var(i)]);
$var(sip_instance) = $(avp(sip_instance)[$var(i)]);
$var(i) = $var(i) + 1;
$avp(late_forking) = 1;
store_dlg_value("late_forking","1");
store_dlg_value("sip_application_type",$avp(sip_application_type));
$var(sip_application_type) = $avp(sip_application_type);
# Launch method
# launch is a fire and forget mechanism, the script does not block or wait, it just continues
$var(push_command) = "/usr/local/bin/sylk-pushclient --url \"http://81.23.228.160:8400/push\" --platform=\"" + $var(pn_platform) + "\" --appid=\"" + $var(pn_app) + "\" --from_name=\"" + $(fn{s.escape.common}) + "\" --mediatype=\"" + $var(sip_application_type) + "\" --event=\"" + $var(pn_event) + "\" --token=\"" + $var(pn_token) + "\" --deviceid=\"" + $var(sip_instance) +"\" --callid=\"" + $ci + "\" --from=\"" + $var(from) + "\" --to=\"" + $var(to) + "\"";
xlog("L_INFO", "[CONFIG] Push notification command: $var(push_command)\n");
launch(exec("$var(push_command)",, $var(rc)), "PN_RESULT");
}
}
if (not t_newtran()) {
sl_reply_error();
exit;
}
if ($avp(late_forking)) {
sl_send_reply(110, "Push sent");
t_wait_for_new_branches();
$avp(filter) = "aor="+$rU+"@"+$rd;
notify_on_event("E_UL_CONTACT_INSERT",$avp(filter), "LATE_FORKING", 40);
}
if (lookup("location")) {
xlog("L_INFO", "[CONFIG] $rU@$rd has online devices for $rm ($ci)\n");
} else {
if ($avp(late_forking)) {
xlog("L_INFO", "[CONFIG] $ru is not yet online ($ci)\n");
} else {
sl_send_reply(480, "User not online");
}
}
}
```
## Handle CANCEL route
```
route[CANCEL] {
...
if ($dlg_val(late_forking) == "1") {
$var(user) = $rU;
$var(domain) = $rd;
$var(sip_application_type) = $dlg_val(sip_application_type);
$avp(query) = "SELECT token, app, platform, sip_instance from push_tokens WHERE username='" + $(var(user){s.escape.common}) + "' AND domain='" + $(var(domain){s.escape.common}) + "'";
xlog("L_DBG", "[CONFIG] $avp(query)\n");
if (avp_db_query($avp(query), "$avp(pn_token);$avp(pn_app);$avp(pn_platform);$avp(sip_instance)")) {
$var(i) = 0;
$var(pn_event) = 'cancel';
$var(from) = $fU + "@" + $fd;
$var(to) = $tU + "@" + $td;
$var(ci) = $ci;
for ($var(pn_token) in $(avp(pn_token)[*])) {
$var(pn_app) = $(avp(pn_app)[$var(i)]);
$var(pn_platform) = $(avp(pn_platform)[$var(i)]);
$var(sip_instance) = $(avp(sip_instance)[$var(i)]);
$var(i) = $var(i) + 1;
# Launch method
# launch is a fire and forget mechanism, the script does not block or wait, it just continues
$var(push_command) = "/etc/opensips/config/siteconfig/pusher.py --url \"http://81.23.228.160:8400/push\" --platform=\"" + $var(pn_platform) + "\" --appid=\"" + $var(pn_app) + "\" --from_name=\"" + $(fn{s.escape.common}) + "\" --mediatype=\"" + $var(sip_application_type) + "\" --event=\"" + $var(pn_event) + "\" --token=\"" + $var(pn_token) + "\" --deviceid=\"" + $var(sip_instance) +"\" --callid=\"" + $ci + "\" --from=\"" + $var(from) + "\" --to=\"" + $var(to) + "\"";
xlog("L_INFO", "[CONFIG] Push notification command: $var(push_command)\n");
launch(exec("$var(push_command)",, $var(rc)), "PN_RESULT");
}
}
}
}
```
## Handle late forking route
```
route[LATE_FORKING] {
# handle incoming calls for mobile devices woken up by push notifications
INFO("$avp(aor) registered contact $avp(uri) while receiving an incoming call");
# take the contact described by the E_UL_CONTACT_INSERT
# event and inject it as a new branch into the original
# transaction
t_inject_branches("event");
}
```
## Handle push result route
```
route[PN_RESULT] {
if ($var(retcode) == "1") {
xlog("L_INFO", "[CONFIG] $var(pn_event) push notification for $var(to) on device $var(sip_instance) ($var(ci)) suceeded\n");
} else {
xlog("L_INFO", "[CONFIG] $var(pn_event) push notification for $var(to) on device $var(sip_instance) ($var(ci)) failed\n");
}
}
```

File Metadata

Mime Type
text/plain
Expires
Sat, Nov 23, 5:38 AM (1 d, 9 h)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
3408858
Default Alt Text
opensips.cfg (9 KB)

Event Timeline