Skip to content

Commit

Permalink
handle redirects & fast pickup priority
Browse files Browse the repository at this point in the history
* internal redirection when the call has been answered uses a refer sent to endpoint
  the endpoint should do a new invite and kamailio needs to redirect to proper media server.

* in the case of a *3xxx, kamailio queries/checks the the parking slot and redirects the call to the proper media server

* if the call was was parked with *4 and someones tries to pickup the call with *3xxx
  call would go next media server and if its not the media handling the parked call
  we would get a redirect to *3xxx
  perform an association
  send refer to endpoint
  the endpoint would send a new invite
  the fast pickup routines take precendence over associations
  and it happens that the channel *3xxx points at original media server initially used

* this commits sepasrates internal redirects from associations and handles it first on fastpick routines

(cherry picked from commit d832c6d)
  • Loading branch information
lazedo committed Dec 4, 2023
1 parent dccb8eb commit 5759eea
Show file tree
Hide file tree
Showing 4 changed files with 70 additions and 31 deletions.
9 changes: 7 additions & 2 deletions kamailio/authorization.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -322,6 +322,9 @@ route[KZ_AUTHORIZATION_SETUP]
# removes params
$avp(auth-user) = $(fU{s.before,;});

# auth scheme
$avp(auth-scheme) = $(fu{uri.scheme});

# Realm
# removes params and port
$avp(auth-domain) = $(fd{s.before,;}{s.before,:});
Expand All @@ -333,7 +336,9 @@ route[KZ_AUTHORIZATION_SETUP]
}

# Contact
$avp(auth-contact) = $(ct{s.escape.common}{s.replace,\','}{s.replace,$$,});
if ($ct != $null) {
$avp(auth-contact) = $(ct{s.escape.common}{s.replace,\','}{s.replace,$$,});
}

# User-Agent
$avp(auth-ua) = "unknown";
Expand All @@ -343,7 +348,7 @@ route[KZ_AUTHORIZATION_SETUP]

routes(KZ_AUTHORIZATION_SETUP);

$avp(auth-uri) = $_s($rz:$avp(auth-user)@$avp(auth-domain));
$avp(auth-uri) = $_s($avp(auth-scheme):$avp(auth-user)@$avp(auth-domain));
}

#!ifndef KZ_DISABLE_CONTACT_METHODS_REMOVAL
Expand Down
51 changes: 33 additions & 18 deletions kamailio/default.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,7 @@ loadmodule "sdpops.so"
######## Generic Hash Table container in shared memory ########
loadmodule "htable.so"
modparam("htable", "htable", "associations=>size=16;autoexpire=7200")
modparam("htable", "htable", "redirects=>size=16;autoexpire=60")
modparam("htable", "db_url", "KAZOO_DB_URL")

####### RTIMER module ##########
Expand Down Expand Up @@ -420,17 +421,19 @@ route[HANDLE_REFER]
if(isflagset(FLAG_REGISTERED_ENDPOINT)) {
$var(referred_by) = $_s($var(referred_by);endpoint_id=$(xavp(ulattrs=>token){re.subst,/(.*)@(.*)/\1/});account_id=$(xavp(ulattrs=>token){re.subst,/(.*)@(.*)/\2/}));
}
routes(HANDLE_EXTERNAL_REFER);
append_hf("Referred-By: $var(referred_by)\r\n");
} else {
if ($hdr(X-Redirect-Server) != $null) {
setflag(FLAG_ASSOCIATE_USER);
setflag(FLAG_ASSOCIATE_SERVER);
#!ifdef WITH_INTERNAL_LISTENER
$var(associate_media_server) = $_s($hdr(X-Redirect-Server);transport=$def(INTERNAL_PROTO));
$avp(associate_media_server) = $_s($hdr(X-Redirect-Server);transport=$def(INTERNAL_PROTO));
#!else
$var(associate_media_server) = $hdr(X-Redirect-Server);
$avp(associate_media_server) = $hdr(X-Redirect-Server);
#!endif
$var(associate_user_source) = $_s($rU@$rd:$rp);
$avp(associate_user_source) = $_s($rU@$rd:$rp);
} else {
routes(HANDLE_INTERNAL_REFER);
append_hf("Referred-By: $var(referred_by)\r\n");
}
record_route();
Expand Down Expand Up @@ -498,15 +501,15 @@ route[HANDLE_IN_DIALOG_REQUESTS]
record_route();
}

