|
@@ -1021,78 +1021,287 @@ r,opt)
|
|
|
|
|
|
Example 1.34. Kamailio config script - sample dispatcher usage
|
|
|
...
|
|
|
-# $Id$
|
|
|
+#!KAMAILIO
|
|
|
+#
|
|
|
# sample config file for dispatcher module
|
|
|
+# - load balancing of VoIP calls with round robin
|
|
|
+# - no TPC listening
|
|
|
+# - don't dispatch REGISTER and presence requests
|
|
|
+#
|
|
|
+# Kamailio (OpenSER) SIP Server v3.2
|
|
|
+# - web: http://www.kamailio.org
|
|
|
+# - git: http://sip-router.org
|
|
|
+#
|
|
|
+# Direct your questions about this file to: [email protected]
|
|
|
+#
|
|
|
+# Refer to the Core CookBook at http://www.kamailio.org/dokuwiki/doku.php
|
|
|
+# for an explanation of possible statements, functions and parameters.
|
|
|
#
|
|
|
+# Several features can be enabled using '#!define WITH_FEATURE' directives:
|
|
|
+#
|
|
|
+# *** To run in debug mode:
|
|
|
+# - define WITH_DEBUG
|
|
|
+#
|
|
|
+
|
|
|
+
|
|
|
+####### Global Parameters #########
|
|
|
+
|
|
|
+#!ifdef WITH_DEBUG
|
|
|
+debug=4
|
|
|
+log_stderror=yes
|
|
|
+#!else
|
|
|
+debug=2
|
|
|
+log_stderror=no
|
|
|
+#!endif
|
|
|
|
|
|
-debug=9 # debug level (cmd line: -dddddddddd)
|
|
|
-fork=no
|
|
|
-log_stderror=yes # (cmd line: -E)
|
|
|
+memdbg=5
|
|
|
+memlog=5
|
|
|
+
|
|
|
+log_facility=LOG_LOCAL0
|
|
|
+
|
|
|
+fork=yes
|
|
|
+children=4
|
|
|
+
|
|
|
+/* comment the next line to enable TCP */
|
|
|
+disable_tcp=yes
|
|
|
+
|
|
|
+/* uncomment the next line to disable the auto discovery of local aliases
|
|
|
+ based on revers DNS on IPs (default on) */
|
|
|
+auto_aliases=no
|
|
|
+
|
|
|
+/* add local domain aliases */
|
|
|
+# alias="mysipserver.com"
|
|
|
|
|
|
-children=2
|
|
|
-check_via=no # (cmd. line: -v)
|
|
|
-dns=off # (cmd. line: -r)
|
|
|
-rev_dns=off # (cmd. line: -R)
|
|
|
port=5060
|
|
|
|
|
|
-# for more info: sip_router -h
|
|
|
+/* uncomment and configure the following line if you want Kamailio to
|
|
|
+ bind on a specific interface/port/proto (default bind on all available) */
|
|
|
+# listen=udp:127.0.0.1:5060
|
|
|
|
|
|
-# ------------------ module loading ----------------------------------
|
|
|
-mpath="/usr/local/lib/kamailio/modules/"
|
|
|
-loadmodule "maxfwd.so"
|
|
|
+sip_warning=no
|
|
|
+
|
|
|
+####### Modules Section ########
|
|
|
+
|
|
|
+#set module path
|
|
|
+mpath="/usr/local/lib/kamailio/modules_k/:/usr/local/lib/kamailio/modules/"
|
|
|
+
|
|
|
+loadmodule "db_mysql.so"
|
|
|
+loadmodule "mi_fifo.so"
|
|
|
+loadmodule "kex.so"
|
|
|
+loadmodule "tm.so"
|
|
|
+loadmodule "tmx.so"
|
|
|
loadmodule "sl.so"
|
|
|
+loadmodule "rr.so"
|
|
|
+loadmodule "pv.so"
|
|
|
+loadmodule "maxfwd.so"
|
|
|
+loadmodule "textops.so"
|
|
|
+loadmodule "siputils.so"
|
|
|
+loadmodule "xlog.so"
|
|
|
+loadmodule "sanity.so"
|
|
|
+loadmodule "ctl.so"
|
|
|
+loadmodule "mi_rpc.so"
|
|
|
+loadmodule "acc.so"
|
|
|
loadmodule "dispatcher.so"
|
|
|
-loadmodule "tm.so"
|
|
|
+
|
|
|
|
|
|
# ----------------- setting module-specific parameters ---------------
|
|
|
|
|
|
-# -- dispatcher params --
|
|
|
-modparam("dispatcher", "list_file", "/usr/local/etc/kamailio/dispatcher.list")
|
|
|
+
|
|
|
+# ----- mi_fifo params -----
|
|
|
+modparam("mi_fifo", "fifo_name", "/tmp/kamailio_fifo")
|
|
|
+
|
|
|
+
|
|
|
+# ----- rr params -----
|
|
|
+# add value to ;lr param to cope with most of the UAs
|
|
|
+modparam("rr", "enable_full_lr", 1)
|
|
|
+# do not append from tag to the RR (no need for this script)
|
|
|
+modparam("rr", "append_fromtag", 0)
|
|
|
+
|
|
|
+
|
|
|
+# ----- acc params -----
|
|
|
+modparam("acc", "log_flag", 1)
|
|
|
+modparam("acc", "failed_transaction_flag", 3)
|
|
|
+modparam("acc", "log_extra",
|
|
|
+ "src_user=$fU;src_domain=$fd;dst_ouser=$tU;dst_user=$rU;dst_domain=$rd;s
|
|
|
+rc_ip=$si")
|
|
|
+
|
|
|
+# ----- tm params -----
|
|
|
+modparam("tm", "fr_timer", 2000)
|
|
|
+modparam("tm", "fr_inv_timer", 40000)
|
|
|
+
|
|
|
+# ----- dispatcher params -----
|
|
|
+modparam("dispatcher", "db_url",
|
|
|
+ "mysql://openser:openserro@localhost/openser")
|
|
|
+modparam("dispatcher", "table_name", "dispatcher")
|
|
|
modparam("dispatcher", "flags", 2)
|
|
|
modparam("dispatcher", "dst_avp", "$avp(AVP_DST)")
|
|
|
modparam("dispatcher", "grp_avp", "$avp(AVP_GRP)")
|
|
|
modparam("dispatcher", "cnt_avp", "$avp(AVP_CNT)")
|
|
|
|
|
|
-# main request routing block
|
|
|
+####### Routing Logic ########
|
|
|
+
|
|
|
+
|
|
|
+# main request routing logic
|
|
|
+
|
|
|
route {
|
|
|
- if ( !mf_process_maxfwd_header("10") )
|
|
|
+
|
|
|
+ # per request initial checks
|
|
|
+ route(REQINIT);
|
|
|
+
|
|
|
+ # handle requests within SIP dialogs
|
|
|
+ route(WITHINDLG);
|
|
|
+
|
|
|
+ ### only initial requests (no To tag)
|
|
|
+
|
|
|
+ # CANCEL processing
|
|
|
+ if (is_method("CANCEL"))
|
|
|
{
|
|
|
- sl_send_reply("483","To Many Hops");
|
|
|
+ if (t_check_trans())
|
|
|
+ t_relay();
|
|
|
exit;
|
|
|
}
|
|
|
|
|
|
- # select from first dst group by round-robin
|
|
|
- if(!ds_select_dst("1", "4"))
|
|
|
+ t_check_trans();
|
|
|
+
|
|
|
+ # record routing for dialog forming requests (in case they are routed)
|
|
|
+ # - remove preloaded route headers
|
|
|
+ remove_hf("Route");
|
|
|
+ if (is_method("INVITE|SUBSCRIBE"))
|
|
|
+ record_route();
|
|
|
+
|
|
|
+ # account only INVITEs
|
|
|
+ if (is_method("INVITE"))
|
|
|
{
|
|
|
- sl_send_reply("500", "No destination available");
|
|
|
- exit;
|
|
|
+ setflag(1); # do accounting
|
|
|
}
|
|
|
|
|
|
- t_on_failure("RTF_DISPATCH");
|
|
|
- if(!t_relay())
|
|
|
+ # handle presence related requests
|
|
|
+ route(PRESENCE);
|
|
|
+
|
|
|
+ # handle registrations
|
|
|
+ route(REGISTRAR);
|
|
|
+
|
|
|
+ if ($rU==$null)
|
|
|
{
|
|
|
+ # request with no Username in RURI
|
|
|
+ sl_send_reply("484","Address Incomplete");
|
|
|
+ exit;
|
|
|
+ }
|
|
|
+
|
|
|
+ # dispatch destinations
|
|
|
+ route(DISPATCH);
|
|
|
+
|
|
|
+ route(RELAY);
|
|
|
+}
|
|
|
+
|
|
|
+
|
|
|
+route[RELAY] {
|
|
|
+ if (!t_relay()) {
|
|
|
sl_reply_error();
|
|
|
+ }
|
|
|
+ exit;
|
|
|
+}
|
|
|
+
|
|
|
+# Per SIP request initial checks
|
|
|
+route[REQINIT] {
|
|
|
+ if (!mf_process_maxfwd_header("10")) {
|
|
|
+ sl_send_reply("483","Too Many Hops");
|
|
|
+ exit;
|
|
|
+ }
|
|
|
+
|
|
|
+ if(!sanity_check("1511", "7"))
|
|
|
+ {
|
|
|
+ xlog("Malformed SIP message from $si:$sp\n");
|
|
|
+ exit;
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+# Handle requests within SIP dialogs
|
|
|
+route[WITHINDLG] {
|
|
|
+ if (has_totag()) {
|
|
|
+ # sequential request withing a dialog should
|
|
|
+ # take the path determined by record-routing
|
|
|
+ if (loose_route()) {
|
|
|
+ if (is_method("BYE")) {
|
|
|
+ setflag(1); # do accounting ...
|
|
|
+ setflag(3); # ... even if the transaction fails
|
|
|
+ }
|
|
|
+ route(RELAY);
|
|
|
+ } else {
|
|
|
+ if (is_method("SUBSCRIBE") && uri == myself) {
|
|
|
+ # in-dialog subscribe requests
|
|
|
+ route(PRESENCE);
|
|
|
+ exit;
|
|
|
+ }
|
|
|
+ if ( is_method("ACK") ) {
|
|
|
+ if ( t_check_trans() ) {
|
|
|
+ # non loose-route, but stateful ACK;
|
|
|
+ # must be ACK after a 487 or e.g. 404 fr
|
|
|
+om upstream server
|
|
|
+ t_relay();
|
|
|
+ exit;
|
|
|
+ } else {
|
|
|
+ # ACK without matching transaction ... i
|
|
|
+gnore and discard.
|
|
|
+ exit;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ sl_send_reply("404","Not here");
|
|
|
+ }
|
|
|
+ exit;
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+# Handle SIP registrations
|
|
|
+route[REGISTRAR] {
|
|
|
+ if(!is_method("REGISTER"))
|
|
|
+ return;
|
|
|
+ sl_send_reply("404", "No registrar");
|
|
|
+ exit;
|
|
|
+}
|
|
|
+
|
|
|
+# Presence server route
|
|
|
+route[PRESENCE] {
|
|
|
+ if(!is_method("PUBLISH|SUBSCRIBE"))
|
|
|
+ return;
|
|
|
+
|
|
|
+ sl_send_reply("404", "Not here");
|
|
|
+ exit;
|
|
|
+}
|
|
|
+
|
|
|
+# Dispatch requests
|
|
|
+route[DISPATCH] {
|
|
|
+ # round robin dispatching on gateways group '1'
|
|
|
+ if(!ds_select_dst("1", "4"))
|
|
|
+ {
|
|
|
+ send_reply("404", "No destination");
|
|
|
exit;
|
|
|
}
|
|
|
+ xlog("L_DBG", "--- SCRIPT: going to <$ru> via <$du>\n");
|
|
|
+ t_on_failure("RTF_DISPATCH");
|
|
|
+ return;
|
|
|
}
|
|
|
|
|
|
-# dispatcher failure routing block
|
|
|
+# Sample failure route
|
|
|
failure_route[RTF_DISPATCH] {
|
|
|
if (t_is_canceled()) {
|
|
|
exit;
|
|
|
}
|
|
|
- # select next destination only for local timeout
|
|
|
- if (t_branch_timeout() && !t_branch_replied())
|
|
|
+ # next DST - only for 500 or local timeout
|
|
|
+ if (t_check_status("500")
|
|
|
+ or (t_branch_timeout() and !t_branch_replied()))
|
|
|
{
|
|
|
if(ds_next_dst())
|
|
|
{
|
|
|
t_on_failure("RTF_DISPATCH");
|
|
|
- t_relay();
|
|
|
+ route(RELAY);
|
|
|
exit;
|
|
|
}
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+
|
|
|
+
|
|
|
...
|
|
|
|
|
|
8. Event routes
|
|
@@ -1134,8 +1343,13 @@ Chapter 2. Frequently Asked Questions
|
|
|
|
|
|
Does dispatcher provide a fair distribution?
|
|
|
|
|
|
- There is no guarantee of that. You should do some measurements to
|
|
|
- decide what distribution algorithm fits better in your environment.
|
|
|
+ The algoritms doing hashing over parts of SIP message don't guarantee a
|
|
|
+ fair distribution. You should do some measurements to decide what
|
|
|
+ hashing algorithm fits better in your environment.
|
|
|
+
|
|
|
+ Other distribution algorithms such as round robin or call load
|
|
|
+ dispatching do a fair distribution in terms of delivered calls to
|
|
|
+ gateways.
|
|
|
|
|
|
2.2.
|
|
|
|