00001
00002 """
00003 * $Id$
00004 *
00005 * Copyright (C) 2006 iptelorg GmbH
00006 *
00007 * This file is part of ser, a free SIP server.
00008 *
00009 * ser is free software; you can redistribute it and/or modify
00010 * it under the terms of the GNU General Public License as published by
00011 * the Free Software Foundation; either version 2 of the License, or
00012 * (at your option) any later version
00013 *
00014 * For a license to use the ser software under conditions
00015 * other than those described here, or to purchase support for this
00016 * software, please contact iptel.org by e-mail at the following addresses:
00017 * info@iptel.org
00018 *
00019 * ser is distributed in the hope that it will be useful,
00020 * but WITHOUT ANY WARRANTY; without even the implied warranty of
00021 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
00022 * GNU General Public License for more details.
00023 *
00024 * You should have received a copy of the GNU General Public License
00025 * along with this program; if not, write to the Free Software
00026 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
00027 *
00028 """
00029 import sys,re
00030
00031 max_depth = 10
00032 debug = 0
00033
00034 re_main_route = re.compile("^([a-z]+_)*route[\s\t]*(?![\(\)])[\s\t]*\{?", re.I)
00035 re_def_route = re.compile("^([a-z]+_)*route(\[\"?([A-Za-z0-9-_:]+)\"?\])+[\s\t]*\{?", re.I)
00036 re_call_route = re.compile("^(.*\([\s\t!]*)?route\(\"?([A-Za-z0-9-_]+)\"?\)", re.I)
00037 routes = {}
00038 f_routes = {}
00039 b_routes = {}
00040 r_routes = {}
00041 s_routes = {}
00042 e_routes = {}
00043
00044
00045 def log(_s):
00046 if debug:
00047 print _s
00048
00049 def print_route_level(_l, _n):
00050 log("prl: %i, %s" % (_l, _n))
00051 if _l > max_depth:
00052 return
00053 spacer = ""
00054 route = ""
00055 for i in range(_l):
00056 spacer += "| "
00057 if i < _l - 1:
00058 route += "| "
00059 else:
00060 route += "\- " + str(_n)
00061 if len(spacer) > 0:
00062 print spacer
00063 if len(route) > 0:
00064 print route
00065
00066 def traverse_routes(_level, _name):
00067 log("tr: %i, %s" % (_level, _name))
00068 if _level > max_depth:
00069 print "warning: max_depth reached"
00070 return
00071 print_route_level(_level, _name)
00072 if routes.has_key(_name):
00073 for r in routes[_name]:
00074 traverse_routes(_level + 1, r)
00075
00076
00077 if len(sys.argv) < 2:
00078 raise "usage: %s configuration-file [max_depth]" % sys.argv[0]
00079 if len(sys.argv) == 3:
00080 max_depth = int(sys.argv[2])
00081 cfg = file(sys.argv[1], "r")
00082 if cfg == None:
00083 raise "Missing config file"
00084 line = cfg.readline()
00085 rt = routes
00086 while line:
00087 line = line.strip()
00088 if not line.startswith("#"):
00089 log(line)
00090 main_match = re_main_route.search(line)
00091 def_match = re_def_route.search(line)
00092 call_match = re_call_route.search(line)
00093 if not call_match == None:
00094 log("CALL: " + line)
00095 name = call_match.group(2)
00096 log(rname +":"+name)
00097 rt[rname].append(name)
00098 elif not def_match == None:
00099 log("DEF: " + line)
00100 rtype = def_match.group(1)
00101 rname = def_match.group(3)
00102 if rtype == "failure_":
00103 rt = f_routes
00104 if rname == None:
00105 rname = "failure"
00106 elif rtype == "onreply_":
00107 rt = r_routes
00108 if rname == None:
00109 rname = "onreply"
00110 elif rtype == "onsend_":
00111 rt = s_routes
00112 if rname == None:
00113 rname = "onsend"
00114 elif rtype == "branch_":
00115 rt = b_routes
00116 if rname == None:
00117 rname = "branch"
00118 elif rtype == "event_":
00119 rt = e_routes
00120 if rname == None:
00121 rname = "event"
00122 else:
00123 rt = routes
00124 log(rname)
00125 rt[rname] = []
00126 elif not main_match == None:
00127 log("MAIN: " + line)
00128 rtype = main_match.group(1)
00129 if rtype == "failure_":
00130 rt = f_routes
00131 rname = "failure"
00132 elif rtype == "onreply_":
00133 rt = r_routes
00134 rname = "onreply"
00135 elif rtype == "onsend_":
00136 rt = s_routes
00137 rname = "onsend"
00138 elif rtype == "branch_":
00139 rt = b_routes
00140 rname = "branch"
00141 elif rtype == "event_":
00142 rt = e_routes
00143 rname = "event"
00144 else:
00145 rt = routes
00146 rname = "Main"
00147 log(rname)
00148 rt[rname] = []
00149 line = cfg.readline()
00150
00151 log("routes: %s" % (routes))
00152 log("branch_routes: %s" % (b_routes))
00153 log("failure_routes: %s" % (f_routes))
00154 log("onreply_routes: %s" % (r_routes))
00155 log("onsend_routes: %s" % (s_routes))
00156 log("event_routes: %s" % (e_routes))
00157
00158 for name in routes.keys():
00159 for val in routes[name]:
00160 if not routes.has_key(val):
00161 print "Missing Route %s!!!" % val
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172 print "\nMain"
00173 traverse_routes(0, "Main")
00174
00175 if len(b_routes) > 0:
00176 print "\nBranch routes\n-------------"
00177 for br in b_routes.keys():
00178 print "\n%s" % (br)
00179 for r in b_routes[br]:
00180 traverse_routes(1, r)
00181
00182 if len(s_routes) > 0:
00183 print "\nSend routes\n-----------"
00184 for sr in s_routes.keys():
00185 print "\n%s" % (sr)
00186 for r in s_routes[sr]:
00187 traverse_routes(1, r)
00188
00189 if len(f_routes) > 0:
00190 print "\nFailure routes\n--------------"
00191 for fr in f_routes.keys():
00192 print "\n%s" % (fr)
00193 for r in f_routes[fr]:
00194 traverse_routes(1, r)
00195
00196 if len(r_routes) > 0:
00197 print "\nOnreply routes\n--------------"
00198 for onr in r_routes.keys():
00199 print "\n%s" % (onr)
00200 for r in r_routes[onr]:
00201 traverse_routes(1, r)
00202
00203 if len(e_routes) > 0:
00204 print "\nEvent routes\n--------------"
00205 for onr in e_routes.keys():
00206 print "\n%s" % (onr)
00207 for r in e_routes[onr]:
00208 traverse_routes(1, r)
00209
00210 print