if ( is_method("REFER") && isflagset(FLAG_INTERNALLY_SOURCED)) {
if ( is_method("REFER") && isflagset(FLAG_INTERNALLY_SOURCED)) {
if ($hdr(X-Redirect-Server) != $null) {
setflag(FLAG_ASSOCIATE_USER);
setflag(FLAG_ASSOCIATE_SERVER);
#!ifdef WITH_INTERNAL_LISTENER
$var(associate_media_server) = $_s($hdr(X-Redirect-Server);transport=$def(INTERNAL_PROTO));
$avp(associate_media_server) = $_s($hdr(X-Redirect-Server);transport=$def(INTERNAL_PROTO));
#!else
$var(associate_media_server) = $hdr(X-Redirect-Server);
$avp(associate_media_server) = $hdr(X-Redirect-Server);
#!endif
$var(associate_user_source) = $_s($rU@$(du{uri.host}):$(du{uri.port}));
$avp(associate_user_source) = $_s($rU@$(du{uri.host}):$(du{uri.port}));
}
}

Expand Down Expand Up @@ -648,18 +651,13 @@ branch_route[MANAGE_BRANCH] {

route[RELAY]
{
if (is_method("INVITE|BYE|SUBSCRIBE|UPDATE|NOTIFY|CANCEL|REFER")) {
if(!t_is_set("branch_route")) t_on_branch("MANAGE_BRANCH");
}

if (isflagset(FLAG_INTERNALLY_SOURCED)) {
xlog("L_DEBUG", "internal to external\n");
route(INTERNAL_TO_EXTERNAL_RELAY);
} else {
xlog("L_DEBUG", "external to internal\n");
route(EXTERNAL_TO_INTERNAL_RELAY);
}

exit();
}

Expand All @@ -673,6 +671,14 @@ route[INTERNAL_TO_EXTERNAL_RELAY]
#!endif

routes(INTERNAL_TO_EXTERNAL_RELAY);
route(RELAY_TO_EXTERNAL);
}

route[RELAY_TO_EXTERNAL]
{
if (is_method("INVITE|BYE|SUBSCRIBE|UPDATE|NOTIFY|CANCEL|REFER")) {
if(!t_is_set("branch_route")) t_on_branch("MANAGE_BRANCH");
}

if(!isflagset(FLAG_RECORD_ROUTE_ADDED) && !has_totag()) {
xlog("L_DEBUG", "adding record route\n");
Expand Down Expand Up @@ -703,6 +709,14 @@ route[EXTERNAL_TO_INTERNAL_RELAY]
#!endif

routes(EXTERNAL_TO_INTERNAL_RELAY);
route(RELAY_TO_INTERNAL);
}

route[RELAY_TO_INTERNAL]
{
if (is_method("INVITE|BYE|SUBSCRIBE|UPDATE|NOTIFY|CANCEL|REFER")) {
if(!t_is_set("branch_route")) t_on_branch("MANAGE_BRANCH");
}

if(!t_is_set("onreply_route")) t_on_reply("INTERNAL_REPLY");
if(!t_is_set("failure_route")) t_on_failure("INTERNAL_FAULT");
Expand Down Expand Up @@ -907,12 +921,13 @@ onsend_route {
$var(user_source) = $xavp(ulrcd=>ruid);
}
$var(redirect_media) = $_s(sip:$(ruri{uri.host}):$(ruri{uri.port});transport=$sndto(sproto));
if (isflagset(FLAG_INTERNALLY_SOURCED)) {
$var(user_source) = $var(associate_user_source);
$var(redirect_media) = $var(associate_media_server);
}
xlog("L_INFO", "associate traffic from $var(user_source) with media server $var(redirect_media)\n");
$sht(associations=>$var(user_source)) = $var(redirect_media);
} else if (isflagset(FLAG_ASSOCIATE_SERVER) && is_request()) {
$var(user_source) = $avp(associate_user_source);
$var(redirect_media) = $avp(associate_media_server);
xlog("L_INFO", "associate traffic redirection from $var(user_source) with media server $var(redirect_media)\n");
$sht(redirects=>$var(user_source)) = $var(redirect_media);
}

#!ifdef SIP_TRACE_ROLE
Expand Down
13 changes: 8 additions & 5 deletions kamailio/dispatcher-role-5.7.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -166,9 +166,10 @@ route[DISPATCHER_CHECK_PREFERRED_ROUTE]
if($sel(cfg_get.kazoo.dispatcher_route_to_associated_media) == 1) {
$var(prefered_route) = $sht(associations=>$var(user_source));
xlog("L_INFO", "found association for contact uri $var(user_source)\n");
route(DISPATCHER_PREFERRED_ROUTE);
append_hf("X-Preferred-Media: true\r\n");
$var(preferred_route) = 1;
if(route(DISPATCHER_PREFERRED_ROUTE)) {
append_hf("X-Preferred-Media: true\r\n");
$var(preferred_route) = 1;
};
}
$sht(associations=>$var(user_source)) = $null;
}
Expand All @@ -179,8 +180,10 @@ route[DISPATCHER_CHECK_PREFERRED_ROUTE]
if($sel(cfg_get.kazoo.dispatcher_route_to_associated_media) == 1) {
$var(prefered_route) = $sht(associations=>$var(user_source));
xlog("L_INFO", "found association for ruri $var(user_source)\n");
route(DISPATCHER_PREFERRED_ROUTE);
append_hf("X-Preferred-Media: true\r\n");
if(route(DISPATCHER_PREFERRED_ROUTE)) {
append_hf("X-Preferred-Media: true\r\n");
$var(preferred_route) = 1;
};
}
$sht(associations=>$var(user_source)) = $null;
}
Expand Down
28 changes: 22 additions & 6 deletions kamailio/presence-fast-pickup.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -63,20 +63,35 @@ route[PRESENCE_FAST_PICKUP_REDIRECT]
}

