| 24 | | |
|---|
| 25 | | $amp_conf_defaults = array( |
|---|
| 26 | | 'AMPDBENGINE' => array('std' , 'mysql'), |
|---|
| 27 | | 'AMPDBNAME' => array('std' , 'asterisk'), |
|---|
| 28 | | 'AMPENGINE' => array('std' , 'asterisk'), |
|---|
| 29 | | 'ASTMANAGERPORT' => array('std' , '5038'), |
|---|
| 30 | | 'ASTMANAGERHOST' => array('std' , 'localhost'), |
|---|
| 31 | | 'AMPDBHOST' => array('std' , 'localhost'), |
|---|
| 32 | | 'AMPDBUSER' => array('std' , 'asteriskuser'), |
|---|
| 33 | | 'AMPDBPASS' => array('std' , 'amp109'), |
|---|
| 34 | | 'AMPMGRUSER' => array('std' , 'admin'), |
|---|
| 35 | | 'AMPMGRPASS' => array('std' , 'amp111'), |
|---|
| 36 | | 'FOPPASSWORD' => array('std' , 'passw0rd'), |
|---|
| 37 | | 'FOPSORT' => array('std' , 'extension'), |
|---|
| 38 | | 'AMPSYSLOGLEVEL '=> array('std' , 'LOG_ERR'), |
|---|
| 39 | | 'ARI_ADMIN_PASSWORD' => array('std' , 'ari_password'), |
|---|
| 40 | | |
|---|
| 41 | | 'ASTETCDIR' => array('dir' , '/etc/asterisk'), |
|---|
| 42 | | 'ASTMODDIR' => array('dir' , '/usr/lib/asterisk/modules'), |
|---|
| 43 | | 'ASTVARLIBDIR' => array('dir' , '/var/lib/asterisk'), |
|---|
| 44 | | 'ASTAGIDIR' => array('dir' , '/var/lib/asterisk/agi-bin'), |
|---|
| 45 | | 'ASTSPOOLDIR' => array('dir' , '/var/spool/asterisk/'), |
|---|
| 46 | | 'ASTRUNDIR' => array('dir' , '/var/run/asterisk'), |
|---|
| 47 | | 'ASTLOGDIR' => array('dir' , '/var/log/asterisk'), |
|---|
| 48 | | 'AMPBIN' => array('dir' , '/var/lib/asterisk/bin'), |
|---|
| 49 | | 'AMPSBIN' => array('dir' , '/usr/sbin'), |
|---|
| 50 | | 'AMPWEBROOT' => array('dir' , '/var/www/html'), |
|---|
| 51 | | 'FOPWEBROOT' => array('dir' , '/var/www/html/panel'), |
|---|
| 52 | | 'MOHDIR' => array('dir' , '/mohmp3'), |
|---|
| 53 | | 'FPBXDBUGFILE' => array('dir' , '/tmp/freepbx_debug.log'), |
|---|
| 54 | | |
|---|
| 55 | | 'USECATEGORIES' => array('bool' , true), |
|---|
| 56 | | 'ENABLECW' => array('bool' , true), |
|---|
| 57 | | 'CWINUSEBUSY' => array('bool' , true), |
|---|
| 58 | | 'FOPRUN' => array('bool' , true), |
|---|
| 59 | | 'AMPBADNUMBER' => array('bool' , true), |
|---|
| 60 | | 'DEVEL' => array('bool' , false), |
|---|
| 61 | | 'DEVELRELOAD' => array('bool' , false), |
|---|
| 62 | | 'CUSTOMASERROR' => array('bool' , true), |
|---|
| 63 | | 'DYNAMICHINTS' => array('bool' , false), |
|---|
| 64 | | 'BADDESTABORT' => array('bool' , false), |
|---|
| 65 | | 'SERVERINTITLE' => array('bool' , false), |
|---|
| 66 | | 'XTNCONFLICTABORT' => array('bool' , false), |
|---|
| 67 | | 'USEDEVSTATE' => array('bool' , false), |
|---|
| 68 | | 'MODULEADMINWGET'=> array('bool' , false), |
|---|
| 69 | | 'AMPDISABLELOG' => array('bool' , true), |
|---|
| 70 | | 'AMPENABLEDEVELDEBUG'=> array('bool' , false), |
|---|
| 71 | | 'AMPMPG123' => array('bool' , true), |
|---|
| 72 | | 'FOPDISABLE' => array('bool' , false), |
|---|
| 73 | | 'ZAP2DAHDICOMPAT' => array('bool' , false), |
|---|
| 74 | | 'USEQUEUESTATE' => array('bool' , false), |
|---|
| 75 | | 'CHECKREFERER' => array('bool' , true), |
|---|
| 76 | | 'USEDIALONE' => array('bool' , false), |
|---|
| 77 | | 'RELOADCONFIRM' => array('bool' , true), |
|---|
| 78 | | 'DISABLECUSTOMCONTEXTS' => array('bool' , false), |
|---|
| 79 | | |
|---|
| 80 | | ); |
|---|
| 81 | | |
|---|
| 82 | | function parse_amportal_conf($filename) { |
|---|
| 83 | | global $amp_conf_defaults; |
|---|
| 84 | | |
|---|
| 85 | | /* defaults |
|---|
| 86 | | * This defines defaults and formating to assure consistency across the system so that |
|---|
| 87 | | * components don't have to keep being 'gun shy' about these variables. |
|---|
| 88 | | * |
|---|
| 89 | | */ |
|---|
| 90 | | $file = file($filename); |
|---|
| 91 | | if (is_array($file)) { |
|---|
| 92 | | foreach ($file as $line) { |
|---|
| 93 | | if (preg_match("/^\s*([a-zA-Z0-9_]+)=([a-zA-Z0-9 .&-@=_!<>\"\']+)\s*$/",$line,$matches)) { |
|---|
| 94 | | $conf[ $matches[1] ] = $matches[2]; |
|---|
| 95 | | } |
|---|
| 96 | | } |
|---|
| 97 | | } else { |
|---|
| 98 | | die_freepbx("<h1>".sprintf(_("Missing or unreadable config file (%s)...cannot continue"), $filename)."</h1>"); |
|---|
| 99 | | } |
|---|
| 100 | | |
|---|
| 101 | | // set defaults |
|---|
| 102 | | foreach ($amp_conf_defaults as $key=>$arr) { |
|---|
| 103 | | |
|---|
| 104 | | switch ($arr[0]) { |
|---|
| 105 | | // for type dir, make sure there is no trailing '/' to keep consistent everwhere |
|---|
| 106 | | // |
|---|
| 107 | | case 'dir': |
|---|
| 108 | | if (!isset($conf[$key]) || trim($conf[$key]) == '') { |
|---|
| 109 | | $conf[$key] = $arr[1]; |
|---|
| 110 | | } else { |
|---|
| 111 | | $conf[$key] = rtrim($conf[$key],'/'); |
|---|
| 112 | | } |
|---|
| 113 | | break; |
|---|
| 114 | | // booleans: |
|---|
| 115 | | // "yes", "true", "on", true, 1 (case-insensitive) will be treated as true, everything else is false |
|---|
| 116 | | // |
|---|
| 117 | | case 'bool': |
|---|
| 118 | | if (!isset($conf[$key])) { |
|---|
| 119 | | $conf[$key] = $arr[1]; |
|---|
| 120 | | } else { |
|---|
| 121 | | $conf[$key] = ($conf[$key] === true || strtolower($conf[$key]) == 'true' || $conf[$key] === 1 || $conf[$key] == '1' |
|---|
| 122 | | || strtolower($conf[$key]) == 'yes' || strtolower($conf[$key]) == 'on'); |
|---|
| 123 | | } |
|---|
| 124 | | break; |
|---|
| 125 | | default: |
|---|
| 126 | | if (!isset($conf[$key])) { |
|---|
| 127 | | $conf[$key] = $arr[1]; |
|---|
| 128 | | } else { |
|---|
| 129 | | $conf[$key] = trim($conf[$key]); |
|---|
| 130 | | } |
|---|
| 131 | | } |
|---|
| 132 | | } |
|---|
| 133 | | return $conf; |
|---|
| 134 | | } |
|---|
| 135 | | |
|---|
| 136 | | function parse_asterisk_conf($filename) { |
|---|
| 137 | | //TODO: Should the correction of $amp_conf be passed by refernce and optional? |
|---|
| 138 | | // |
|---|
| 139 | | global $amp_conf; |
|---|
| 140 | | $conf = array(); |
|---|
| 141 | | |
|---|
| 142 | | $convert = array( |
|---|
| 143 | | 'astetcdir' => 'ASTETCDIR', |
|---|
| 144 | | 'astmoddir' => 'ASTMODDIR', |
|---|
| 145 | | 'astvarlibdir' => 'ASTVARLIBDIR', |
|---|
| 146 | | 'astagidir' => 'ASTAGIDIR', |
|---|
| 147 | | 'astspooldir' => 'ASTSPOOLDIR', |
|---|
| 148 | | 'astrundir' => 'ASTRUNDIR', |
|---|
| 149 | | 'astlogdir' => 'ASTLOGDIR' |
|---|
| 150 | | ); |
|---|
| 151 | | |
|---|
| 152 | | $file = file($filename); |
|---|
| 153 | | foreach ($file as $line) { |
|---|
| 154 | | if (preg_match("/^\s*([a-zA-Z0-9]+)\s* => \s*(.*)\s*([;#].*)?/",$line,$matches)) { |
|---|
| 155 | | $conf[ $matches[1] ] = rtrim($matches[2],"/ \t"); |
|---|
| 156 | | } |
|---|
| 157 | | } |
|---|
| 158 | | |
|---|
| 159 | | // Now that we parsed asterisk.conf, we need to make sure $amp_conf is consistent |
|---|
| 160 | | // so just set it to what we found, since this is what asterisk will use anyhow. |
|---|
| 161 | | // |
|---|
| 162 | | foreach ($convert as $ast_conf_key => $amp_conf_key) { |
|---|
| 163 | | if (isset($conf[$ast_conf_key])) { |
|---|
| 164 | | $amp_conf[$amp_conf_key] = $conf[$ast_conf_key]; |
|---|
| 165 | | } |
|---|
| 166 | | } |
|---|
| 167 | | return $conf; |
|---|
| 168 | | } |
|---|
| 169 | | |
|---|
| 170 | | /** check if a specific extension is being used, or get a list of all extensions that are being used |
|---|
| 171 | | * @param mixed an array of extension numbers to check against, or if boolean true then return list of all extensions |
|---|
| 172 | | * @param array a hash of module names to search for callbacks, otherwise global $active_modules is used |
|---|
| 173 | | * @return array returns an empty array if exten not in use, or any array with usage info, or of all usage |
|---|
| 174 | | * if exten is boolean true |
|---|
| 175 | | * @description Upon passing in an array of extension numbers, this api will query all modules to determine if any |
|---|
| 176 | | * are using those extension numbers. If so, it will return an array with the usage information |
|---|
| 177 | | * as described below, otherwise an empty array. If passed boolean true, it will return an array |
|---|
| 178 | | * of the same format with all extensions on the system that are being used. |
|---|
| 179 | | * |
|---|
| 180 | | * $exten_usage[$module][$exten]['description'] // description of the extension |
|---|
| 181 | | * ['edit_url'] // a url that could be invoked to edit extension |
|---|
| 182 | | * ['status'] // Status: INUSE, RESERVED, RESTRICTED |
|---|
| 183 | | */ |
|---|
| 184 | | function framework_check_extension_usage($exten=true, $module_hash=false) { |
|---|
| 185 | | global $active_modules; |
|---|
| 186 | | $exten_usage = array(); |
|---|
| 187 | | |
|---|
| 188 | | if (!is_array($module_hash)) { |
|---|
| 189 | | $module_hash = $active_modules; |
|---|
| 190 | | } |
|---|
| 191 | | |
|---|
| 192 | | if (!is_array($exten) && $exten !== true) { |
|---|
| 193 | | $exten = array($exten); |
|---|
| 194 | | } |
|---|
| 195 | | |
|---|
| 196 | | foreach(array_keys($module_hash) as $mod) { |
|---|
| 197 | | $function = $mod."_check_extensions"; |
|---|
| 198 | | if (function_exists($function)) { |
|---|
| 199 | | $prev_domain = textdomain(NULL); |
|---|
| 200 | | if (isset($_COOKIE['lang']) && is_dir("./modules/$mod/i18n/".$_COOKIE['lang'])) { |
|---|
| 201 | | bindtextdomain($mod,"./modules/$mod/i18n"); |
|---|
| 202 | | bind_textdomain_codeset($mod, 'utf8'); |
|---|
| 203 | | textdomain($mod); |
|---|
| 204 | | $module_usage = $function($exten); |
|---|
| 205 | | } else { |
|---|
| 206 | | textdomain('amp'); |
|---|
| 207 | | $module_usage = $function($exten); |
|---|
| 208 | | } |
|---|
| 209 | | if (!empty($module_usage)) { |
|---|
| 210 | | $exten_usage[$mod] = $module_usage; |
|---|
| 211 | | } |
|---|
| 212 | | textdomain($prev_domain); |
|---|
| 213 | | } |
|---|
| 214 | | } |
|---|
| 215 | | if ($exten === true) { |
|---|
| 216 | | return $exten_usage; |
|---|
| 217 | | } else { |
|---|
| 218 | | $exten_matches = array(); |
|---|
| 219 | | foreach (array_keys($exten_usage) as $mod) { |
|---|
| 220 | | foreach ($exten as $test_exten) { |
|---|
| 221 | | if (isset($exten_usage[$mod][$test_exten])) { |
|---|
| 222 | | $exten_matches[$mod][$test_exten] = $exten_usage[$mod][$test_exten]; |
|---|
| 223 | | } |
|---|
| 224 | | } |
|---|
| 225 | | } |
|---|
| 226 | | } |
|---|
| 227 | | return $exten_matches; |
|---|
| 228 | | } |
|---|
| 229 | | |
|---|
| 230 | | /** check if a specific destination is being used, or get a list of all destinations that are being used |
|---|
| 231 | | * @param mixed an array of destinations to check against, or if boolean true then return list of all destinations in use |
|---|
| 232 | | * @param array a hash of module names to search for callbacks, otherwise global $active_modules is used |
|---|
| 233 | | * @return array returns an empty array if destination not in use, or any array with usage info, or of all usage |
|---|
| 234 | | * if dest is boolean true |
|---|
| 235 | | * @description Upon passing in an array of destinations, this api will query all modules to determine if any |
|---|
| 236 | | * are using that destination. If so, it will return an array with the usage information |
|---|
| 237 | | * as described below, otherwise an empty array. If passed boolean true, it will return an array |
|---|
| 238 | | * of the same format with all destinations on the system that are being used. |
|---|
| 239 | | * |
|---|
| 240 | | * $dest_usage[$module][]['dest'] // The destination being used |
|---|
| 241 | | * ['description'] // Description of who is using it |
|---|
| 242 | | * ['edit_url'] // a url that could be invoked to edit the using entity |
|---|
| 243 | | * |
|---|
| 244 | | */ |
|---|
| 245 | | function framework_check_destination_usage($dest=true, $module_hash=false) { |
|---|
| 246 | | global $active_modules; |
|---|
| 247 | | |
|---|
| 248 | | $dest_usage = array(); |
|---|
| 249 | | $dest_matches = array(); |
|---|
| 250 | | |
|---|
| 251 | | if (!is_array($module_hash)) { |
|---|
| 252 | | $module_hash = $active_modules; |
|---|
| 253 | | } |
|---|
| 254 | | |
|---|
| 255 | | if (!is_array($dest) && $dest !== true) { |
|---|
| 256 | | $dest = array($dest); |
|---|
| 257 | | } |
|---|
| 258 | | |
|---|
| 259 | | foreach(array_keys($module_hash) as $mod) { |
|---|
| 260 | | $function = $mod."_check_destinations"; |
|---|
| 261 | | if (function_exists($function)) { |
|---|
| 262 | | $prev_domain = textdomain(NULL); |
|---|
| 263 | | if (isset($_COOKIE['lang']) && is_dir("./modules/$mod/i18n/".$_COOKIE['lang'])) { |
|---|
| 264 | | bindtextdomain($mod,"./modules/$mod/i18n"); |
|---|
| 265 | | bind_textdomain_codeset($mod, 'utf8'); |
|---|
| 266 | | textdomain($mod); |
|---|
| 267 | | $module_usage = $function($dest); |
|---|
| 268 | | } else { |
|---|
| 269 | | textdomain('amp'); |
|---|
| 270 | | $module_usage = $function($dest); |
|---|
| 271 | | } |
|---|
| 272 | | if (!empty($module_usage)) { |
|---|
| 273 | | $dest_usage[$mod] = $module_usage; |
|---|
| 274 | | } |
|---|
| 275 | | textdomain($prev_domain); |
|---|
| 276 | | } |
|---|
| 277 | | } |
|---|
| 278 | | if ($dest === true) { |
|---|
| 279 | | return $dest_usage; |
|---|
| 280 | | } else { |
|---|
| 281 | | /* |
|---|
| 282 | | $destlist[] = array( |
|---|
| 283 | | 'dest' => $thisdest, |
|---|
| 284 | | 'description' => 'Annoucement: '.$result['description'], |
|---|
| 285 | | 'edit_url' => 'config.php?display=announcement&type='.$type.'&extdisplay='.urlencode($thisid), |
|---|
| 286 | | ); |
|---|
| 287 | | */ |
|---|
| 288 | | foreach (array_keys($dest_usage) as $mod) { |
|---|
| 289 | | foreach ($dest as $test_dest) { |
|---|
| 290 | | foreach ($dest_usage[$mod] as $dest_item) { |
|---|
| 291 | | if ($dest_item['dest'] == $test_dest) { |
|---|
| 292 | | $dest_matches[$mod][] = $dest_item; |
|---|
| 293 | | } |
|---|
| 294 | | } |
|---|
| 295 | | } |
|---|
| 296 | | } |
|---|
| 297 | | } |
|---|
| 298 | | return $dest_matches; |
|---|
| 299 | | } |
|---|
| 300 | | |
|---|
| 301 | | /** provide optional alert() box and formatted url info for extension conflicts |
|---|
| 302 | | * @param array an array of extensions that are in conflict obtained from framework_check_extension_usage |
|---|
| 303 | | * @param boolean default false. True if url and descriptions should be split, false to combine (see return) |
|---|
| 304 | | * @param boolean default true. True to echo an alert() box, false to bypass the alert box |
|---|
| 305 | | * @return array returns an array of formatted URLs with descriptions. If $split is true, retuns an array |
|---|
| 306 | | * of the URLs with each element an array in the format of array('label' => 'description, 'url' => 'a url') |
|---|
| 307 | | * @description This is used upon detecting conflicting extension numbers to provide an optional alert box of the issue |
|---|
| 308 | | * by a module which should abort the attempt to create the extension. It also returns an array of |
|---|
| 309 | | * URLs that can be displayed by the module to show the conflicting extension(s) and links to edit |
|---|
| 310 | | * them or further interogate. The resulting URLs are returned in an array either formatted for immediate |
|---|
| 311 | | * display or split into a description and the raw URL to provide more fine grained control (or use with guielements). |
|---|
| 312 | | */ |
|---|
| 313 | | function framework_display_extension_usage_alert($usage_arr=array(),$split=false,$alert=true) { |
|---|
| 314 | | $url = array(); |
|---|
| 315 | | if (!empty($usage_arr)) { |
|---|
| 316 | | $conflicts=0; |
|---|
| 317 | | foreach($usage_arr as $rawmodule => $properties) { |
|---|
| 318 | | foreach($properties as $exten => $details) { |
|---|
| 319 | | $conflicts++; |
|---|
| 320 | | if ($conflicts == 1) { |
|---|
| 321 | | switch ($details['status']) { |
|---|
| 322 | | case 'INUSE': |
|---|
| 323 | | $str = "Extension $exten not available, it is currently used by ".htmlspecialchars($details['description'])."."; |
|---|
| 324 | | if ($split) { |
|---|
| 325 | | $url[] = array('label' => "Edit: ".htmlspecialchars($details['description']), |
|---|
| 326 | | 'url' => $details['edit_url'], |
|---|
| 327 | | ); |
|---|
| 328 | | } else { |
|---|
| 329 | | $url[] = "<a href='".$details['edit_url']."'>Edit: ".htmlspecialchars($details['description'])."</a>"; |
|---|
| 330 | | } |
|---|
| 331 | | break; |
|---|
| 332 | | default: |
|---|
| 333 | | $str = "This extension is not available: ".htmlspecialchars($details['description'])."."; |
|---|
| 334 | | } |
|---|
| 335 | | } else { |
|---|
| 336 | | if ($split) { |
|---|
| 337 | | $url[] = array('label' => "Edit: ".htmlspecialchars($details['description']), |
|---|
| 338 | | 'url' => $details['edit_url'], |
|---|
| 339 | | ); |
|---|
| 340 | | } else { |
|---|
| 341 | | $url[] = "<a href='".$details['edit_url']."'>Edit: ".htmlspecialchars($details['description'])."</a>"; |
|---|
| 342 | | } |
|---|
| 343 | | } |
|---|
| 344 | | } |
|---|
| 345 | | } |
|---|
| 346 | | if ($conflicts > 1) { |
|---|
| 347 | | $str .= sprintf(" There are %s additonal conflicts not listed",$conflicts-1); |
|---|
| 348 | | } |
|---|
| 349 | | } |
|---|
| 350 | | if ($alert) { |
|---|
| 351 | | echo "<script>javascript:alert('$str')</script>"; |
|---|
| 352 | | } |
|---|
| 353 | | return($url); |
|---|
| 354 | | } |
|---|
| 355 | | |
|---|
| 356 | | /** check if a specific destination is being used, or get a list of all destinations that are being used |
|---|
| 357 | | * @param mixed an array of destinations to check against |
|---|
| 358 | | * @param array a hash of module names to search for callbacks, otherwise global $active_modules is used |
|---|
| 359 | | * @return array array with a message and tooltip to display usage of this destination |
|---|
| 360 | | * @description This is called to generate a label and tooltip which summarized the usage of this |
|---|
| 361 | | * destination and a tooltip listing all the places that use it |
|---|
| 362 | | * |
|---|
| 363 | | */ |
|---|
| 364 | | function framework_display_destination_usage($dest, $module_hash=false) { |
|---|
| 365 | | |
|---|
| 366 | | if (!is_array($dest)) { |
|---|
| 367 | | $dest = array($dest); |
|---|
| 368 | | } |
|---|
| 369 | | $usage_list = framework_check_destination_usage($dest, $module_hash); |
|---|
| 370 | | if (!empty($usage_list)) { |
|---|
| 371 | | $usage_count = 0; |
|---|
| 372 | | $str = null; |
|---|
| 373 | | foreach ($usage_list as $mod_list) { |
|---|
| 374 | | foreach ($mod_list as $details) { |
|---|
| 375 | | $usage_count++; |
|---|
| 376 | | $str .= $details['description']."<br />"; |
|---|
| 377 | | } |
|---|
| 378 | | } |
|---|
| 379 | | $object = $usage_count > 1 ? _("Objects"):_("Object"); |
|---|
| 380 | | return array('text' => ' '.sprintf(dgettext('amp',"Used as Destination by %s %s"),$usage_count, dgettext('amp',$object)), |
|---|
| 381 | | 'tooltip' => $str, |
|---|
| 382 | | ); |
|---|
| 383 | | } else { |
|---|
| 384 | | return array(); |
|---|
| 385 | | } |
|---|
| 386 | | } |
|---|
| 387 | | |
|---|
| 388 | | /** determines which module a list of destinations belongs to, and if the destination object exists |
|---|
| 389 | | * @param mixed an array of destinations to check against |
|---|
| 390 | | * @param array a hash of module names to search for callbacks, otherwise global $active_modules is used |
|---|
| 391 | | * @return array an array structure with informaiton about the destinations (see code) |
|---|
| 392 | | * @description Mainly used by framework_list_problem_destinations. This function will find the module |
|---|
| 393 | | * that a destination belongs to and determine if the object still exits. This allow it to |
|---|
| 394 | | * either obtain the identify, identify it as an object that has been deleted, or identify |
|---|
| 395 | | * it as an unknown destination, usually a custom destination. |
|---|
| 396 | | * |
|---|
| 397 | | */ |
|---|
| 398 | | function framework_identify_destinations($dest, $module_hash=false) { |
|---|
| 399 | | global $active_modules; |
|---|
| 400 | | static $dest_cache = array(); |
|---|
| 401 | | |
|---|
| 402 | | $dest_results = array(); |
|---|
| 403 | | |
|---|
| 404 | | $dest_usage = array(); |
|---|
| 405 | | $dest_matches = array(); |
|---|
| 406 | | |
|---|
| 407 | | if (!is_array($module_hash)) { |
|---|
| 408 | | $module_hash = $active_modules; |
|---|
| 409 | | } |
|---|
| 410 | | |
|---|
| 411 | | if (!is_array($dest)) { |
|---|
| 412 | | $dest = array($dest); |
|---|
| 413 | | } |
|---|
| 414 | | |
|---|
| 415 | | foreach ($dest as $target) { |
|---|
| 416 | | if (isset($dest_cache[$target])) { |
|---|
| 417 | | $dest_results[$target] = $dest_cache[$target]; |
|---|
| 418 | | } else { |
|---|
| 419 | | $found_owner = false; |
|---|
| 420 | | foreach(array_keys($module_hash) as $mod) { |
|---|
| 421 | | $function = $mod."_getdestinfo"; |
|---|
| 422 | | if (function_exists($function)) { |
|---|
| 423 | | $prev_domain = textdomain(NULL); |
|---|
| 424 | | if (isset($_COOKIE['lang']) && is_dir("./modules/$mod/i18n/".$_COOKIE['lang'])) { |
|---|
| 425 | | bindtextdomain($mod,"./modules/$mod/i18n"); |
|---|
| 426 | | bind_textdomain_codeset($mod, 'utf8'); |
|---|
| 427 | | textdomain($mod); |
|---|
| 428 | | $check_module = $function($target); |
|---|
| 429 | | } else { |
|---|
| 430 | | textdomain('amp'); |
|---|
| 431 | | $check_module = $function($target); |
|---|
| 432 | | } |
|---|
| 433 | | textdomain($prev_domain); |
|---|
| 434 | | if ($check_module !== false) { |
|---|
| 435 | | $found_owner = true; |
|---|
| 436 | | $dest_cache[$target] = array($mod => $check_module); |
|---|
| 437 | | $dest_results[$target] = $dest_cache[$target]; |
|---|
| 438 | | break; |
|---|
| 439 | | } |
|---|
| 440 | | } |
|---|
| 441 | | } |
|---|
| 442 | | if (! $found_owner) { |
|---|
| 443 | | //echo "Not Found: $target\n"; |
|---|
| 444 | | $dest_cache[$target] = false; |
|---|
| 445 | | $dest_results[$target] = $dest_cache[$target]; |
|---|
| 446 | | } |
|---|
| 447 | | } |
|---|
| 448 | | } |
|---|
| 449 | | return $dest_results; |
|---|
| 450 | | } |
|---|
| 451 | | |
|---|
| 452 | | /** create a comprehensive list of all destinations that are problematic |
|---|
| 453 | | * @param array an array of destinations to check against |
|---|
| 454 | | * @param bool set to true if custome (unknown) destinations should be reported |
|---|
| 455 | | * @return array an array of the destinations that are empty, orphaned or custom |
|---|
| 456 | | * @description This function will scan the entire system and identify destinations |
|---|
| 457 | | * that are problematic. Either empty, orphaned or an unknow custom |
|---|
| 458 | | * destinations. An orphaned destination is one that should belong |
|---|
| 459 | | * to a module but the object it would have pointed to does not exist |
|---|
| 460 | | * because it was probably deleted. |
|---|
| 461 | | */ |
|---|
| 462 | | function framework_list_problem_destinations($module_hash=false, $ignore_custom=false) { |
|---|
| 463 | | global $active_modules; |
|---|
| 464 | | |
|---|
| 465 | | if (!is_array($module_hash)) { |
|---|
| 466 | | $module_hash = $active_modules; |
|---|
| 467 | | } |
|---|
| 468 | | |
|---|
| 469 | | $my_dest_arr = array(); |
|---|
| 470 | | $problem_dests = array(); |
|---|
| 471 | | |
|---|
| 472 | | $all_dests = framework_check_destination_usage(true, $module_hash); |
|---|
| 473 | | |
|---|
| 474 | | foreach ($all_dests as $dests) { |
|---|
| 475 | | foreach ($dests as $adest) { |
|---|
| 476 | | if (!empty($adest['dest'])) { |
|---|
| 477 | | $my_dest_arr[] = $adest['dest']; |
|---|
| 478 | | } |
|---|
| 479 | | } |
|---|
| 480 | | } |
|---|
| 481 | | $my_dest_arr = array_unique($my_dest_arr); |
|---|
| 482 | | |
|---|
| 483 | | $identities = framework_identify_destinations($my_dest_arr, $module_hash); |
|---|
| 484 | | |
|---|
| 485 | | foreach ($all_dests as $dests) { |
|---|
| 486 | | foreach ($dests as $adest) { |
|---|
| 487 | | if (empty($adest['dest'])) { |
|---|
| 488 | | $problem_dests[] = array('status' => 'EMPTY', |
|---|
| 489 | | 'dest' => $adest['dest'], |
|---|
| 490 | | 'description' => $adest['description'], |
|---|
| 491 | | 'edit_url' => $adest['edit_url'], |
|---|
| 492 | | ); |
|---|
| 493 | | } else if ($identities[$adest['dest']] === false){ |
|---|
| 494 | | if ($ignore_custom) { |
|---|
| 495 | | continue; |
|---|
| 496 | | } |
|---|
| 497 | | $problem_dests[] = array('status' => 'CUSTOM', |
|---|
| 498 | | 'dest' => $adest['dest'], |
|---|
| 499 | | 'description' => $adest['description'], |
|---|
| 500 | | 'edit_url' => $adest['edit_url'], |
|---|
| 501 | | ); |
|---|
| 502 | | } else if (is_array($identities[$adest['dest']])){ |
|---|
| 503 | | foreach ($identities[$adest['dest']] as $details) { |
|---|
| 504 | | if (empty($details)) { |
|---|
| 505 | | $problem_dests[] = array('status' => 'ORPHAN', |
|---|
| 506 | | 'dest' => $adest['dest'], |
|---|
| 507 | | 'description' => $adest['description'], |
|---|
| 508 | | 'edit_url' => $adest['edit_url'], |
|---|
| 509 | | ); |
|---|
| 510 | | |
|---|
| 511 | | } |
|---|
| 512 | | break; // there is only one set per array |
|---|
| 513 | | } |
|---|
| 514 | | } else { |
|---|
| 515 | | echo "ERROR?\n"; |
|---|
| 516 | | var_dump($adest); |
|---|
| 517 | | } |
|---|
| 518 | | } |
|---|
| 519 | | } |
|---|
| 520 | | return $problem_dests; |
|---|
| 521 | | } |
|---|
| 522 | | |
|---|
| 523 | | /** sort the hash based on the inner key |
|---|
| 524 | | */ |
|---|
| 525 | | function _framework_sort_exten($a, $b) { |
|---|
| 526 | | $a_key = array_keys($a); |
|---|
| 527 | | $a_key = $a_key[0]; |
|---|
| 528 | | $b_key = array_keys($b); |
|---|
| 529 | | $b_key = $b_key[0]; |
|---|
| 530 | | if ($a_key == $b_key) { |
|---|
| 531 | | return 0; |
|---|
| 532 | | } else { |
|---|
| 533 | | return ($a_key < $b_key) ? -1 : 1; |
|---|
| 534 | | } |
|---|
| 535 | | } |
|---|
| 536 | | |
|---|
| 537 | | /** create a comprehensive list of all extensions conflicts |
|---|
| 538 | | * @return array an array of the destinations that are empty, orphaned or custom |
|---|
| 539 | | * @description This returns an array structure with information about all |
|---|
| 540 | | * extension numbers that are in conflict. This means the same number |
|---|
| 541 | | * is being used by 2 or more modules and the results will be ambiguous |
|---|
| 542 | | * which one will be ignored when dialed. See the code for the |
|---|
| 543 | | * structure of the retured array. |
|---|
| 544 | | */ |
|---|
| 545 | | function framework_list_extension_conflicts($module_hash=false) { |
|---|
| 546 | | global $active_modules; |
|---|
| 547 | | |
|---|
| 548 | | if (!is_array($module_hash)) { |
|---|
| 549 | | $module_hash = $active_modules; |
|---|
| 550 | | } |
|---|
| 551 | | |
|---|
| 552 | | $exten_list = framework_check_extension_usage(true,$module_hash); |
|---|
| 553 | | |
|---|
| 554 | | /** Bookkeeping hashes |
|---|
| 555 | | * full_hash[] will contain the first extension encountered |
|---|
| 556 | | * conflict_hash[] will contain any subsequent extensions if conflicts |
|---|
| 557 | | * |
|---|
| 558 | | * If there are conflicts, the full set is what is in conflict_hash + the |
|---|
| 559 | | * first extension encoutnered in full_hash[] |
|---|
| 560 | | */ |
|---|
| 561 | | $full_hash = array(); |
|---|
| 562 | | $conflict_hash = array(); |
|---|
| 563 | | |
|---|
| 564 | | foreach ($exten_list as $mod => $mod_extens) { |
|---|
| 565 | | foreach ($mod_extens as $exten => $details) { |
|---|
| 566 | | if (!isset($full_hash[$exten])) { |
|---|
| 567 | | $full_hash[$exten] = $details; |
|---|
| 568 | | } else { |
|---|
| 569 | | $conflict_hash[] = array($exten => $details); |
|---|
| 570 | | } |
|---|
| 571 | | } |
|---|
| 572 | | } |
|---|
| 573 | | |
|---|
| 574 | | // extract conflicting remaining extension from full_hash but needs to be unique |
|---|
| 575 | | // |
|---|
| 576 | | if (!empty($conflict_hash)) { |
|---|
| 577 | | $other_conflicts = array(); |
|---|
| 578 | | foreach ($conflict_hash as $item) { |
|---|
| 579 | | foreach (array_keys($item) as $exten) { |
|---|
| 580 | | $other_conflicts[$exten] = $full_hash[$exten]; |
|---|
| 581 | | } |
|---|
| 582 | | } |
|---|
| 583 | | foreach ($other_conflicts as $exten => $details) { |
|---|
| 584 | | $conflict_hash[] = array($exten => $details); |
|---|
| 585 | | } |
|---|
| 586 | | usort($conflict_hash, "_framework_sort_exten"); |
|---|
| 587 | | return $conflict_hash; |
|---|
| 588 | | } |
|---|
| 589 | | } |
|---|
| 590 | | |
|---|
| 591 | | /** Expands variables from amportal.conf |
|---|
| 592 | | * Replaces any variables enclosed in percent (%) signs with their value |
|---|
| 593 | | * eg, "%AMPWEBROOT%/admin/functions.inc.php" |
|---|
| 594 | | */ |
|---|
| 595 | | function expand_variables($string) { |
|---|
| 596 | | global $amp_conf; |
|---|
| 597 | | $search = $replace = array(); |
|---|
| 598 | | foreach ($amp_conf as $key=>$value) { |
|---|
| 599 | | $search[] = '%'.$key.'%'; |
|---|
| 600 | | $replace[] = $value; |
|---|
| 601 | | } |
|---|
| 602 | | return str_replace($search, $replace, $string); |
|---|
| 603 | | } |
|---|
| | 27 | require_once( (defined('AMP_BASE_INCLUDE_PATH') ? AMP_BASE_INCLUDE_PATH.'/' : '').'libraries/usage_registry.functions.php'); |
|---|
| | 28 | require_once( (defined('AMP_BASE_INCLUDE_PATH') ? AMP_BASE_INCLUDE_PATH.'/' : '').'libraries/php-upgrade.functions.php'); |
|---|
| | 29 | require_once( (defined('AMP_BASE_INCLUDE_PATH') ? AMP_BASE_INCLUDE_PATH.'/' : '').'libraries/sql.functions.php'); |
|---|