$du = $var(fast_pickup_redirected_to);

append_hf("X-Preferred-Media: true\r\n");
}

route[DISPATCHER_SELECT_OVERRIDE_FAST_PICKUP_ATTEMPT]
route[DISPATCHER_SELECT_OVERRIDE_FAST_PICKUP]
{
if (!is_method("INVITE")) {
return;
}

$var(replaced_call_id) = "none";
# redirects
$var(user_source) = $(ct{tobody.user}) + "@" + $si + ":" + $sp;
if ($sht(redirects=>$var(user_source)) != $null) {
$vn(presence_redirect_to) = $sht(redirects=>$var(user_source));
$sht(redirects=>$var(user_source)) = $null;
route(PRESENCE_FAST_PICKUP_REDIRECT);
if($du != $null) {
xlog("L_INFO", "found redirect for user $var(user_source) , redirecting ($(ru{uri.user})) to $du\n");
route(RELAY_TO_INTERNAL);
exit();
}
}

$var(replaced_call_id) = "none";
if($hdr(Replaces)!= $null) {
$var(replaced_call_id) = $(hdr(Replaces){s.select,0,;});
}

# cookie
if($var(replaced_call_id) =~ "kfp+") {
remove_hf_re("^Replaces");
$var(PickupOptions) = $(var(replaced_call_id){re.subst,/^kfp\+(.{2})([^@]*)@(.*)/\1/}{s.decode.hexa});
Expand All @@ -97,6 +112,7 @@ route[DISPATCHER_SELECT_OVERRIDE_FAST_PICKUP_ATTEMPT]
}
}

# realtime query for replaces call-id location
if($sel(cfg_get.kazoo.presence_fast_pickup_realtime) == 1) {
if($var(replaced_call_id) != "none") {
xlog("L_INFO", "request has replaces call-id $var(replaced_call_id)\n");
Expand Down Expand Up @@ -142,9 +158,8 @@ route[DISPATCHER_SELECT_OVERRIDE_FAST_PICKUP_ATTEMPT]
}
}

##### CALL-PARK ####

##### STAR 5 CHECK ####
# park hash
## *5 check, call was parked with *3 and user is retrieving it with *5
if($sel(cfg_get.kazoo.presence_fast_pickup_star_5) == 1) {
if($(ru{uri.user}) =~ "^\*5") {
$var(park) = $_s(*3$(ru{uri.user}{s.substr,2,0})@$(ru{uri.domain}));
Expand All @@ -160,6 +175,7 @@ route[DISPATCHER_SELECT_OVERRIDE_FAST_PICKUP_ATTEMPT]
}
}

## park hash from uri.user
if($sel(cfg_get.kazoo.presence_fast_pickup_park) == 1) {
if($sht(park=>$(ru{uri.user})@$(ru{uri.domain})) != $null) {
$var(park) = $_s($(ru{uri.user})@$(ruri{uri.domain}));
Expand All @@ -175,7 +191,7 @@ route[DISPATCHER_SELECT_OVERRIDE_FAST_PICKUP_ATTEMPT]
}
}

##### CALL-PARK IN KAZOO ####
# park realtime query
if($sel(cfg_get.kazoo.presence_fast_pickup_query_park) == 1) {
$var(park_extension) = "^\*3";
if($sel(cfg_get.kazoo.presence_fast_pickup_star_5) == 1) {
Expand Down

0 comments on commit 5759eea

Please sign in to comment.