Changeset 6600
- Timestamp:
- 09/07/08 18:33:09 (5 years ago)
- Files:
-
- freepbx/trunk (modified) (1 prop)
- freepbx/trunk/CHANGES (modified) (2 diffs)
- freepbx/trunk/amp_conf/astetc/chan_dahdi.conf.template (copied) (copied from freepbx/branches/2.5/amp_conf/astetc/chan_dahdi.conf.template)
- freepbx/trunk/amp_conf/bin/freepbx_engine (modified) (1 diff)
- freepbx/trunk/amp_conf/bin/libfreepbx.confgen.php (modified) (3 diffs)
- freepbx/trunk/amp_conf/bin/retrieve_conf (modified) (3 diffs)
- freepbx/trunk/amp_conf/htdocs/admin/config.php (modified) (1 diff)
- freepbx/trunk/amp_conf/htdocs/admin/extensions.class.php (modified) (2 diffs)
- freepbx/trunk/amp_conf/htdocs/admin/functions.inc.php (modified) (36 diffs)
- freepbx/trunk/amp_conf/htdocs/admin/page.modules.php (modified) (13 diffs)
- freepbx/trunk/amp_conf/htdocs/admin/views/freepbx_admin.php (modified) (3 diffs)
- freepbx/trunk/amp_conf/htdocs/recordings/includes/display.php (modified) (1 diff)
- freepbx/trunk/amp_conf/htdocs/recordings/includes/main.conf.php (modified) (1 diff)
- freepbx/trunk/amp_conf/htdocs/recordings/modules/callmonitor.module (modified) (6 diffs)
- freepbx/trunk/amp_conf/htdocs/recordings/modules/followme.module (modified) (2 diffs)
- freepbx/trunk/amportal.conf (modified) (1 diff)
Legend:
- Unmodified
- Added
- Removed
- Modified
- Copied
- Moved
freepbx/trunk
- Property svnmerge-integrated changed from /freepbx/branches/2.4:1-5944 /freepbx/branches/2.5:1-6538 to /freepbx/branches/2.4:1-5944 /freepbx/branches/2.5:1-6599
freepbx/trunk/CHANGES
r6539 r6600 16 16 ARI updates could be split from other framework updates in order to allow people 17 17 with highly customized FOP and ARI changes to pull framework updates easier. 18 19 - Added Streaming categories to MoH in addition to downloaded files 18 20 19 21 2.5.0 Added before rc1 … … 101 103 the stats are updated based on the STATS interval but a few items are checked 102 104 less frequently (such as Astersisk Uptime) based on the INFO value 105 106 ZAP2DAHDICOMPAT=true|false 107 DEFAULT VALUE: false 108 If set to true, FreePBX will check if you have chan_dadhi installed. If so, it will 109 automatically use all your ZAP configuration settings (devices and trunks) and 110 silently convert them, under the covers, to DAHDI so no changes are needed. The 111 GUI will continue to refer to these as ZAP but it will use the proper DAHDI channels. 112 This will also keep Zap Channel DIDs working. 103 113 104 114 freepbx/trunk/amp_conf/bin/freepbx_engine
r6244 r6600 96 96 # Ensure that various hardware devices are owned correctly. 97 97 [ -e /dev/zap ] && chown -R $AMPDEVUSER:$AMPDEVGROUP /dev/zap 98 [ -e /dev/dahdi ] && chown -R $AMPDEVUSER:$AMPDEVGROUP /dev/dahdi 98 99 [ -e /dev/capi20 ] && chown -R $AMPDEVUSER:$AMPDEVGROUP /dev/capi20 99 100 [ -e /dev/misdn ] && chown -R $AMPDEVUSER:$AMPDEVGROUP /dev/misdn freepbx/trunk/amp_conf/bin/libfreepbx.confgen.php
r5974 r6600 170 170 171 171 function generate_configurations_zap($ast_version) { 172 172 global $chan_dahdi; 173 173 global $amp_conf; 174 174 global $db; … … 177 177 178 178 $zap_conf = $amp_conf['ASTETCDIR']."/zapata_additional.conf"; 179 $channel_name = 'ZAP'; 180 if ($chan_dahdi) { 181 $zap_conf = $amp_conf['ASTETCDIR']."/chan_dahdi_additional.conf"; 182 $channel_name = 'DAHDI'; 183 } 179 184 180 185 $table_name = "zap"; … … 184 189 $zap_conf_fh = fopen($zap_conf,"w"); 185 190 if ($zap_conf_fh === false) { 186 fatal(_("Cannot write ZAP configurations"),sprintf(_("Failed creating/overwriting Zapataextensions file: %s"),$zap_conf));191 fatal(_("Cannot write $channel_name configurations"),sprintf(_("Failed creating/overwriting $channel_name extensions file: %s"),$zap_conf)); 187 192 } 188 193 freepbx/trunk/amp_conf/bin/retrieve_conf
r6539 r6600 370 370 $engine = $engineinfo['engine']; 371 371 $version = $engineinfo['version']; 372 $chan_dahdi = ast_with_dahdi(); 372 373 373 374 // Check for and report any extension conflicts … … 482 483 freepbx_log('retrieve_conf', 'devel-debug', 'generateConf from '.$classname); 483 484 if (isset(${$classname}->use_warning_banner)) { 484 write_file(${$classname}->get_filename(),${$classname}->generateConf(),${$classname}->use_ nowarning_banner);485 write_file(${$classname}->get_filename(),${$classname}->generateConf(),${$classname}->use_warning_banner); 485 486 } else { 486 487 write_file(${$classname}->get_filename(),${$classname}->generateConf()); … … 588 589 set_error_handler("report_errors"); 589 590 if (copy($source, $dest)) { 590 $ret = chmod($dest, '0754');591 $ret = chmod($dest,0754); 591 592 } 592 593 restore_error_handler(); freepbx/trunk/amp_conf/htdocs/admin/config.php
r6539 r6600 129 129 //create an array of module sections to display 130 130 // stored as [items][$type][$category][$name] = $displayvalue 131 if ( !$quitemode &&isset($module['items']) && is_array($module['items'])) {131 if (isset($module['items']) && is_array($module['items'])) { 132 132 // loop through the types 133 133 foreach($module['items'] as $itemKey => $item) { freepbx/trunk/amp_conf/htdocs/admin/extensions.class.php
r6539 r6600 929 929 class ext_zapbarge extends extension { 930 930 function output() { 931 return "ZapBarge(".$this->data.")"; 931 global $chan_dahdi; 932 933 if ($chan_dahdi) { 934 $command = 'DAHDIBarge'; 935 } else { 936 $command = 'ZapBarge'; 937 } 938 939 return "$command(".$this->data.")"; 932 940 } 933 941 } … … 974 982 class ext_lookupcidname extends extension { 975 983 function output() { 976 return "LookupCIDName"; 977 } 984 global $version; 985 986 if (version_compare($version, "1.6", "ge")) { 987 $outstr=addslashes('Set(CALLERID(name)=${DB(cidname/${CALLERID(num)})})'); 988 return $outstr; 989 } else { 990 return "LookupCIDName"; 991 } 992 } 978 993 } 979 994 freepbx/trunk/amp_conf/htdocs/admin/functions.inc.php
r6539 r6600 20 20 define('MODULE_STATUS_NEEDUPGRADE', 3); 21 21 define('MODULE_STATUS_BROKEN', -1); 22 23 class modulelist { 24 var $_loaded = false; 25 var $module_array = array(); 26 var $_db; 27 28 function &create(&$db) { 29 static $obj; 30 if (!isset($obj)) { 31 $obj = new modulelist($db); 32 } 33 return $obj; 34 } 35 function modulelist(&$db) { 36 $this->_db =& $db; 37 $module_serialized = sql("SELECT `data` FROM `module_xml` WHERE `id` = 'mod_serialized'","getOne"); 38 if (isset($module_serialized) && $module_serialized) { 39 $this->module_array = (unserialize($module_serialized)); 40 $this->_loaded = true; 41 } 42 } 43 function is_loaded() { 44 return $this->_loaded; 45 } 46 function initialize(&$module_list) { 47 $this->module_array = $module_list; 48 $module_serialized = $this->_db->escapeSimple(serialize($this->module_array)); 49 sql("DELETE FROM `module_xml` WHERE `id` = 'mod_serialized'"); 50 sql("INSERT INTO `module_xml` (`id`, `time`, `data`) VALUES ('mod_serialized', '".time()."','".$module_serialized."')"); 51 $this->_loaded = true; 52 } 53 function invalidate() { 54 unset($this->module_array); 55 sql("DELETE FROM `module_xml` WHERE `id` = 'mod_serialized'"); 56 $this->_loaded = false; 57 } 58 } 59 60 define("NOTIFICATION_TYPE_CRITICAL", 100); 61 define("NOTIFICATION_TYPE_SECURITY", 200); 62 define("NOTIFICATION_TYPE_UPDATE", 300); 63 define("NOTIFICATION_TYPE_ERROR", 400); 64 define("NOTIFICATION_TYPE_WARNING" , 500); 65 define("NOTIFICATION_TYPE_NOTICE", 600); 66 67 class notifications { 68 69 var $not_loaded = true; 70 var $notification_table = array(); 71 var $_db; 72 73 function &create(&$db) { 74 static $obj; 75 if (!isset($obj)) { 76 $obj = new notifications($db); 77 } 78 return $obj; 79 } 80 81 function notifications(&$db) { 82 $this->_db =& $db; 83 } 84 85 86 function add_critical($module, $id, $display_text, $extended_text="", $link="", $reset=true, $candelete=false) { 87 $this->_add_type(NOTIFICATION_TYPE_CRITICAL, $module, $id, $display_text, $extended_text, $link, $reset, $candelete); 88 } 89 function add_security($module, $id, $display_text, $extended_text="", $link="", $reset=true, $candelete=false) { 90 $this->_add_type(NOTIFICATION_TYPE_SECURITY, $module, $id, $display_text, $extended_text, $link, $reset, $candelete); 91 } 92 function add_update($module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=false) { 93 $this->_add_type(NOTIFICATION_TYPE_UPDATE, $module, $id, $display_text, $extended_text, $link, $reset, $candelete); 94 } 95 function add_error($module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=false) { 96 $this->_add_type(NOTIFICATION_TYPE_ERROR, $module, $id, $display_text, $extended_text, $link, $reset, $candelete); 97 } 98 function add_warning($module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=false) { 99 $this->_add_type(NOTIFICATION_TYPE_WARNING, $module, $id, $display_text, $extended_text, $link, $reset, $candelete); 100 } 101 function add_notice($module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=true) { 102 $this->_add_type(NOTIFICATION_TYPE_NOTICE, $module, $id, $display_text, $extended_text, $link, $reset, $candelete); 103 } 104 105 106 function list_critical($show_reset=false) { 107 return $this->_list(NOTIFICATION_TYPE_CRITICAL, $show_reset); 108 } 109 function list_security($show_reset=false) { 110 return $this->_list(NOTIFICATION_TYPE_SECURITY, $show_reset); 111 } 112 function list_update($show_reset=false) { 113 return $this->_list(NOTIFICATION_TYPE_UPDATE, $show_reset); 114 } 115 function list_error($show_reset=false) { 116 return $this->_list(NOTIFICATION_TYPE_ERROR, $show_reset); 117 } 118 function list_warning($show_reset=false) { 119 return $this->_list(NOTIFICATION_TYPE_WARNING, $show_reset); 120 } 121 function list_notice($show_reset=false) { 122 return $this->_list(NOTIFICATION_TYPE_NOTICE, $show_reset); 123 } 124 function list_all($show_reset=false) { 125 return $this->_list("", $show_reset); 126 } 127 128 129 function reset($module, $id) { 130 $module = q($module); 131 $id = q($id); 132 133 $sql = "UPDATE notifications SET reset = 1 WHERE module = $module AND id = $id"; 134 sql($sql); 135 } 136 137 function delete($module, $id) { 138 $module = q($module); 139 $id = q($id); 140 141 $sql = "DELETE FROM notifications WHERE module = $module AND id = $id"; 142 sql($sql); 143 } 144 145 function safe_delete($module, $id) { 146 $module = q($module); 147 $id = q($id); 148 149 $sql = "DELETE FROM notifications WHERE module = $module AND id = $id AND candelete = 1"; 150 sql($sql); 151 } 152 153 /* Internal functions 154 */ 155 156 function _add_type($level, $module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=false) { 157 if ($this->not_loaded) { 158 $this->notification_table = $this->_list("",true); 159 $this->not_loaded = false; 160 } 161 162 $existing_row = false; 163 foreach ($this->notification_table as $row) { 164 if ($row['module'] == $module && $row['id'] == $id ) { 165 $existing_row = $row; 166 break; 167 } 168 } 169 // Found an existing row - check if anything changed or if we are suppose to reset it 170 // 171 $candelete = $candelete ? 1 : 0; 172 if ($existing_row) { 173 174 if (($reset && $existing_row['reset'] == 1) || $existing_row['level'] != $level || $existing_row['display_text'] != $display_text || $existing_row['extended_text'] != $extended_text || $existing_row['link'] != $link || $existing_row['candelete'] == $candelete) { 175 176 // If $reset is set to the special case of PASSIVE then the updates will not change it's value in an update 177 // 178 $reset_value = ($reset == 'PASSIVE') ? $existing_row['reset'] : 0; 179 180 $module = q($module); 181 $id = q($id); 182 $level = q($level); 183 $display_text = q($display_text); 184 $extended_text = q($extended_text); 185 $link = q($link); 186 $now = time(); 187 $sql = "UPDATE notifications SET 188 level = $level, 189 display_text = $display_text, 190 extended_text = $extended_text, 191 link = $link, 192 reset = $reset_value, 193 candelete = $candelete, 194 timestamp = $now 195 WHERE module = $module AND id = $id 196 "; 197 sql($sql); 198 199 // TODO: I should really just add this to the internal cache, but really 200 // how often does this get called that if is a big deal. 201 $this->not_loaded = true; 202 } 203 } else { 204 // No existing row so insert this new one 205 // 206 $now = time(); 207 $module = q($module); 208 $id = q($id); 209 $level = q($level); 210 $display_text = q($display_text); 211 $extended_text = q($extended_text); 212 $link = q($link); 213 $sql = "INSERT INTO notifications 214 (module, id, level, display_text, extended_text, link, reset, candelete, timestamp) 215 VALUES 216 ($module, $id, $level, $display_text, $extended_text, $link, 0, $candelete, $now) 217 "; 218 sql($sql); 219 220 // TODO: I should really just add this to the internal cache, but really 221 // how often does this get called that if is a big deal. 222 $this->not_loaded = true; 223 } 224 } 225 226 function _list($level, $show_reset=false) { 227 228 $level = q($level); 229 $where = array(); 230 231 if (!$show_reset) { 232 $where[] = "reset = 0"; 233 } 234 235 switch ($level) { 236 case NOTIFICATION_TYPE_CRITICAL: 237 case NOTIFICATION_TYPE_SECURITY: 238 case NOTIFICATION_TYPE_UPDATE: 239 case NOTIFICATION_TYPE_ERROR: 240 case NOTIFICATION_TYPE_WARNING: 241 case NOTIFICATION_TYPE_NOTICE: 242 $where[] = "level = $level "; 243 break; 244 default: 245 } 246 $sql = "SELECT * FROM notifications "; 247 if (count($where)) { 248 $sql .= " WHERE ".implode(" AND ", $where); 249 } 250 $sql .= " ORDER BY level, module"; 251 252 $list = sql($sql,"getAll",DB_FETCHMODE_ASSOC); 253 return $list; 254 } 255 /* Returns the number of active notifications 256 */ 257 function get_num_active() { 258 $sql = "SELECT COUNT(id) FROM notifications WHERE reset = 0"; 259 return sql($sql,'getOne'); 260 } 261 } 262 263 class cronmanager { 264 /** 265 * note: time is the hour time of day a job should run, -1 indicates don't care 266 */ 267 268 function &create(&$db) { 269 static $obj; 270 if (!isset($obj)) { 271 $obj = new cronmanager($db); 272 } 273 return $obj; 274 } 275 276 function cronmanager(&$db) { 277 $this->_db =& $db; 278 } 279 280 function save_email($address) { 281 $address = q($address); 282 sql("DELETE FROM admin WHERE variable = 'email'"); 283 sql("INSERT INTO admin (variable, value) VALUES ('email', $address)"); 284 } 285 286 function get_email() { 287 $sql = "SELECT value FROM admin WHERE variable = 'email'"; 288 return sql($sql, 'getOne'); 289 } 290 291 function save_hash($id, &$string) { 292 $hash = md5($string); 293 $id = q($id); 294 sql("DELETE FROM admin WHERE variable = $id"); 295 sql("INSERT INTO admin (variable, value) VALUE ($id, '$hash')"); 296 } 297 298 function check_hash($id, &$string) { 299 $id = q($id); 300 $sql = "SELECT value FROM admin WHERE variable = $id LIMIT 1"; 301 $hash = sql($sql, "getOne"); 302 return ($hash == md5($string)); 303 } 304 305 function enable_updates($freq=24) { 306 global $amp_conf; 307 308 $night_time = array(19,20,21,22,23,0,1,2,3,4,5); 309 $run_time = $night_time[rand(0,10)]; 310 $command = $amp_conf['AMPBIN']."/module_admin listonline"; 311 $lasttime = 0; 312 313 $sql = "SELECT * FROM cronmanager WHERE module = 'module_admin' AND id = 'UPDATES'"; 314 $result = sql($sql, "getAll",DB_FETCHMODE_ASSOC); 315 if (count($result)) { 316 $sql = "UPDATE cronmanager SET 317 freq = '$freq', 318 command = '$command' 319 WHERE 320 module = 'module_admin' AND id = 'UPDATES' 321 "; 322 } else { 323 $sql = "INSERT INTO cronmanager 324 (module, id, time, freq, lasttime, command) 325 VALUES 326 ('module_admin', 'UPDATES', '$run_time', $freq, 0, '$command') 327 "; 328 } 329 sql($sql); 330 } 331 332 function disable_updates() { 333 sql("DELETE FROM cronmanager WHERE module = 'module_admin' AND id = 'UPDATES'"); 334 } 335 336 function updates_enabled() { 337 $results = sql("SELECT module, id FROM cronmanager WHERE module = 'module_admin' AND id = 'UPDATES'",'getAll'); 338 return count($results); 339 } 340 341 /** run_jobs() 342 * select all entries that need to be run now and run them, then update the times. 343 * 344 * 1. select all entries 345 * 2. foreach entry, if its paramters indicate it should be run, then run it and 346 * update it was run in the time stamp. 347 */ 348 function run_jobs() { 349 350 $errors = 0; 351 $error_arr = array(); 352 353 $now = time(); 354 $jobs = sql("SELECT * FROM cronmanager","getAll", DB_FETCHMODE_ASSOC); 355 foreach ($jobs as $job) { 356 $nexttime = $job['lasttime'] + $job['freq']*3600; 357 if ($nexttime <= $now) { 358 if ($job['time'] >= 0 && $job['time'] < 24) { 359 $date_arr = getdate($now); 360 // Now if lasttime is 0, then we want this kicked off at the proper hour 361 // after wich the frequencey will set the pace for same time each night 362 // 363 if (($date_arr['hours'] != $job['time']) && !$job['lasttime']) { 364 continue; 365 } 366 } 367 } else { 368 // no need to run job, time is not up yet 369 continue; 370 } 371 // run the job 372 exec($job['command'],$job_out,$ret); 373 if ($ret) { 374 $errors++; 375 $error_arr[] = array($job['command'],$ret); 376 377 // If there where errors, let's print them out in case the script is being debugged or running 378 // from cron which will then put the errors out through the cron system. 379 // 380 foreach ($job_out as $line) { 381 echo $line."\n"; 382 } 383 } else { 384 $module = $job['module']; 385 $id = $job['id']; 386 $sql = "UPDATE cronmanager SET lasttime = $now WHERE module = '$module' AND id = '$id'"; 387 sql($sql); 388 } 389 } 390 if ($errors) { 391 $nt =& notifications::create($db); 392 $text = sprintf(_("Cronmanager encountered %s Errors"),$errors); 393 $extext = _("The following commands failed with the listed error"); 394 foreach ($error_arr as $item) { 395 $extext .= "<br>".$item[0]." (".$item[1].")"; 396 } 397 $nt->add_error('cron_manager', 'EXECFAIL', $text, $extext, '', true, true); 398 } 399 } 400 } 401 402 class ampuser { 403 var $username; 404 var $_password; 405 var $_extension_high; 406 var $_extension_low; 407 var $_deptname; 408 var $_sections; 409 410 function ampuser($username) { 411 $this->username = $username; 412 if ($user = getAmpUser($username)) { 413 $this->_password = $user["password"]; 414 $this->_extension_high = $user["extension_high"]; 415 $this->_extension_low = $user["extension_low"]; 416 $this->_deptname = $user["deptname"]; 417 $this->_sections = $user["sections"]; 418 } else { 419 // user doesn't exist 420 $this->_password = false; 421 $this->_extension_high = ""; 422 $this->_extension_low = ""; 423 $this->_deptname = ""; 424 $this->_sections = array(); 425 } 426 } 427 428 /** Give this user full admin access 429 */ 430 function setAdmin() { 431 $this->_extension_high = ""; 432 $this->_extension_low = ""; 433 $this->_deptname = ""; 434 $this->_sections = array("*"); 435 } 436 437 function checkPassword($password) { 438 // strict checking so false will never match 439 return ($this->_password === $password); 440 } 441 442 function checkSection($section) { 443 // if they have * then it means all sections 444 return in_array("*", $this->_sections) || in_array($section, $this->_sections); 445 } 446 } 447 448 /* Usage 449 Grab some XML data, either from a file, URL, etc. however you want. Assume storage in $strYourXML; 450 451 $xml = new xml2Array($strYourXML); 452 xml array is in $xml->data; 453 This is basically an array version of the XML data (no attributes), striaght-up. If there are 454 multiple items with the same name, they are split into a numeric sub-array, 455 eg, <items><item test="123">foo</item><item>bar</item></items> 456 becomes: array('item' => array(0=>array('item'=>'foo'), 1=>array('item'=>'foo')) 457 attributes are in $xml->attributes; 458 These are stored with xpath type paths, as $xml->attributes['/items/item/0']["test"] == "123" 459 460 461 Other way (still works, but not as nice): 462 463 $objXML = new xml2Array(); 464 $arrOutput = $objXML->parse($strYourXML); 465 print_r($arrOutput); //print it out, or do whatever! 466 467 */ 468 469 class xml2Array { 470 var $arrOutput = array(); 471 var $resParser; 472 var $strXmlData; 473 474 var $attributes; 475 var $data; 476 477 function xml2Array($strInputXML = false) { 478 if (!empty($strInputXML)) { 479 $this->data = $this->parseAdvanced($strInputXML); 480 } 481 } 482 483 function parse($strInputXML) { 484 485 $this->resParser = xml_parser_create (); 486 xml_set_object($this->resParser,$this); 487 xml_set_element_handler($this->resParser, "tagOpen", "tagClosed"); 488 489 xml_set_character_data_handler($this->resParser, "tagData"); 490 491 $this->strXmlData = xml_parse($this->resParser,$strInputXML ); 492 if(!$this->strXmlData) { 493 die_freepbx(sprintf("XML error: %s at line %d", 494 xml_error_string(xml_get_error_code($this->resParser)), 495 xml_get_current_line_number($this->resParser))); 496 } 497 498 xml_parser_free($this->resParser); 499 500 return $this->arrOutput; 501 } 502 function tagOpen($parser, $name, $attrs) { 503 $tag=array("name"=>$name,"attrs"=>$attrs); 504 @array_push($this->arrOutput,$tag); 505 } 506 507 function tagData($parser, $tagData) { 508 if(trim($tagData)) { 509 if(isset($this->arrOutput[count($this->arrOutput)-1]['tagData'])) { 510 $this->arrOutput[count($this->arrOutput)-1]['tagData'] .= "\n".$tagData; 511 } 512 else { 513 $this->arrOutput[count($this->arrOutput)-1]['tagData'] = $tagData; 514 } 515 } 516 } 517 518 function tagClosed($parser, $name) { 519 @$this->arrOutput[count($this->arrOutput)-2]['children'][] = $this->arrOutput[count($this->arrOutput)-1]; 520 array_pop($this->arrOutput); 521 } 522 523 function recursive_parseLevel($items, &$attrs, $path = "") { 524 $array = array(); 525 foreach (array_keys($items) as $idx) { 526 @$items[$idx]['name'] = strtolower($items[$idx]['name']); 527 528 $multi = false; 529 if (isset($array[ $items[$idx]['name'] ])) { 530 // this child is already set, so we're adding multiple items to an array 531 532 if (!is_array($array[ $items[$idx]['name'] ]) || !isset($array[ $items[$idx]['name'] ][0])) { 533 // hasn't already been made into a numerically-indexed array, so do that now 534 // we're basically moving the current contents of this item into a 1-item array (at the 535 // original location) so that we can add a second item in the code below 536 $array[ $items[$idx]['name'] ] = array( $array[ $items[$idx]['name'] ] ); 537 538 if (isset($attrs[ $path.'/'.$items[$idx]['name'] ])) { 539 // move the attributes to /0 540 $attrs[ $path.'/'.$items[$idx]['name'].'/0' ] = $attrs[ $path.'/'.$items[$idx]['name'] ]; 541 unset($attrs[ $path.'/'.$items[$idx]['name'] ]); 542 } 543 } 544 $multi = true; 545 } 546 547 if ($multi) { 548 $newitem = &$array[ $items[$idx]['name'] ][]; 549 } else { 550 $newitem = &$array[ $items[$idx]['name'] ]; 551 } 552 553 554 if (isset($items[$idx]['children']) && is_array($items[$idx]['children'])) { 555 $newitem = $this->recursive_parseLevel($items[$idx]['children'], $attrs, $path.'/'.$items[$idx]['name']); 556 } else if (isset($items[$idx]['tagData'])) { 557 $newitem = $items[$idx]['tagData']; 558 } else { 559 $newitem = false; 560 } 561 562 if (isset($items[$idx]['attrs']) && is_array($items[$idx]['attrs']) && count($items[$idx]['attrs'])) { 563 $attrpath = $path.'/'.$items[$idx]['name']; 564 if ($multi) { 565 $attrpath .= '/'.(count($array[ $items[$idx]['name'] ])-1); 566 } 567 foreach ($items[$idx]['attrs'] as $name=>$value) { 568 $attrs[ $attrpath ][ strtolower($name) ] = $value; 569 } 570 } 571 } 572 return $array; 573 } 574 575 function parseAdvanced($strInputXML) { 576 $array = $this->parse($strInputXML); 577 $this->attributes = array(); 578 return $this->data = $this->recursive_parseLevel($array, $this->attributes); 579 } 580 } 581 582 /* 583 Return a much more manageable assoc array with module data. 584 */ 585 class xml2ModuleArray extends xml2Array { 586 function parseModulesXML($strInputXML) { 587 $array = $this->parseAdvanced($strInputXML); 588 if (isset($array['xml'])) { 589 foreach ($array['xml'] as $key=>$module) { 590 if ($key == 'module') { 591 // copy the structure verbatim 592 $modules[ $module['name'] ] = $module; 593 } 594 } 595 } 596 597 // if you are confused about what's happening below, uncomment this why we do it 598 // echo "<pre>"; print_r($arrOutput); echo "</pre>"; 599 600 // ignore the regular xml garbage ([0]['children']) & loop through each module 601 if(!is_array($arrOutput[0]['children'])) return false; 602 foreach($arrOutput[0]['children'] as $module) { 603 if(!is_array($module['children'])) return false; 604 // loop through each modules's tags 605 foreach($module['children'] as $modTags) { 606 if(isset($modTags['children']) && is_array($modTags['children'])) { 607 $$modTags['name'] = $modTags['children']; 608 // loop if there are children (menuitems and requirements) 609 foreach($modTags['children'] as $subTag) { 610 $subTags[strtolower($subTag['name'])] = $subTag['tagData']; 611 } 612 $$modTags['name'] = $subTags; 613 unset($subTags); 614 } else { 615 // create a variable for each tag we find 616 $$modTags['name'] = $modTags['tagData']; 617 } 618 619 } 620 // now build our return array 621 $arrModules[$RAWNAME]['rawname'] = $RAWNAME; // This has to be set 622 $arrModules[$RAWNAME]['displayName'] = $NAME; // This has to be set 623 $arrModules[$RAWNAME]['version'] = $VERSION; // This has to be set 624 $arrModules[$RAWNAME]['type'] = isset($TYPE)?$TYPE:'setup'; 625 $arrModules[$RAWNAME]['category'] = isset($CATEGORY)?$CATEGORY:'Unknown'; 626 $arrModules[$RAWNAME]['info'] = isset($INFO)?$INFO:'http://www.freepbx.org/wiki/'.$RAWNAME; 627 $arrModules[$RAWNAME]['location'] = isset($LOCATION)?$LOCATION:'local'; 628 $arrModules[$RAWNAME]['items'] = isset($MENUITEMS)?$MENUITEMS:null; 629 $arrModules[$RAWNAME]['requirements'] = isset($REQUIREMENTS)?$REQUIREMENTS:null; 630 $arrModules[$RAWNAME]['md5sum'] = isset($MD5SUM)?$MD5SUM:null; 631 //print_r($arrModules); 632 //unset our variables 633 unset($NAME); 634 unset($VERSION); 635 unset($TYPE); 636 unset($CATEGORY); 637 unset($AUTHOR); 638 unset($EMAIL); 639 unset($LOCATION); 640 unset($MENUITEMS); 641 unset($REQUIREMENTS); 642 unset($MD5SUM); 643 } 644 //echo "<pre>"; print_r($arrModules); echo "</pre>"; 645 646 return $arrModules; 647 } 648 } 649 650 class moduleHook { 651 var $hookHtml = ''; 652 var $arrHooks = array(); 653 654 function install_hooks($viewing_itemid,$target_module,$target_menuid = '') { 655 global $active_modules; 656 // loop through all active modules 657 foreach($active_modules as $this_module) { 658 // look for requested hooks for $module 659 // ie: findme_hook_extensions() 660 $funct = $this_module['rawname'] . '_hook_' . $target_module; 661 if( function_exists( $funct ) ) { 662 // execute the function, appending the 663 // html output to that of other hooking modules 664 if ($hookReturn = $funct($target_menuid, $viewing_itemid)) { 665 $this->hookHtml .= $hookReturn; 666 } 667 // remember who installed hooks 668 // we need to know this for processing form vars 669 $this->arrHooks[] = $this_module['rawname']; 670 } 671 } 672 } 673 674 // process the request from the module we hooked 675 function process_hooks($viewing_itemid, $target_module, $target_menuid, $request) { 676 if(is_array($this->arrHooks)) { 677 foreach($this->arrHooks as $hookingMod) { 678 // check if there is a processing function 679 $funct = $hookingMod . '_hookProcess_' . $target_module; 680 if( function_exists( $funct ) ) { 681 $funct($viewing_itemid, $request); 682 } 683 } 684 } 685 } 686 } 22 687 23 688 $amp_conf_defaults = array( … … 64 729 'AMPENABLEDEVELDEBUG'=> array('bool' , false), 65 730 'AMPMPG123' => array('bool' , true), 731 'ZAP2DAHDICOMPAT' => array('bool' , false), 66 732 ); 67 733 … … 73 739 * components don't have to keep being 'gun shy' about these variables. 74 740 * 75 76 741 */ 77 742 $file = file($filename); … … 118 783 } 119 784 } 120 121 /*122 TODO: what was this, should the comment be removed?123 124 if (($amp_conf["AMPDBENGINE"] == "sqlite") && (!isset($amp_conf["AMPDBENGINE"])))125 $amp_conf["AMPDBFILE"] = "/var/lib/freepbx/freepbx.sqlite";126 */127 128 785 return $conf; 129 786 } … … 160 817 } 161 818 return $conf; 162 }163 164 165 define("NOTIFICATION_TYPE_CRITICAL", 100);166 define("NOTIFICATION_TYPE_SECURITY", 200);167 define("NOTIFICATION_TYPE_UPDATE", 300);168 define("NOTIFICATION_TYPE_ERROR", 400);169 define("NOTIFICATION_TYPE_WARNING" , 500);170 define("NOTIFICATION_TYPE_NOTICE", 600);171 172 class modulelist {173 var $_loaded = false;174 var $module_array = array();175 var $_db;176 177 function &create(&$db) {178 static $obj;179 if (!isset($obj)) {180 $obj = new modulelist($db);181 }182 return $obj;183 }184 function modulelist(&$db) {185 $this->_db =& $db;186 $module_serialized = sql("SELECT `data` FROM `module_xml` WHERE `id` = 'mod_serialized'","getOne");187 if (isset($module_serialized) && $module_serialized) {188 $this->module_array = (unserialize($module_serialized));189 $this->_loaded = true;190 }191 }192 function is_loaded() {193 return $this->_loaded;194 }195 function initialize(&$module_list) {196 $this->module_array = $module_list;197 $module_serialized = $this->_db->escapeSimple(serialize($this->module_array));198 sql("DELETE FROM `module_xml` WHERE `id` = 'mod_serialized'");199 sql("INSERT INTO `module_xml` (`id`, `time`, `data`) VALUES ('mod_serialized', '".time()."','".$module_serialized."')");200 $this->_loaded = true;201 }202 function invalidate() {203 unset($this->module_array);204 sql("DELETE FROM `module_xml` WHERE `id` = 'mod_serialized'");205 $this->_loaded = false;206 }207 }208 209 210 211 class notifications {212 213 var $not_loaded = true;214 var $notification_table = array();215 var $_db;216 217 function &create(&$db) {218 static $obj;219 if (!isset($obj)) {220 $obj = new notifications($db);221 }222 return $obj;223 }224 225 function notifications(&$db) {226 $this->_db =& $db;227 }228 229 230 function add_critical($module, $id, $display_text, $extended_text="", $link="", $reset=true, $candelete=false) {231 $this->_add_type(NOTIFICATION_TYPE_CRITICAL, $module, $id, $display_text, $extended_text, $link, $reset, $candelete);232 }233 function add_security($module, $id, $display_text, $extended_text="", $link="", $reset=true, $candelete=false) {234 $this->_add_type(NOTIFICATION_TYPE_SECURITY, $module, $id, $display_text, $extended_text, $link, $reset, $candelete);235 }236 function add_update($module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=false) {237 $this->_add_type(NOTIFICATION_TYPE_UPDATE, $module, $id, $display_text, $extended_text, $link, $reset, $candelete);238 }239 function add_error($module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=false) {240 $this->_add_type(NOTIFICATION_TYPE_ERROR, $module, $id, $display_text, $extended_text, $link, $reset, $candelete);241 }242 function add_warning($module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=false) {243 $this->_add_type(NOTIFICATION_TYPE_WARNING, $module, $id, $display_text, $extended_text, $link, $reset, $candelete);244 }245 function add_notice($module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=true) {246 $this->_add_type(NOTIFICATION_TYPE_NOTICE, $module, $id, $display_text, $extended_text, $link, $reset, $candelete);247 }248 249 250 function list_critical($show_reset=false) {251 return $this->_list(NOTIFICATION_TYPE_CRITICAL, $show_reset);252 }253 function list_security($show_reset=false) {254 return $this->_list(NOTIFICATION_TYPE_SECURITY, $show_reset);255 }256 function list_update($show_reset=false) {257 return $this->_list(NOTIFICATION_TYPE_UPDATE, $show_reset);258 }259 function list_error($show_reset=false) {260 return $this->_list(NOTIFICATION_TYPE_ERROR, $show_reset);261 }262 function list_warning($show_reset=false) {263 return $this->_list(NOTIFICATION_TYPE_WARNING, $show_reset);264 }265 function list_notice($show_reset=false) {266 return $this->_list(NOTIFICATION_TYPE_NOTICE, $show_reset);267 }268 function list_all($show_reset=false) {269 return $this->_list("", $show_reset);270 }271 272 273 function reset($module, $id) {274 $module = q($module);275 $id = q($id);276 277 $sql = "UPDATE notifications SET reset = 1 WHERE module = $module AND id = $id";278 sql($sql);279 }280 281 function delete($module, $id) {282 $module = q($module);283 $id = q($id);284 285 $sql = "DELETE FROM notifications WHERE module = $module AND id = $id";286 sql($sql);287 }288 289 function safe_delete($module, $id) {290 $module = q($module);291 $id = q($id);292 293 $sql = "DELETE FROM notifications WHERE module = $module AND id = $id AND candelete = 1";294 sql($sql);295 }296 297 /* Internal functions298 */299 300 function _add_type($level, $module, $id, $display_text, $extended_text="", $link="", $reset=false, $candelete=false) {301 if ($this->not_loaded) {302 $this->notification_table = $this->_list("",true);303 $this->not_loaded = false;304 }305 306 $existing_row = false;307 foreach ($this->notification_table as $row) {308 if ($row['module'] == $module && $row['id'] == $id ) {309 $existing_row = $row;310 break;311 }312 }313 // Found an existing row - check if anything changed or if we are suppose to reset it314 //315 $candelete = $candelete ? 1 : 0;316 if ($existing_row) {317 318 if (($reset && $existing_row['reset'] == 1) || $existing_row['level'] != $level || $existing_row['display_text'] != $display_text || $existing_row['extended_text'] != $extended_text || $existing_row['link'] != $link || $existing_row['candelete'] == $candelete) {319 320 // If $reset is set to the special case of PASSIVE then the updates will not change it's value in an update321 //322 $reset_value = ($reset == 'PASSIVE') ? $existing_row['reset'] : 0;323 324 $module = q($module);325 $id = q($id);326 $level = q($level);327 $display_text = q($display_text);328 $extended_text = q($extended_text);329 $link = q($link);330 $now = time();331 $sql = "UPDATE notifications SET332 level = $level,333 display_text = $display_text,334 extended_text = $extended_text,335 link = $link,336 reset = $reset_value,337 candelete = $candelete,338 timestamp = $now339 WHERE module = $module AND id = $id340 ";341 sql($sql);342 343 // TODO: I should really just add this to the internal cache, but really344 // how often does this get called that if is a big deal.345 $this->not_loaded = true;346 }347 } else {348 // No existing row so insert this new one349 //350 $now = time();351 $module = q($module);352 $id = q($id);353 $level = q($level);354 $display_text = q($display_text);355 $extended_text = q($extended_text);356 $link = q($link);357 $sql = "INSERT INTO notifications358 (module, id, level, display_text, extended_text, link, reset, candelete, timestamp)359 VALUES360 ($module, $id, $level, $display_text, $extended_text, $link, 0, $candelete, $now)361 ";362 sql($sql);363 364 // TODO: I should really just add this to the internal cache, but really365 // how often does this get called that if is a big deal.366 $this->not_loaded = true;367 }368 }369 370 function _list($level, $show_reset=false) {371 372 $level = q($level);373 $where = array();374 375 if (!$show_reset) {376 $where[] = "reset = 0";377 }378 379 switch ($level) {380 case NOTIFICATION_TYPE_CRITICAL:381 case NOTIFICATION_TYPE_SECURITY:382 case NOTIFICATION_TYPE_UPDATE:383 case NOTIFICATION_TYPE_ERROR:384 case NOTIFICATION_TYPE_WARNING:385 case NOTIFICATION_TYPE_NOTICE:386 $where[] = "level = $level ";387 break;388 default:389 }390 $sql = "SELECT * FROM notifications ";391 if (count($where)) {392 $sql .= " WHERE ".implode(" AND ", $where);393 }394 $sql .= " ORDER BY level, module";395 396 $list = sql($sql,"getAll",DB_FETCHMODE_ASSOC);397 return $list;398 }399 /* Returns the number of active notifications400 */401 function get_num_active() {402 $sql = "SELECT COUNT(id) FROM notifications WHERE reset = 0";403 return sql($sql,'getOne');404 }405 }406 407 class cronmanager {408 /**409 * note: time is the hour time of day a job should run, -1 indicates don't care410 */411 412 function &create(&$db) {413 static $obj;414 if (!isset($obj)) {415 $obj = new cronmanager($db);416 }417 return $obj;418 }419 420 function cronmanager(&$db) {421 $this->_db =& $db;422 }423 424 function save_email($address) {425 $address = q($address);426 sql("DELETE FROM admin WHERE variable = 'email'");427 sql("INSERT INTO admin (variable, value) VALUES ('email', $address)");428 }429 430 function get_email() {431 $sql = "SELECT value FROM admin WHERE variable = 'email'";432 return sql($sql, 'getOne');433 }434 435 function save_hash($id, &$string) {436 $hash = md5($string);437 $id = q($id);438 sql("DELETE FROM admin WHERE variable = $id");439 sql("INSERT INTO admin (variable, value) VALUE ($id, '$hash')");440 }441 442 function check_hash($id, &$string) {443 $id = q($id);444 $sql = "SELECT value FROM admin WHERE variable = $id LIMIT 1";445 $hash = sql($sql, "getOne");446 return ($hash == md5($string));447 }448 449 function enable_updates($freq=24) {450 global $amp_conf;451 452 $night_time = array(19,20,21,22,23,0,1,2,3,4,5);453 $run_time = $night_time[rand(0,10)];454 $command = $amp_conf['AMPBIN']."/module_admin listonline";455 $lasttime = 0;456 457 $sql = "SELECT * FROM cronmanager WHERE module = 'module_admin' AND id = 'UPDATES'";458 $result = sql($sql, "getAll",DB_FETCHMODE_ASSOC);459 if (count($result)) {460 $sql = "UPDATE cronmanager SET461 freq = '$freq',462 command = '$command'463 WHERE464 module = 'module_admin' AND id = 'UPDATES'465 ";466 } else {467 $sql = "INSERT INTO cronmanager468 (module, id, time, freq, lasttime, command)469 VALUES470 ('module_admin', 'UPDATES', '$run_time', $freq, 0, '$command')471 ";472 }473 sql($sql);474 }475 476 function disable_updates() {477 sql("DELETE FROM cronmanager WHERE module = 'module_admin' AND id = 'UPDATES'");478 }479 480 function updates_enabled() {481 $results = sql("SELECT module, id FROM cronmanager WHERE module = 'module_admin' AND id = 'UPDATES'",'getAll');482 return count($results);483 }484 485 /** run_jobs()486 * select all entries that need to be run now and run them, then update the times.487 *488 * 1. select all entries489 * 2. foreach entry, if its paramters indicate it should be run, then run it and490 * update it was run in the time stamp.491 */492 function run_jobs() {493 494 $errors = 0;495 $error_arr = array();496 497 $now = time();498 $jobs = sql("SELECT * FROM cronmanager","getAll", DB_FETCHMODE_ASSOC);499 foreach ($jobs as $job) {500 $nexttime = $job['lasttime'] + $job['freq']*3600;501 if ($nexttime <= $now) {502 if ($job['time'] >= 0 && $job['time'] < 24) {503 $date_arr = getdate($now);504 // Now if lasttime is 0, then we want this kicked off at the proper hour505 // after wich the frequencey will set the pace for same time each night506 //507 if (($date_arr['hours'] != $job['time']) && !$job['lasttime']) {508 continue;509 }510 }511 } else {512 // no need to run job, time is not up yet513 continue;514 }515 // run the job516 exec($job['command'],$job_out,$ret);517 if ($ret) {518 $errors++;519 $error_arr[] = array($job['command'],$ret);520 521 // If there where errors, let's print them out in case the script is being debugged or running522 // from cron which will then put the errors out through the cron system.523 //524 foreach ($job_out as $line) {525 echo $line."\n";526 }527 } else {528 $module = $job['module'];529 $id = $job['id'];530 $sql = "UPDATE cronmanager SET lasttime = $now WHERE module = '$module' AND id = '$id'";531 sql($sql);532 }533 }534 if ($errors) {535 $nt =& notifications::create($db);536 $text = sprintf(_("Cronmanager encountered %s Errors"),$errors);537 $extext = _("The following commands failed with the listed error");538 foreach ($error_arr as $item) {539 $extext .= "<br>".$item[0]." (".$item[1].")";540 }541 $nt->add_error('cron_manager', 'EXECFAIL', $text, $extext, '', true, true);542 }543 }544 819 } 545 820 … … 946 1221 } 947 1222 1223 // returns true if extension is within allowed range 1224 function checkRange($extension){ 1225 $low = isset($_SESSION["AMP_user"]->_extension_low)?$_SESSION["AMP_user"]->_extension_low:''; 1226 $high = isset($_SESSION["AMP_user"]->_extension_high)?$_SESSION["AMP_user"]->_extension_high:''; 1227 1228 if ((($extension >= $low) && ($extension <= $high)) || ($low == '' && $high == '')) 1229 return true; 1230 else 1231 return false; 1232 } 1233 948 1234 function getAmpAdminUsers() { 949 1235 global $db; … … 980 1266 } 981 1267 982 class ampuser {983 var $username;984 var $_password;985 var $_extension_high;986 var $_extension_low;987 var $_deptname;988 var $_sections;989 990 function ampuser($username) {991 $this->username = $username;992 if ($user = getAmpUser($username)) {993 $this->_password = $user["password"];994 $this->_extension_high = $user["extension_high"];995 $this->_extension_low = $user["extension_low"];996 $this->_deptname = $user["deptname"];997 $this->_sections = $user["sections"];998 } else {999 // user doesn't exist1000 $this->_password = false;1001 $this->_extension_high = "";1002 $this->_extension_low = "";1003 $this->_deptname = "";1004 $this->_sections = array();1005 }1006 }1007 1008 /** Give this user full admin access1009 */1010 function setAdmin() {1011 $this->_extension_high = "";1012 $this->_extension_low = "";1013 $this->_deptname = "";1014 $this->_sections = array("*");1015 }1016 1017 function checkPassword($password) {1018 // strict checking so false will never match1019 return ($this->_password === $password);1020 }1021 1022 function checkSection($section) {1023 // if they have * then it means all sections1024 return in_array("*", $this->_sections) || in_array($section, $this->_sections);1025 }1026 }1027 1028 // returns true if extension is within allowed range1029 function checkRange($extension){1030 $low = isset($_SESSION["AMP_user"]->_extension_low)?$_SESSION["AMP_user"]->_extension_low:'';1031 $high = isset($_SESSION["AMP_user"]->_extension_high)?$_SESSION["AMP_user"]->_extension_high:'';1032 1033 if ((($extension >= $low) && ($extension <= $high)) || ($low == '' && $high == ''))1034 return true;1035 else1036 return false;1037 }1038 1039 1268 // returns true if department string matches dept for this user 1040 1269 function checkDept($dept){ … … 1045 1274 else 1046 1275 return false; 1276 } 1277 1278 /** 1279 * returns true if asterisk is running with chan_dahdi 1280 * 1281 * @return bool 1282 */ 1283 function ast_with_dahdi() { 1284 global $version; 1285 global $astman; 1286 global $amp_conf; 1287 1288 if (!$amp_conf['ZAP2DAHDICOMPAT']) { 1289 return false; 1290 } 1291 1292 if (empty($version)) { 1293 $engine_info = engine_getinfo(); 1294 $version = $engine_info['version']; 1295 } 1296 1297 if (version_compare($version, '1.4', 'ge') && $amp_conf['AMPENGINE'] == 'asterisk') { 1298 if (isset($astman) && $astman->connected()) { 1299 $response = $astman->send_request('Command', array('Command' => 'module show like chan_dahdi')); 1300 if (preg_match('/1 modules loaded/', $response['data'])) { 1301 return true; 1302 } 1303 } 1304 } 1305 return false; 1047 1306 } 1048 1307 … … 1084 1343 } 1085 1344 1086 1087 1345 if (!function_exists('version_compare_freepbx')) { 1088 1346 /* verison_compare that works with freePBX version numbers … … 1099 1357 } 1100 1358 1101 1102 1359 /* queries database using PEAR. 1103 1360 * $type can be query, getAll, getRow, getCol, getOne, etc … … 1122 1379 * @return string A value that can be safely inserted into an SQL query 1123 1380 */ 1124 function q(&$value) { 1381 function q(&$value) { 1125 1382 global $db; 1126 1383 return $db->quoteSmart($value); … … 1129 1386 // sql text formatting -- couldn't see that one was available already 1130 1387 function sql_formattext($txt) { 1388 global $db; 1131 1389 if (isset($txt)) { 1132 $fmt = str_replace("'", "''",$txt);1390 $fmt = $db->escapeSimple($txt); 1133 1391 $fmt = "'" . $fmt . "'"; 1134 1392 } else { … … 1138 1396 return $fmt; 1139 1397 } 1140 1141 1398 1142 1399 function die_freepbx($text, $extended_text="", $type="FATAL") { … … 1395 1652 } 1396 1653 } 1397 1398 1654 1399 1655 /** Recursively read voicemail.conf (and any included files) … … 1672 1928 fclose($fd); 1673 1929 } 1674 1675 } 1676 1930 } 1677 1931 1678 1932 // $goto is the current goto destination setting … … 1680 1934 // esnure that any form that includes this calls the setDestinations() javascript function on submit. 1681 1935 // ie: if the form name is "edit", and drawselects has been called with $i=2 then use onsubmit="setDestinations(edit,2)" 1682 function drawselects($goto,$i,$show_custom=false) { 1936 function drawselects($goto,$i,$show_custom=false) { 1683 1937 global $tabindex; 1684 1938 … … 1779 2033 } 1780 2034 1781 1782 2035 /* below are legacy functions required to allow pre 2.0 modules to function (ie: interact with 'extensions' table) */ 1783 2036 … … 1804 2057 } 1805 2058 1806 1807 2059 //get args for specified exten and priority - primarily used to grab goto destination 1808 2060 function legacy_args_get($exten,$priority,$context) { … … 1815 2067 /* end legacy functions */ 1816 2068 1817 /* Usage1818 Grab some XML data, either from a file, URL, etc. however you want. Assume storage in $strYourXML;1819 1820 $xml = new xml2Array($strYourXML);1821 xml array is in $xml->data;1822 This is basically an array version of the XML data (no attributes), striaght-up. If there are1823 multiple items with the same name, they are split into a numeric sub-array,1824 eg, <items><item test="123">foo</item><item>bar</item></items>1825 becomes: array('item' => array(0=>array('item'=>'foo'), 1=>array('item'=>'foo'))1826 attributes are in $xml->attributes;1827 These are stored with xpath type paths, as $xml->attributes['/items/item/0']["test"] == "123"1828 1829 1830 Other way (still works, but not as nice):1831 1832 $objXML = new xml2Array();1833 $arrOutput = $objXML->parse($strYourXML);1834 print_r($arrOutput); //print it out, or do whatever!1835 1836 */1837 1838 class xml2Array {1839 var $arrOutput = array();1840 var $resParser;1841 var $strXmlData;1842 1843 var $attributes;1844 var $data;1845 1846 function xml2Array($strInputXML = false) {1847 if (!empty($strInputXML)) {1848 $this->data = $this->parseAdvanced($strInputXML);1849 }1850 }1851 1852 function parse($strInputXML) {1853 1854 $this->resParser = xml_parser_create ();1855 xml_set_object($this->resParser,$this);1856 xml_set_element_handler($this->resParser, "tagOpen", "tagClosed");1857 1858 xml_set_character_data_handler($this->resParser, "tagData");1859 1860 $this->strXmlData = xml_parse($this->resParser,$strInputXML );1861 if(!$this->strXmlData) {1862 die_freepbx(sprintf("XML error: %s at line %d",1863 xml_error_string(xml_get_error_code($this->resParser)),1864 xml_get_current_line_number($this->resParser)));1865 }1866 1867 xml_parser_free($this->resParser);1868 1869 return $this->arrOutput;1870 }1871 function tagOpen($parser, $name, $attrs) {1872 $tag=array("name"=>$name,"attrs"=>$attrs);1873 @array_push($this->arrOutput,$tag);1874 }1875 1876 function tagData($parser, $tagData) {1877 if(trim($tagData)) {1878 if(isset($this->arrOutput[count($this->arrOutput)-1]['tagData'])) {1879 $this->arrOutput[count($this->arrOutput)-1]['tagData'] .= "\n".$tagData;1880 }1881 else {1882 $this->arrOutput[count($this->arrOutput)-1]['tagData'] = $tagData;1883 }1884 }1885 }1886 1887 function tagClosed($parser, $name) {1888 @$this->arrOutput[count($this->arrOutput)-2]['children'][] = $this->arrOutput[count($this->arrOutput)-1];1889 array_pop($this->arrOutput);1890 }1891 1892 function recursive_parseLevel($items, &$attrs, $path = "") {1893 $array = array();1894 foreach (array_keys($items) as $idx) {1895 @$items[$idx]['name'] = strtolower($items[$idx]['name']);1896 1897 $multi = false;1898 if (isset($array[ $items[$idx]['name'] ])) {1899 // this child is already set, so we're adding multiple items to an array1900 1901 if (!is_array($array[ $items[$idx]['name'] ]) || !isset($array[ $items[$idx]['name'] ][0])) {1902 // hasn't already been made into a numerically-indexed array, so do that now1903 // we're basically moving the current contents of this item into a 1-item array (at the1904 // original location) so that we can add a second item in the code below1905 $array[ $items[$idx]['name'] ] = array( $array[ $items[$idx]['name'] ] );1906 1907 if (isset($attrs[ $path.'/'.$items[$idx]['name'] ])) {1908 // move the attributes to /01909 $attrs[ $path.'/'.$items[$idx]['name'].'/0' ] = $attrs[ $path.'/'.$items[$idx]['name'] ];1910 unset($attrs[ $path.'/'.$items[$idx]['name'] ]);1911 }1912 }1913 $multi = true;1914 }1915 1916 if ($multi) {1917 $newitem = &$array[ $items[$idx]['name'] ][];1918 } else {1919 $newitem = &$array[ $items[$idx]['name'] ];1920 }1921 1922 1923 if (isset($items[$idx]['children']) && is_array($items[$idx]['children'])) {1924 $newitem = $this->recursive_parseLevel($items[$idx]['children'], $attrs, $path.'/'.$items[$idx]['name']);1925 } else if (isset($items[$idx]['tagData'])) {1926 $newitem = $items[$idx]['tagData'];1927 } else {1928 $newitem = false;1929 }1930 1931 if (isset($items[$idx]['attrs']) && is_array($items[$idx]['attrs']) && count($items[$idx]['attrs'])) {1932 $attrpath = $path.'/'.$items[$idx]['name'];1933 if ($multi) {1934 $attrpath .= '/'.(count($array[ $items[$idx]['name'] ])-1);1935 }1936 foreach ($items[$idx]['attrs'] as $name=>$value) {1937 $attrs[ $attrpath ][ strtolower($name) ] = $value;1938 }1939 }1940 }1941 return $array;1942 }1943 1944 function parseAdvanced($strInputXML) {1945 $array = $this->parse($strInputXML);1946 $this->attributes = array();1947 return $this->data = $this->recursive_parseLevel($array, $this->attributes);1948 }1949 }1950 1951 1952 /*1953 Return a much more manageable assoc array with module data.1954 */1955 class xml2ModuleArray extends xml2Array {1956 function parseModulesXML($strInputXML) {1957 $array = $this->parseAdvanced($strInputXML);1958 if (isset($array['xml'])) {1959 foreach ($array['xml'] as $key=>$module) {1960 if ($key == 'module') {1961 // copy the structure verbatim1962 $modules[ $module['name'] ] = $module;1963 }1964 }1965 }1966 1967 // if you are confused about what's happening below, uncomment this why we do it1968 // echo "<pre>"; print_r($arrOutput); echo "</pre>";1969 1970 // ignore the regular xml garbage ([0]['children']) & loop through each module1971 if(!is_array($arrOutput[0]['children'])) return false;1972 foreach($arrOutput[0]['children'] as $module) {1973 if(!is_array($module['children'])) return false;1974 // loop through each modules's tags1975 foreach($module['children'] as $modTags) {1976 if(isset($modTags['children']) && is_array($modTags['children'])) {1977 $$modTags['name'] = $modTags['children'];1978 // loop if there are children (menuitems and requirements)1979 foreach($modTags['children'] as $subTag) {1980 $subTags[strtolower($subTag['name'])] = $subTag['tagData'];1981 }1982 $$modTags['name'] = $subTags;1983 unset($subTags);1984 } else {1985 // create a variable for each tag we find1986 $$modTags['name'] = $modTags['tagData'];1987 }1988 1989 }1990 // now build our return array1991 $arrModules[$RAWNAME]['rawname'] = $RAWNAME; // This has to be set1992 $arrModules[$RAWNAME]['displayName'] = $NAME; // This has to be set1993 $arrModules[$RAWNAME]['version'] = $VERSION; // This has to be set1994 $arrModules[$RAWNAME]['type'] = isset($TYPE)?$TYPE:'setup';1995 $arrModules[$RAWNAME]['category'] = isset($CATEGORY)?$CATEGORY:'Unknown';1996 $arrModules[$RAWNAME]['info'] = isset($INFO)?$INFO:'http://www.freepbx.org/wiki/'.$RAWNAME;1997 $arrModules[$RAWNAME]['location'] = isset($LOCATION)?$LOCATION:'local';1998 $arrModules[$RAWNAME]['items'] = isset($MENUITEMS)?$MENUITEMS:null;1999 $arrModules[$RAWNAME]['requirements'] = isset($REQUIREMENTS)?$REQUIREMENTS:null;2000 $arrModules[$RAWNAME]['md5sum'] = isset($MD5SUM)?$MD5SUM:null;2001 //print_r($arrModules);2002 //unset our variables2003 unset($NAME);2004 unset($VERSION);2005 unset($TYPE);2006 unset($CATEGORY);2007 unset($AUTHOR);2008 unset($EMAIL);2009 unset($LOCATION);2010 unset($MENUITEMS);2011 unset($REQUIREMENTS);2012 unset($MD5SUM);2013 }2014 //echo "<pre>"; print_r($arrModules); echo "</pre>";2015 2016 return $arrModules;2017 }2018 }2019 2069 2020 2070 function get_headers_assoc($url ) { … … 2050 2100 } 2051 2101 2052 2053 2054 class moduleHook { 2055 var $hookHtml = ''; 2056 var $arrHooks = array(); 2057 2058 function install_hooks($viewing_itemid,$target_module,$target_menuid = '') { 2059 global $active_modules; 2060 // loop through all active modules 2061 foreach($active_modules as $this_module) { 2062 // look for requested hooks for $module 2063 // ie: findme_hook_extensions() 2064 $funct = $this_module['rawname'] . '_hook_' . $target_module; 2065 if( function_exists( $funct ) ) { 2066 // execute the function, appending the 2067 // html output to that of other hooking modules 2068 if ($hookReturn = $funct($target_menuid, $viewing_itemid)) { 2069 $this->hookHtml .= $hookReturn; 2070 } 2071 // remember who installed hooks 2072 // we need to know this for processing form vars 2073 $this->arrHooks[] = $this_module['rawname']; 2074 } 2075 } 2076 } 2077 2078 // process the request from the module we hooked 2079 function process_hooks($viewing_itemid, $target_module, $target_menuid, $request) { 2080 if(is_array($this->arrHooks)) { 2081 foreach($this->arrHooks as $hookingMod) { 2082 // check if there is a processing function 2083 $funct = $hookingMod . '_hookProcess_' . $target_module; 2084 if( function_exists( $funct ) ) { 2085 $funct($viewing_itemid, $request); 2086 } 2087 } 2088 } 2089 } 2090 } 2091 2092 function execSQL( $file ) 2093 { 2102 function execSQL( $file ) { 2094 2103 global $db; 2095 2104 $data = null; … … 2115 2124 _module_runscripts($moddir, $type); 2116 2125 } 2117 2118 2126 2119 2127 /** Replaces variables in a string with the values from ampconf … … 2158 2166 $got_new = false; 2159 2167 2160 //this should be in an upgrade file ... putting here for now.2161 /*2162 sql('CREATE TABLE IF NOT EXISTS module_xml (time INT NOT NULL , data BLOB NOT NULL) TYPE = MYISAM ;');2163 */2164 2165 2168 $result = sql("SELECT * FROM module_xml WHERE id = 'xml'",'getRow',DB_FETCHMODE_ASSOC); 2166 2169 $data = $result['data']; … … 2216 2219 } 2217 2220 2218 //echo time() - $result['time'];2219 2221 $parser = new xml2ModuleArray($data); 2220 2222 $xmlarray = $parser->parseAdvanced($data); 2221 //$modules = $xmlarray['XML']['MODULE'];2222 2223 2223 2224 if ($got_new) { … … 2225 2226 } 2226 2227 2227 2228 //echo "<hr>Raw XML Data<pre>"; print_r(htmlentities($data)); echo "</pre>";2229 //echo "<hr>XML2ARRAY<pre>"; print_r($xmlarray); echo "</pre>";2230 2231 2232 2228 if (isset($xmlarray['xml']['module'])) { 2233 2229 … … 2240 2236 return null; 2241 2237 } else { 2242 2243 2244 2238 $modules = array(); 2245 2239 foreach ($xmlarray['xml']['module'] as $mod) { … … 2688 2682 } 2689 2683 2690 2691 2684 /** Enables a module 2692 2685 * @param string The name of the module to enable … … 2984 2977 return true; 2985 2978 } 2986 2987 2979 2988 2980 /** Installs or upgrades a module from it's directory … … 3188 3180 } 3189 3181 3190 3191 3182 /** Internal use only */ 3192 3183 function _module_setenabled($modulename, $enabled) { … … 3222 3213 if (isset($xmlarray['module'])) { 3223 3214 // add a couple fields first 3215 $xmlarray['module']['name'] = str_replace("\n&\n","&",$xmlarray['module']['name']); 3224 3216 $xmlarray['module']['displayname'] = $xmlarray['module']['name']; 3217 if (isset($xmlarray['module']['description'])) { 3218 $xmlarray['module']['description'] = trim(str_replace("\n","",$xmlarray['module']['description'])); 3219 } 3225 3220 if (isset($xmlarray['module']['menuitems'])) { 3226 3221 3227 3222 foreach ($xmlarray['module']['menuitems'] as $item=>$displayname) { 3223 $displayname = str_replace("\n&\n","&",$displayname); 3224 $xmlarray['module']['menuitems'][$item] = $displayname; 3228 3225 $path = '/module/menuitems/'.$item; 3229 3226 3230 3227 // find category 3231 3228 if (isset($parser->attributes[$path]['category'])) { 3232 $category = $parser->attributes[$path]['category'];3229 $category = str_replace("\n&\n","&",$parser->attributes[$path]['category']); 3233 3230 } else if (isset($xmlarray['module']['category'])) { 3234 $category = $xmlarray['module']['category'];3231 $category = str_replace("\n&\n","&",$xmlarray['module']['category']); 3235 3232 } else { 3236 3233 $category = 'Basic'; … … 3285 3282 } 3286 3283 } 3287 3288 3284 return $xmlarray['module']; 3289 3285 } … … 3372 3368 return true; 3373 3369 } 3370 3374 3371 function _modules_doinclude($filename, $modulename) { 3375 3372 // we provide the following variables to the included file (as well as $filename and $modulename) … … 3380 3377 } 3381 3378 } 3382 3383 3379 3384 3380 /* module_get_annoucements() … … 3390 3386 function module_get_annoucements() { 3391 3387 global $db; 3388 global $amp_conf; 3392 3389 $firstinstall=false; 3393 3390 $type=null; … … 3440 3437 } 3441 3438 3439 $fn = "http://mirror.freepbx.org/version-".getversion().".html".$options; 3442 3440 if (!$amp_conf['MODULEADMINWGET']) { 3443 $announcement = @ file_get_contents( "http://mirror.freepbx.org/version-".getversion().".html".$options);3441 $announcement = @ file_get_contents($fn); 3444 3442 } else { 3445 3443 $announcement = ''; … … 3451 3449 return $announcement; 3452 3450 } 3453 3454 3451 3455 3452 /* Assumes properly formated input, which is ok since … … 3577 3574 $notifications->delete('freepbx', 'modules_broken'); 3578 3575 } 3576 } 3577 3578 /** Log a debug message to a debug file 3579 * @param string debug message to be printed 3580 * @param string optional mode, default 'a' 3581 * @param string optinal filename, default /tmp/freepbx_debug.log 3582 */ 3583 function freepbx_debug($string, $option='a', $filename='/tmp/freepbx_debug.log') { 3584 $fh = fopen($filename,$option); 3585 fwrite($fh,$string."\n"); 3586 fclose($fh); 3579 3587 } 3580 3588 freepbx/trunk/amp_conf/htdocs/admin/page.modules.php
r6575 r6600 13 13 } 14 14 15 16 15 $extdisplay = isset($_REQUEST['extdisplay'])?$_REQUEST['extdisplay']:''; 16 17 17 // can't go online if external management is on 18 18 $online = (isset($_REQUEST['online']) && !EXTERNAL_PACKAGE_MANAGEMENT) ? $_REQUEST['online'] : false; 19 19 20 // fix php errors from undefined variable. Not sure if we can just change the reference below to use 20 21 // online since it changes values so just setting to what we decided it is here. 21 22 $_REQUEST['online'] = $online ? 1 : 0; 23 22 24 $moduleaction = isset($_REQUEST['moduleaction'])?$_REQUEST['moduleaction']:false; 23 25 /* … … 36 38 $freepbx_help_url = "http://www.freepbx.org/freepbx-help-system?freepbx_version=".urlencode($freepbx_version); 37 39 38 function pageReload(){39 return "";40 //return "<script language=\"Javascript\">document.location='".$_SERVER['PHP_SELF']."?".$_SERVER['QUERY_STRING']."&foo=".rand()."'</script>";41 }42 43 44 40 if (!$quietmode) { 45 41 ?> … … 54 50 } 55 51 } 56 57 52 function check_upgrade_all() { 58 53 var re = /^moduleaction\[([a-z0-9_\-]+)\]$/; … … 68 63 } 69 64 } 70 71 65 function check_download_all() { 72 66 var re = /^moduleaction\[([a-z0-9_\-]+)\]$/; … … 82 76 } 83 77 } 84 85 86 78 function showhide_upgrades() { 87 79 var upgradesonly = document.getElementById('show_upgradable_only').checked; 88 89 80 var module_re = /^module_([a-z0-9_]+)$/; // regex to match a module element id 90 81 var cat_re = /^category_([a-zA-Z0-9_]+)$/; // regex to match a category element id 91 92 82 var elements = document.getElementById('modulelist').getElementsByTagName('li'); 93 94 83 // loop through all modules, check if there is an upgrade_<module> radio box 95 84 for(i=0; i<elements.length; i++) { … … 101 90 } 102 91 } 103 104 105 106 92 // hide category headings that don't have any visible modules 107 108 93 var elements = document.getElementById('modulelist').getElementsByTagName('div'); 109 94 // loop through category items … … 120 105 } 121 106 } 122 123 107 document.getElementById(elements[i].id).style.display = display ? 'block' : 'none'; 124 108 } 125 109 } 126 127 } 128 110 } 129 111 function process_module_actions(actions) { 130 112 freepbx_modal_show('moduleBox'); … … 142 124 } 143 125 } 144 145 126 </script> 146 127 <?php … … 155 136 <?php 156 137 } 157 158 138 159 139 $modules_local = module_getinfo(false,false,true); … … 204 184 } 205 185 186 //-------------------------------------------------------------------------------------------------------- 187 switch ($extdisplay) { // process, confirm, or nothing 188 case 'process': 189 echo "<div id=\"moduleBoxContents\">"; 190 echo "<h4>"._("Please wait while module actions are performed")."</h4>\n"; 191 echo "<div id=\"moduleprogress\">"; 192 193 // stop output buffering, and send output 194 @ ob_end_flush(); 195 flush(); 196 foreach ($moduleaction as $modulename => $action) { 197 $didsomething = true; // set to false in default clause of switch() below.. 198 199 switch ($action) { 200 case 'upgrade': 201 case 'downloadinstall': 202 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 203 echo sprintf(_('Downloading %s'), $modulename).' <span id="downloadprogress_'.$modulename.'"></span>'; 204 if (is_array($errors = module_download($modulename, false, 'download_progress'))) { 205 echo '<span class="error">'.sprintf(_("Error(s) downloading %s"),$modulename).': '; 206 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 207 echo '</span>'; 208 } else { 209 if (is_array($errors = module_install($modulename))) { 210 echo '<span class="error">'.sprintf(_("Error(s) installing %s"),$modulename).': '; 211 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 212 echo '</span>'; 213 } else { 214 echo '<span class="success">'.sprintf(_("%s installed successfully"),$modulename).'</span>'; 215 } 216 } 217 } 218 break; 219 case 'install': 220 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 221 if (is_array($errors = module_install($modulename))) { 222 echo '<span class="error">'.sprintf(_("Error(s) installing %s"),$modulename).': '; 223 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 224 echo '</span>'; 225 } else { 226 echo '<span class="success">'.sprintf(_("%s installed successfully"),$modulename).'</span>'; 227 } 228 } 229 break; 230 case 'enable': 231 if (is_array($errors = module_enable($modulename))) { 232 echo '<span class="error">'.sprintf(_("Error(s) enabling %s"),$modulename).': '; 233 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 234 echo '</span>'; 235 } else { 236 echo '<span class="success">'.sprintf(_("%s enabled successfully"),$modulename).'</span>'; 237 } 238 break; 239 case 'disable': 240 if (is_array($errors = module_disable($modulename))) { 241 echo '<span class="error">'.sprintf(_("Error(s) disabling %s"),$modulename).': '; 242 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 243 echo '</span>'; 244 } else { 245 echo '<span class="success">'.sprintf(_("%s disabled successfully"),$modulename).'</span>'; 246 } 247 break; 248 case 'uninstall': 249 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 250 if (is_array($errors = module_uninstall($modulename))) { 251 echo '<span class="error">'.sprintf(_("Error(s) uninstalling %s"),$modulename).': '; 252 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 253 echo '</span>'; 254 } else { 255 echo '<span class="success">'.sprintf(_("%s uninstalled successfully"),$modulename).'</span>'; 256 } 257 } 258 break; 259 default: 260 // just so we don't send an <hr> and flush() 261 $didsomething = false; 262 } 263 264 if ($didsomething) { 265 echo "<hr /><br />"; 266 flush(); 267 } 268 } 269 echo "</div>"; 270 if ($quietmode) { 271 echo "\t<a href=\"#\" onclick=\"parent.close_module_actions(true);\" />"._("Return")."</a>"; 272 } else { 273 echo "\t<input type=\"button\" value=\""._("Return")."\" onclick=\"location.href = 'config.php?display=modules&type=tool&online=".($_REQUEST['online']?1:0)."';\" />"; 274 echo "</div>"; 275 } 276 break; 277 case 'confirm': 278 ksort($moduleaction); 279 280 echo "<form name=\"modulesGUI\" action=\"config.php\" method=\"post\">"; 281 echo "<input type=\"hidden\" name=\"display\" value=\"".$display."\" />"; 282 echo "<input type=\"hidden\" name=\"type\" value=\"".$type."\" />"; 283 echo "<input type=\"hidden\" name=\"online\" value=\"".$online."\" />"; 284 echo "<input type=\"hidden\" name=\"extdisplay\" value=\"process\" />"; 285 286 echo "\t<script type=\"text/javascript\"> var moduleActions = new Array(); </script>\n"; 287 288 $actionstext = array(); 289 $errorstext = array(); 290 foreach ($moduleaction as $module => $action) { 291 $text = false; 292 $skipaction = false; 293 294 // make sure name is set. This is a problem for broken modules 295 if (!isset($modules[$module]['name'])) { 296 $modules[$module]['name'] = $module; 297 } 298 299 switch ($action) { 300 case 'upgrade': 301 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 302 if (is_array($errors = module_checkdepends($modules_online[$module]))) { 303 $skipaction = true; 304 $errorstext[] = sprintf(_("%s cannot be upgraded: %s Please try again after the dependencies have been installed."), 305 $modules[$module]['name'], 306 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 307 } else { 308 $actionstext[] = sprintf(_("%s %s will be upgraded to online version %s"), $modules[$module]['name'], $modules[$module]['dbversion'], $modules_online[$module]['version']); 309 } 310 } 311 break; 312 case 'downloadinstall': 313 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 314 if (is_array($errors = module_checkdepends($modules_online[$module]))) { 315 $skipaction = true; 316 $errorstext[] = sprintf(_("%s cannot be installed: %s Please try again after the dependencies have been installed."), 317 $modules[$module]['name'], 318 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 319 } else { 320 $actionstext[] = sprintf(_("%s %s will be downloaded and installed"), $modules[$module]['name'], $modules_online[$module]['version']); 321 } 322 } 323 break; 324 case 'install': 325 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 326 if (is_array($errors = module_checkdepends($modules[$module]))) { 327 $skipaction = true; 328 $errorstext[] = sprintf((($modules[$module]['status'] == MODULE_STATUS_NEEDUPGRADE) ? _("%s cannot be upgraded: %s Please try again after the dependencies have been installed.") : _("%s cannot be installed: %s Please try again after the dependencies have been installed.") ), 329 $modules[$module]['name'], 330 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 331 } else { 332 if ($modules[$module]['status'] == MODULE_STATUS_NEEDUPGRADE) { 333 $actionstext[] = sprintf(_("%s %s will be upgraded to %s"), $modules[$module]['name'], $modules[$module]['dbversion'], $modules[$module]['version']); 334 } else { 335 $actionstext[] = sprintf(_("%s %s will be installed and enabled"), $modules[$module]['name'], $modules[$module]['version']); 336 } 337 } 338 } 339 break; 340 case 'enable': 341 if (is_array($errors = module_checkdepends($modules[$module]))) { 342 $skipaction = true; 343 $errorstext[] = sprintf(_("%s cannot be enabled: %s Please try again after the dependencies have been installed."), 344 $modules[$module]['name'], 345 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 346 } else { 347 $actionstext[] = sprintf(_("%s %s will be enabled"), $modules[$module]['name'], $modules[$module]['dbversion']); 348 } 349 break; 350 case 'disable': 351 if (is_array($errors = module_reversedepends($modules[$module]))) { 352 $skipaction = true; 353 $errorstext[] = sprintf(_("%s cannot be disabled because the following modules depend on it: %s Please disable those modules first then try again."), 354 $modules[$module]['name'], 355 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 356 } else { 357 $actionstext[] = sprintf(_("%s %s will be disabled"), $modules[$module]['name'], $modules[$module]['dbversion']); 358 } 359 break; 360 case 'uninstall': 361 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 362 if (is_array($errors = module_reversedepends($modules[$module]))) { 363 $skipaction = true; 364 $errorstext[] = sprintf(_("%s cannot be uninstalled because the following modules depend on it: %s Please disable those modules first then try again."), 365 $modules[$module]['name'], 366 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 367 } else { 368 $actionstext[] = sprintf(_("%s %s will be uninstalled"), $modules[$module]['name'], $modules[$module]['dbversion']); 369 } 370 } 371 break; 372 } 373 374 // If error above we skip this action so we can proceed with the others 375 // 376 if (!$skipaction) { //TODO 377 echo "\t<script type=\"text/javascript\"> moduleActions['".$module."'] = '".$action."'; </script>\n"; 378 } 379 } 380 381 // Write out the erros, if there are additional actions that can be accomplished list those next with the choice to 382 // process which will ignore the ones with errors but process the rest. 383 // 384 if (count($errorstext) > 0) { 385 echo "<h4>"._("Errors with selection:")."</h4>\n"; 386 echo "<ul>\n"; 387 foreach ($errorstext as $text) { 388 echo "\t<li>".$text."</li>\n"; 389 } 390 echo "</ul>"; 391 } 392 if (count($actionstext) > 0) { 393 if (count($errorstext) > 0) { 394 echo "<h4>"._("You may confirm the remaining selection and then try the again for the listed issues once the required dependencies have been met:")."</h4>\n"; 395 } else { 396 echo "<h4>"._("Please confirm the following actions:")."</h4>\n"; 397 } 398 echo "<ul>\n"; 399 foreach ($actionstext as $text) { 400 echo "\t<li>".$text."</li>\n"; 401 } 402 echo "</ul>"; 403 echo "\t<input type=\"button\" value=\"Confirm\" name=\"process\" onclick=\"process_module_actions(moduleActions);\" />"; 404 } else { 405 echo "<h4>"._("No actions to perform")."</h4>\n"; 406 echo "<p>"._("Please select at least one action to perform by clicking on the module, and selecting an action on the \"Action\" tab.")."</p>"; 407 } 408 echo "\t<input type=\"button\" value=\""._("Cancel")."\" onclick=\"location.href = 'config.php?display=modules&type=tool&online=".($_REQUEST['online']?1:0)."';\" />"; 409 echo "</form>"; 410 411 break; 412 case 'upload': 413 // display links 414 echo "<a href='config.php?display=modules&type=tool'>"._("Manage local modules")."</a>\n"; 415 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 416 echo " | <a class='info' href='config.php?display=modules&type=tool&online=1'>"._("Check for updates online")."<span>"._("Checking for updates will transmit your FreePBX and Asterisk version numbers along with a unique but random identifier. This is used to provide proper update information and track version usage to focus development and maintenance efforts. No private information is transmitted.")."</span></a>\n"; 417 } 418 419 if (isset($_FILES['uploadmod']) && !empty($_FILES['uploadmod']['name'])) { 420 // display upload link, only if they did upload something 421 echo " | <a href='config.php?display=modules&type=tool&extdisplay=upload'>"._("Upload module")."</a><br />\n"; 422 423 $res = module_handleupload($_FILES['uploadmod']); 424 if (is_array($res)) { 425 426 echo '<div class="error"><p>'; 427 echo sprintf(_('The following error(s) occurred processing the uploaded file: %s'), 428 '<ul><li>'.implode('</li><li>',$res).'</li></ul>'); 429 echo sprintf(_('You should fix the problem or select another file and %s.'), 430 "<a href='config.php?display=modules&type=tool'>"._("try again")."</a>"); 431 echo "</p></div>\n"; 432 } else { 433 434 echo "<p>".sprintf(_("Module uploaded successfully. You need to enable the module using %s to make it available."), 435 "<a href='config.php?display=modules&type=tool'>"._("local module administration")."</a>") 436 ."</p>\n"; 437 } 438 439 } else { 440 echo "<p>"._('You can upload a tar gzip file containing a FreePBX module from your local system. If a module with the same name already exists, it will be overwritten.')."</p>\n"; 441 442 echo "<form name=\"modulesGUI-upload\" action=\"config.php\" method=\"post\" enctype=\"multipart/form-data\">"; 443 echo "<input type=\"hidden\" name=\"display\" value=\"".$display."\" />"; 444 echo "<input type=\"hidden\" name=\"type\" value=\"".$type."\" />"; 445 echo "<input type=\"hidden\" name=\"extdisplay\" value=\"upload\" />"; 446 echo "<input type=\"file\" name=\"uploadmod\" /> "; 447 echo " <input type=\"submit\" value=\"Upload\" />"; 448 echo "</form>"; 449 } 450 451 break; 452 case 'online': 453 default: 454 455 uasort($modules, 'category_sort_callback'); 456 457 if ($online) { 458 // Check for annoucements such as security advisories, required updates, etc. 459 // 460 $announcements = module_get_annoucements(); 461 if (isset($announcements) && !empty($announcements)) { 462 echo "<div class='announcements'>$announcements</div>"; 463 } 464 465 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 466 echo "<a href='config.php?display=modules&type=tool&online=0'>"._("Manage local modules")."</a>\n"; 467 echo "<input type=\"checkbox\" id=\"show_upgradable_only\" onclick=\"showhide_upgrades();\" /><label for=\"show_upgradable_only\">"._("Show only upgradable")."</label>"; 468 } 469 } else { 470 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 471 echo "<a class='info' href='config.php?display=modules&type=tool&online=1'>"._("Check for updates online")."<span>"._("Checking for updates will transmit your FreePBX and Asterisk version numbers along with a unique but random identifier. This is used to provide proper update information and track version usage to focus development and maintenance efforts. No private information is transmitted.")."</span></a>\n"; 472 } 473 echo " | <a href='config.php?display=modules&type=tool&extdisplay=upload'>"._("Upload module")."</a><br />\n"; 474 } 475 476 echo "<form name=\"modulesGUI\" action=\"config.php\" method=\"post\">"; 477 echo "<input type=\"hidden\" name=\"display\" value=\"".$display."\" />"; 478 echo "<input type=\"hidden\" name=\"type\" value=\"".$type."\" />"; 479 echo "<input type=\"hidden\" name=\"online\" value=\"".$online."\" />"; 480 echo "<input type=\"hidden\" name=\"extdisplay\" value=\"confirm\" />"; 481 482 echo "<div class=\"modulebuttons\">"; 483 if ($online) { 484 echo "\t<a href=\"javascript:void(null);\" onclick=\"check_download_all();\">"._("Download all")."</a>"; 485 echo "\t<a href=\"javascript:void(null);\" onclick=\"check_upgrade_all();\">"._("Upgrade all")."</a>"; 486 } 487 echo "\t<input type=\"reset\" value=\""._("Reset")."\" />"; 488 echo "\t<input type=\"submit\" value=\""._("Process")."\" name=\"process\" />"; 489 echo "</div>"; 490 491 echo "<div id=\"modulelist\">\n"; 492 493 echo "\t<div id=\"modulelist-header\">"; 494 echo "\t\t<span class=\"modulename\">"._("Module")."</span>\n"; 495 echo "\t\t<span class=\"moduletype\">"._("Type")."</span>\n"; 496 echo "\t\t<span class=\"moduleversion\">"._("Version")."</span>\n"; 497 echo "\t\t<span class=\"clear\"> </span>\n"; 498 echo "\t</div>"; 499 500 $category = false; 501 $numdisplayed = 0; 502 $fd = $amp_conf['ASTETCDIR'].'/freepbx_module_admin.conf'; 503 if (file_exists($fd)) { 504 $module_filter = parse_ini_file($fd); 505 } else { 506 $module_filter = array(); 507 } 508 foreach (array_keys($modules) as $name) { 509 if (isset($module_filter[$name]) && strtolower(trim($module_filter[$name])) == 'hidden') { 510 continue; 511 } 512 $numdisplayed++; 513 514 if ($category !== $modules[$name]['category']) { 515 // show category header 516 517 if ($category !== false) { 518 // not the first one, so end the previous blocks 519 echo "\t</ul></div>\n"; 520 } 521 522 // start a new category header, and associated html blocks 523 $category = $modules[$name]['category']; 524 echo "\t<div class=\"category\" id=\"category_".prep_id($category)."\"><h3>"._($category)."</h3>\n"; 525 echo "\t<ul>"; 526 } 527 528 // This will load any module's i18n translations that are available and try to use them when printing the 529 // module names with a fall back to using the amp.po master translations for a check if not available in 530 // the local module. For new modules of course, there will be no translations usually. 531 // 532 if (extension_loaded('gettext') && is_dir("modules/".$name."/i18n")) { 533 bindtextdomain($name,"modules/".$name."/i18n"); 534 bind_textdomain_codeset($name, 'utf8'); 535 $loc_domain = $name; 536 537 $name_text = dgettext($loc_domain,$modules[$name]['name']); 538 if ($name_text == $modules[$name]['name']) { 539 $name_text = _($name_text); 540 } 541 } else { 542 $name_text = _($modules[$name]['name']); 543 $loc_domain = false; 544 } 545 546 echo "\t\t<li id=\"module_".prep_id($name)."\">\n"; 547 548 // ---- module header 549 echo "\t\t<div class=\"moduleheader\" onclick=\"toggleInfoPane('infopane_".prep_id($name)."');\" >\n"; 550 echo "\t\t\t<span class=\"modulename\"><a href=\"javascript:void(null);\">".(!empty($name_text) ? $name_text : $name)."</a></span>\n"; 551 echo "\t\t\t<span class=\"moduletype\">".$modules[$name]['type']."</span>\n"; 552 echo "\t\t\t<span class=\"moduleversion\">".(isset($modules[$name]['dbversion'])?$modules[$name]['dbversion']:' ')."</span>\n"; 553 554 echo "\t\t\t<span class=\"modulestatus\">"; 555 switch ($modules[$name]['status']) { 556 case MODULE_STATUS_NOTINSTALLED: 557 if (isset($modules_local[$name])) { 558 echo '<span class="notinstalled">'._('Not Installed (Locally available)').'</span>'; 559 } else { 560 echo '<span class="notinstalled">'.sprintf(_('Not Installed (Available online: %s)'), $modules_online[$name]['version']).'</span>'; 561 } 562 break; 563 case MODULE_STATUS_DISABLED: 564 if (isset($modules_online[$name]['version'])) { 565 $vercomp = version_compare_freepbx($modules_local[$name]['version'], $modules_online[$name]['version']); 566 if ($vercomp < 0) { 567 echo '<span class="alert">'.sprintf(_('Disabled; Online upgrade available (%s)'),$modules_online[$name]['version']).'</span>'; 568 } else if ($vercomp > 0) { 569 echo sprintf(_('Disabled; Newer than online version (%s)'), $modules_online[$name]['version']); 570 } else { 571 echo _('Disabled; up to date'); 572 } 573 } else { 574 echo 'Disabled'; 575 } 576 break; 577 case MODULE_STATUS_NEEDUPGRADE: 578 echo '<span class="alert">'.sprintf(_('Disabled; Pending upgrade to %s'),$modules_local[$name]['version']).'</span>'; 579 break; 580 case MODULE_STATUS_BROKEN: 581 echo '<span class="alert">'._('Broken').'</span>'; 582 break; 583 default: 584 // check for online upgrade 585 if (isset($modules_online[$name]['version'])) { 586 $vercomp = version_compare_freepbx($modules_local[$name]['version'], $modules_online[$name]['version']); 587 if ($vercomp < 0) { 588 echo '<span class="alert">'.sprintf(_('Online upgrade available (%s)'), $modules_online[$name]['version']).'</span>'; 589 } else if ($vercomp > 0) { 590 echo sprintf(_('Newer than online version (%s)'),$modules_online[$name]['version']); 591 } else { 592 echo _('Enabled and up to date'); 593 } 594 } else if (isset($modules_online)) { 595 // we're connected to online, but didn't find this module 596 echo _('Enabled; Not available online'); 597 } else { 598 echo _('Enabled'); 599 } 600 break; 601 } 602 echo "</span>\n"; 603 604 605 echo "\t\t\t<span class=\"clear\"> </span>\n"; 606 echo "\t\t</div>\n"; 607 608 // ---- end of module header 609 610 // ---- drop-down tab box thingy: 611 612 echo "\t\t<div class=\"moduleinfopane\" id=\"infopane_".prep_id($name)."\" >\n"; 613 echo "\t\t\t<div class=\"tabber\">\n"; 614 615 if (isset($modules_online[$name]['attention']) && !empty($modules_online[$name]['attention'])) { 616 echo "\t\t\t\t<div class=\"tabbertab\" title=\""._("Attention")."\">\n"; 617 echo nl2br( $loc_domain ? dgettext($loc_domain,$modules[$name]['attention']) : _($modules[$name]['attention']) ); 618 echo "\t\t\t\t</div>\n"; 619 } 620 621 echo "\t\t\t\t<div class=\"tabbertab actiontab\" title=\""._("Action")."\">\n"; 622 623 echo '<input type="radio" checked="CHECKED" id="noaction_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="0" /> '. 624 '<label for="noaction_'.prep_id($name).'">'._('No Action').'</label> <br />'; 625 switch ($modules[$name]['status']) { 626 627 case MODULE_STATUS_NOTINSTALLED: 628 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 629 if (isset($modules_local[$name])) { 630 echo '<input type="radio" id="install_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="install" /> '. 631 '<label for="install_'.prep_id($name).'">'._('Install').'</label> <br />'; 632 } else { 633 echo '<input type="radio" id="upgrade_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="downloadinstall" /> '. 634 '<label for="upgrade_'.prep_id($name).'">'._('Download and Install').'</label> <br />'; 635 } 636 } 637 break; 638 case MODULE_STATUS_DISABLED: 639 echo '<input type="radio" id="enable_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="enable" /> '. 640 '<label for="enable_'.prep_id($name).'">'._('Enable').'</label> <br />'; 641 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 642 echo '<input type="radio" id="uninstall_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="uninstall" /> '. 643 '<label for="uninstall_'.prep_id($name).'">'._('Uninstall').'</label> <br />'; 644 if (isset($modules_online[$name]['version'])) { 645 $vercomp = version_compare_freepbx($modules_local[$name]['version'], $modules_online[$name]['version']); 646 if ($vercomp < 0) { 647 echo '<input type="radio" id="upgrade_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="upgrade" /> '. 648 '<label for="upgrade_'.prep_id($name).'">'.sprintf(_('Download and Upgrade to %s, and Enable'),$modules_online[$name]['version']).'</label> <br />'; 649 } 650 } 651 } 652 break; 653 case MODULE_STATUS_NEEDUPGRADE: 654 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 655 echo '<input type="radio" id="install_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="install" /> '. 656 '<label for="install_'.prep_id($name).'">'.sprintf(_('Upgrade to %s and Enable'),$modules_local[$name]['version']).'</label> <br />'; 657 echo '<input type="radio" id="uninstall_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="uninstall" /> '. 658 '<label for="uninstall_'.prep_id($name).'">'._('Uninstall').'</label> <br />'; 659 } 660 break; 661 case MODULE_STATUS_BROKEN: 662 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 663 echo '<input type="radio" id="install_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="install" /> '. 664 '<label for="install_'.prep_id($name).'">'._('Install').'</label> <br />'; 665 echo '<input type="radio" id="uninstall_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="uninstall" /> '. 666 '<label for="uninstall_'.prep_id($name).'">'._('Uninstall').'</label> <br />'; 667 } 668 break; 669 default: 670 // check for online upgrade 671 if (isset($modules_online[$name]['version'])) { 672 $vercomp = version_compare_freepbx($modules_local[$name]['version'], $modules_online[$name]['version']); 673 if ($vercomp < 0) { 674 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 675 echo '<input type="radio" id="upgrade_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="upgrade" /> '. 676 '<label for="upgrade_'.prep_id($name).'">'.sprintf(_('Download and Upgrade to %s'), $modules_online[$name]['version']).'</label> <br />'; 677 } 678 } 679 } 680 if (enable_option($name,'candisable')) { 681 echo '<input type="radio" id="disable_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="disable" /> '. 682 '<label for="disable_'.prep_id($name).'">'._('Disable').'</label> <br />'; 683 } 684 if (!EXTERNAL_PACKAGE_MANAGEMENT && enable_option($name,'canuninstall')) { 685 echo '<input type="radio" id="uninstall_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="uninstall" /> '. 686 '<label for="uninstall_'.prep_id($name).'">'._('Uninstall').'</label> <br />'; 687 } 688 break; 689 } 690 echo "\t\t\t\t</div>\n"; 691 692 echo "\t\t\t\t<div class=\"tabbertab\" title=\""._("Description")."\">\n"; 693 if (isset($modules[$name]['description']) && !empty($modules[$name]['description'])) { 694 echo "<h5>".sprintf(_("Description for version %s"),$modules[$name]['version'])."</h5>"; 695 echo nl2br( $loc_domain ? dgettext($loc_domain,$modules[$name]['description']) : _($modules[$name]['description']) ); 696 } else { 697 echo _("No description is available."); 698 } 699 if (isset($modules[$name]['info']) && !empty($modules[$name]['info'])) { 700 echo '<p>'._('More info').': <a href="'.$modules[$name]['info'].'" target="_new">'.$modules[$name]['info'].'</a></p>'; 701 } else { 702 echo '<p>'._('More info').': <a href="'."$freepbx_help_url&freepbx_module=".urlencode($name).'" target="help">'.sprintf(_("Get help for %s"),$name_text).'</a></p>'; 703 } 704 echo "\t\t\t\t</div>\n"; 705 706 if (isset($modules[$name]['changelog']) && !empty($modules[$name]['changelog'])) { 707 echo "\t\t\t\t<div class=\"tabbertab\" title=\""._("Changelog")."\">\n"; 708 echo "<h5>".sprintf(_("Change Log for version %s"), $modules[$name]['version'])."</h5>"; 709 710 // convert "1.x.x:" and "*1.x.x*" into bold, and do nl2br 711 // TODO: need to fix this to convert 1.x.xbetax.x, 1.x.xalphax.x, 1.x.xrcx.x, 1.x.xRCx.x formats as well 712 // 713 $changelog = nl2br($modules[$name]['changelog']); 714 $changelog = preg_replace('/(\d+(\.\d+|\.\d+beta\d+|\.\d+alpha\d+|\.\d+rc\d+|\.\d+RC\d+)+):/', '<strong>$0</strong>', $changelog); 715 $changelog = preg_replace('/\*(\d+(\.\d+|\.\d+beta\d+|\.\d+alpha\d+|\.\d+rc\d+|\.\d+RC\d+)+)\*/', '<strong>$1:</strong>', $changelog); 716 717 // convert '#xxx', 'ticket xxx', 'bug xxx' to ticket links and rxxx to changeset links in trac 718 // 719 $changelog = preg_replace_callback('/(?<!\w)(?:#|bug |ticket )([^&]\d{3,4})(?!\w)/i', 'trac_replace_ticket', $changelog); 720 $changelog = preg_replace_callback('/(?<!\w)r(\d+)(?!\w)/', 'trac_replace_changeset', $changelog); 721 $changelog = preg_replace_callback('/(?<!\w)\[(\d+)\](?!\w)/', 'trac_replace_changeset', $changelog); 722 723 echo $changelog; 724 echo "\t\t\t\t</div>\n"; 725 } 726 727 if ($amp_conf['DEVEL']) { 728 echo "\t\t\t\t<div class=\"tabbertab\" title=\""._("Debug")."\">\n"; 729 echo "\t\t\t\t<h5>".$name."</h5><pre>\n"; 730 print_r($modules_local[$name]); 731 echo "</pre>"; 732 if (isset($modules_online)) { 733 echo "\t\t\t\t<h5>Online info</h5><pre>\n"; 734 print_r($modules_online[$name]); 735 echo "</pre>\n"; 736 } 737 echo "\t\t\t\t<h5>combined</h5><pre>\n"; 738 print_r($modules[$name]); 739 echo "</pre>\n"; 740 echo "\t\t\t\t</div>\n"; 741 } 742 743 echo "\t\t\t</div>\n"; 744 echo "\t\t</div>\n"; 745 746 // ---- end of drop-down tab box 747 748 echo "\t\t</li>\n"; 749 } 750 751 if ($numdisplayed == 0) { 752 if (isset($modules_online) && count($modules_online) > 0) { 753 echo _("All available modules are up-to-date and installed."); 754 } else { 755 echo _("No modules to display."); 756 } 757 } 758 759 echo "\t</ul></div>\n"; 760 echo "</div>"; 761 762 echo "<div class=\"modulebuttons\">"; 763 if ($online) { 764 echo "\t<a href=\"javascript:void(null);\" onclick=\"check_download_all();\">"._("Download all")."</a>"; 765 echo "\t<a href=\"javascript:void(null);\" onclick=\"check_upgrade_all();\">"._("Upgrade all")."</a>"; 766 } 767 echo "\t<input type=\"reset\" value=\""._("Reset")."\" />"; 768 echo "\t<input type=\"submit\" value=\""._("Process")."\" name=\"process\" />"; 769 echo "</div>"; 770 771 echo "</form>"; 772 break; 773 } 774 775 if ($quietmode) { 776 echo '</body></html>'; 777 } 778 779 //------------------------------------------------------------------------------------------- 780 // Help functions 781 // 206 782 207 783 function category_sort_callback($a, $b) { … … 273 849 ), 274 850 ); 275 276 851 if (isset($modules[$module_name][$option]) && strtolower(trim($modules[$module_name][$option])) == 'no') { 277 852 $enable=false; … … 280 855 $enable=false; 281 856 } 282 283 857 return $enable; 284 858 } … … 298 872 } 299 873 300 //-------------------------------------------------------------------------------------------------------- 301 switch ($extdisplay) { // process, confirm, or nothing 302 case 'process': 303 echo "<div id=\"moduleBoxContents\">"; 304 echo "<h4>"._("Please wait while module actions are performed")."</h4>\n"; 305 306 echo "<div id=\"moduleprogress\">"; 307 308 // stop output buffering, and send output 309 @ ob_end_flush(); 310 311 flush(); 312 foreach ($moduleaction as $modulename => $action) { 313 $didsomething = true; // set to false in default clause of switch() below.. 314 315 switch ($action) { 316 case 'upgrade': 317 case 'downloadinstall': 318 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 319 echo sprintf(_('Downloading %s'), $modulename).' <span id="downloadprogress_'.$modulename.'"></span>'; 320 if (is_array($errors = module_download($modulename, false, 'download_progress'))) { 321 echo '<span class="error">'.sprintf(_("Error(s) downloading %s"),$modulename).': '; 322 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 323 echo '</span>'; 324 } else { 325 326 if (is_array($errors = module_install($modulename))) { 327 echo '<span class="error">'.sprintf(_("Error(s) installing %s"),$modulename).': '; 328 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 329 echo '</span>'; 330 } else { 331 echo '<span class="success">'.sprintf(_("%s installed successfully"),$modulename).'</span>'; 332 } 333 } 334 } 335 break; 336 case 'install': 337 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 338 if (is_array($errors = module_install($modulename))) { 339 echo '<span class="error">'.sprintf(_("Error(s) installing %s"),$modulename).': '; 340 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 341 echo '</span>'; 342 } else { 343 echo '<span class="success">'.sprintf(_("%s installed successfully"),$modulename).'</span>'; 344 } 345 } 346 break; 347 case 'enable': 348 if (is_array($errors = module_enable($modulename))) { 349 echo '<span class="error">'.sprintf(_("Error(s) enabling %s"),$modulename).': '; 350 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 351 echo '</span>'; 352 } else { 353 echo '<span class="success">'.sprintf(_("%s enabled successfully"),$modulename).'</span>'; 354 } 355 break; 356 case 'disable': 357 if (is_array($errors = module_disable($modulename))) { 358 echo '<span class="error">'.sprintf(_("Error(s) disabling %s"),$modulename).': '; 359 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 360 echo '</span>'; 361 } else { 362 echo '<span class="success">'.sprintf(_("%s disabled successfully"),$modulename).'</span>'; 363 } 364 break; 365 case 'uninstall': 366 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 367 if (is_array($errors = module_uninstall($modulename))) { 368 echo '<span class="error">'.sprintf(_("Error(s) uninstalling %s"),$modulename).': '; 369 echo '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'; 370 echo '</span>'; 371 } else { 372 echo '<span class="success">'.sprintf(_("%s uninstalled successfully"),$modulename).'</span>'; 373 } 374 } 375 break; 376 default: 377 // just so we don't send an <hr> and flush() 378 $didsomething = false; 379 } 380 381 if ($didsomething) { 382 echo "<hr /><br />"; 383 flush(); 384 } 385 } 386 echo "</div>"; 387 if ($quietmode) { 388 echo "\t<a href=\"#\" onclick=\"parent.close_module_actions(true);\" />"._("Return")."</a>"; 389 } else { 390 echo "\t<input type=\"button\" value=\""._("Return")."\" onclick=\"location.href = 'config.php?display=modules&type=tool&online=".($_REQUEST['online']?1:0)."';\" />"; 391 echo "</div>"; 392 } 393 break; 394 case 'confirm': 395 ksort($moduleaction); 396 397 echo "<form name=\"modulesGUI\" action=\"config.php\" method=\"post\">"; 398 echo "<input type=\"hidden\" name=\"display\" value=\"".$display."\" />"; 399 echo "<input type=\"hidden\" name=\"type\" value=\"".$type."\" />"; 400 echo "<input type=\"hidden\" name=\"online\" value=\"".$online."\" />"; 401 echo "<input type=\"hidden\" name=\"extdisplay\" value=\"process\" />"; 402 403 echo "\t<script type=\"text/javascript\"> var moduleActions = new Array(); </script>\n"; 404 405 $actionstext = array(); 406 $errorstext = array(); 407 foreach ($moduleaction as $module => $action) { 408 $text = false; 409 $skipaction = false; 410 411 // make sure name is set. This is a problem for broken modules 412 if (!isset($modules[$module]['name'])) { 413 $modules[$module]['name'] = $module; 414 } 415 416 switch ($action) { 417 case 'upgrade': 418 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 419 if (is_array($errors = module_checkdepends($modules_online[$module]))) { 420 $skipaction = true; 421 $errorstext[] = sprintf(_("%s cannot be upgraded: %s Please try again after the dependencies have been installed."), 422 $modules[$module]['name'], 423 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 424 } else { 425 $actionstext[] = sprintf(_("%s %s will be upgraded to online version %s"), $modules[$module]['name'], $modules[$module]['dbversion'], $modules_online[$module]['version']); 426 } 427 } 428 break; 429 case 'downloadinstall': 430 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 431 if (is_array($errors = module_checkdepends($modules_online[$module]))) { 432 $skipaction = true; 433 $errorstext[] = sprintf(_("%s cannot be installed: %s Please try again after the dependencies have been installed."), 434 $modules[$module]['name'], 435 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 436 } else { 437 $actionstext[] = sprintf(_("%s %s will be downloaded and installed"), $modules[$module]['name'], $modules_online[$module]['version']); 438 } 439 } 440 break; 441 case 'install': 442 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 443 if (is_array($errors = module_checkdepends($modules[$module]))) { 444 $skipaction = true; 445 $errorstext[] = sprintf((($modules[$module]['status'] == MODULE_STATUS_NEEDUPGRADE) ? _("%s cannot be upgraded: %s Please try again after the dependencies have been installed.") : _("%s cannot be installed: %s Please try again after the dependencies have been installed.") ), 446 $modules[$module]['name'], 447 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 448 } else { 449 if ($modules[$module]['status'] == MODULE_STATUS_NEEDUPGRADE) { 450 $actionstext[] = sprintf(_("%s %s will be upgraded to %s"), $modules[$module]['name'], $modules[$module]['dbversion'], $modules[$module]['version']); 451 } else { 452 $actionstext[] = sprintf(_("%s %s will be installed and enabled"), $modules[$module]['name'], $modules[$module]['version']); 453 } 454 } 455 } 456 break; 457 case 'enable': 458 if (is_array($errors = module_checkdepends($modules[$module]))) { 459 $skipaction = true; 460 $errorstext[] = sprintf(_("%s cannot be enabled: %s Please try again after the dependencies have been installed."), 461 $modules[$module]['name'], 462 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 463 } else { 464 $actionstext[] = sprintf(_("%s %s will be enabled"), $modules[$module]['name'], $modules[$module]['dbversion']); 465 } 466 break; 467 case 'disable': 468 if (is_array($errors = module_reversedepends($modules[$module]))) { 469 $skipaction = true; 470 $errorstext[] = sprintf(_("%s cannot be disabled because the following modules depend on it: %s Please disable those modules first then try again."), 471 $modules[$module]['name'], 472 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 473 } else { 474 $actionstext[] = sprintf(_("%s %s will be disabled"), $modules[$module]['name'], $modules[$module]['dbversion']); 475 } 476 break; 477 case 'uninstall': 478 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 479 if (is_array($errors = module_reversedepends($modules[$module]))) { 480 $skipaction = true; 481 $errorstext[] = sprintf(_("%s cannot be uninstalled because the following modules depend on it: %s Please disable those modules first then try again."), 482 $modules[$module]['name'], 483 '<ul><li>'.implode('</li><li>',$errors).'</li></ul>'); 484 } else { 485 $actionstext[] = sprintf(_("%s %s will be uninstalled"), $modules[$module]['name'], $modules[$module]['dbversion']); 486 } 487 } 488 break; 489 } 490 491 // If error above we skip this action so we can proceed with the others 492 // 493 if (!$skipaction) { //TODO 494 echo "\t<script type=\"text/javascript\"> moduleActions['".$module."'] = '".$action."'; </script>\n"; 495 } 496 } 497 498 // Write out the erros, if there are additional actions that can be accomplished list those next with the choice to 499 // process which will ignore the ones with errors but process the rest. 500 // 501 if (count($errorstext) > 0) { 502 echo "<h4>"._("Errors with selection:")."</h4>\n"; 503 echo "<ul>\n"; 504 foreach ($errorstext as $text) { 505 echo "\t<li>".$text."</li>\n"; 506 } 507 echo "</ul>"; 508 } 509 if (count($actionstext) > 0) { 510 if (count($errorstext) > 0) { 511 echo "<h4>"._("You may confirm the remaining selection and then try the again for the listed issues once the required dependencies have been met:")."</h4>\n"; 512 } else { 513 echo "<h4>"._("Please confirm the following actions:")."</h4>\n"; 514 } 515 echo "<ul>\n"; 516 foreach ($actionstext as $text) { 517 echo "\t<li>".$text."</li>\n"; 518 } 519 echo "</ul>"; 520 echo "\t<input type=\"button\" value=\"Confirm\" name=\"process\" onclick=\"process_module_actions(moduleActions);\" />"; 521 } else { 522 echo "<h4>"._("No actions to perform")."</h4>\n"; 523 echo "<p>"._("Please select at least one action to perform by clicking on the module, and selecting an action on the \"Action\" tab.")."</p>"; 524 } 525 echo "\t<input type=\"button\" value=\""._("Cancel")."\" onclick=\"location.href = 'config.php?display=modules&type=tool&online=".($_REQUEST['online']?1:0)."';\" />"; 526 echo "</form>"; 527 528 break; 529 case 'upload': 530 // display links 531 echo "<a href='config.php?display=modules&type=tool'>"._("Manage local modules")."</a>\n"; 532 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 533 echo " | <a class='info' href='config.php?display=modules&type=tool&online=1'>"._("Check for updates online")."<span>"._("Checking for updates will transmit your FreePBX and Asterisk version numbers along with a unique but random identifier. This is used to provide proper update information and track version usage to focus development and maintenance efforts. No private information is transmitted.")."</span></a>\n"; 534 } 535 536 if (isset($_FILES['uploadmod']) && !empty($_FILES['uploadmod']['name'])) { 537 // display upload link, only if they did upload something 538 echo " | <a href='config.php?display=modules&type=tool&extdisplay=upload'>"._("Upload module")."</a><br />\n"; 539 540 $res = module_handleupload($_FILES['uploadmod']); 541 if (is_array($res)) { 542 543 echo '<div class="error"><p>'; 544 echo sprintf(_('The following error(s) occurred processing the uploaded file: %s'), 545 '<ul><li>'.implode('</li><li>',$res).'</li></ul>'); 546 echo sprintf(_('You should fix the problem or select another file and %s.'), 547 "<a href='config.php?display=modules&type=tool'>"._("try again")."</a>"); 548 echo "</p></div>\n"; 549 } else { 550 551 echo "<p>".sprintf(_("Module uploaded successfully. You need to enable the module using %s to make it available."), 552 "<a href='config.php?display=modules&type=tool'>"._("local module administration")."</a>") 553 ."</p>\n"; 554 } 555 556 } else { 557 echo "<p>"._('You can upload a tar gzip file containing a FreePBX module from your local system. If a module with the same name already exists, it will be overwritten.')."</p>\n"; 558 559 echo "<form name=\"modulesGUI-upload\" action=\"config.php\" method=\"post\" enctype=\"multipart/form-data\">"; 560 echo "<input type=\"hidden\" name=\"display\" value=\"".$display."\" />"; 561 echo "<input type=\"hidden\" name=\"type\" value=\"".$type."\" />"; 562 echo "<input type=\"hidden\" name=\"extdisplay\" value=\"upload\" />"; 563 564 echo "<input type=\"file\" name=\"uploadmod\" /> "; 565 echo " <input type=\"submit\" value=\"Upload\" />"; 566 echo "</form>"; 567 } 568 569 break; 570 case 'online': 571 default: 572 573 uasort($modules, 'category_sort_callback'); 574 575 if ($online) { 576 //echo "<a href='config.php?display=modules&type=tool&extdisplay=local'>"._("Terminate Connection to Online Module Repository")."</a><br />\n"; 577 //echo "<a href='config.php?display=modules&type=tool&extdisplay=online&refresh=true'>"._("Force Refresh of Local Module Cache")."</a>\n"; 578 579 // Check for annoucements such as security advisories, required updates, etc. 580 // 581 $announcements = module_get_annoucements(); 582 if (isset($announcements) && !empty($announcements)) { 583 echo "<div class='announcements'>$announcements</div>"; 584 } 585 586 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 587 echo "<a href='config.php?display=modules&type=tool&online=0'>"._("Manage local modules")."</a>\n"; 588 echo "<input type=\"checkbox\" id=\"show_upgradable_only\" onclick=\"showhide_upgrades();\" /><label for=\"show_upgradable_only\">"._("Show only upgradable")."</label>"; 589 } 590 } else { 591 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 592 echo "<a class='info' href='config.php?display=modules&type=tool&online=1'>"._("Check for updates online")."<span>"._("Checking for updates will transmit your FreePBX and Asterisk version numbers along with a unique but random identifier. This is used to provide proper update information and track version usage to focus development and maintenance efforts. No private information is transmitted.")."</span></a>\n"; 593 } 594 echo " | <a href='config.php?display=modules&type=tool&extdisplay=upload'>"._("Upload module")."</a><br />\n"; 595 } 596 597 echo "<form name=\"modulesGUI\" action=\"config.php\" method=\"post\">"; 598 echo "<input type=\"hidden\" name=\"display\" value=\"".$display."\" />"; 599 echo "<input type=\"hidden\" name=\"type\" value=\"".$type."\" />"; 600 echo "<input type=\"hidden\" name=\"online\" value=\"".$online."\" />"; 601 echo "<input type=\"hidden\" name=\"extdisplay\" value=\"confirm\" />"; 602 603 echo "<div class=\"modulebuttons\">"; 604 if ($online) { 605 echo "\t<a href=\"javascript:void(null);\" onclick=\"check_download_all();\">"._("Download all")."</a>"; 606 echo "\t<a href=\"javascript:void(null);\" onclick=\"check_upgrade_all();\">"._("Upgrade all")."</a>"; 607 } 608 echo "\t<input type=\"reset\" value=\""._("Reset")."\" />"; 609 echo "\t<input type=\"submit\" value=\""._("Process")."\" name=\"process\" />"; 610 echo "</div>"; 611 612 echo "<div id=\"modulelist\">\n"; 613 614 echo "\t<div id=\"modulelist-header\">"; 615 echo "\t\t<span class=\"modulename\">"._("Module")."</span>\n"; 616 echo "\t\t<span class=\"moduletype\">"._("Type")."</span>\n"; 617 echo "\t\t<span class=\"moduleversion\">"._("Version")."</span>\n"; 618 echo "\t\t<span class=\"clear\"> </span>\n"; 619 echo "\t</div>"; 620 621 $category = false; 622 $numdisplayed = 0; 623 $fd = $amp_conf['ASTETCDIR'].'/freepbx_module_admin.conf'; 624 if (file_exists($fd)) { 625 $module_filter = parse_ini_file($fd); 626 } else { 627 $module_filter = array(); 628 } 629 foreach (array_keys($modules) as $name) { 630 if (isset($module_filter[$name]) && strtolower(trim($module_filter[$name])) == 'hidden') { 631 continue; 632 } 633 $numdisplayed++; 634 635 if ($category !== $modules[$name]['category']) { 636 // show category header 637 638 if ($category !== false) { 639 // not the first one, so end the previous blocks 640 echo "\t</ul></div>\n"; 641 } 642 643 // start a new category header, and associated html blocks 644 $category = $modules[$name]['category']; 645 echo "\t<div class=\"category\" id=\"category_".prep_id($category)."\"><h3>"._($category)."</h3>\n"; 646 echo "\t<ul>"; 647 } 648 649 echo "\t\t<li id=\"module_".prep_id($name)."\">\n"; 650 651 // ---- module header 652 echo "\t\t<div class=\"moduleheader\" onclick=\"toggleInfoPane('infopane_".prep_id($name)."');\" >\n"; 653 echo "\t\t\t<span class=\"modulename\"><a href=\"javascript:void(null);\">".(!empty($modules[$name]['name']) ? $modules[$name]['name'] : $name)."</a></span>\n"; 654 echo "\t\t\t<span class=\"moduletype\">".$modules[$name]['type']."</span>\n"; 655 echo "\t\t\t<span class=\"moduleversion\">".(isset($modules[$name]['dbversion'])?$modules[$name]['dbversion']:' ')."</span>\n"; 656 657 echo "\t\t\t<span class=\"modulestatus\">"; 658 switch ($modules[$name]['status']) { 659 case MODULE_STATUS_NOTINSTALLED: 660 if (isset($modules_local[$name])) { 661 echo '<span class="notinstalled">'._('Not Installed (Locally available)').'</span>'; 662 } else { 663 echo '<span class="notinstalled">'.sprintf(_('Not Installed (Available online: %s)'), $modules_online[$name]['version']).'</span>'; 664 } 665 break; 666 case MODULE_STATUS_DISABLED: 667 if (isset($modules_online[$name]['version'])) { 668 $vercomp = version_compare_freepbx($modules_local[$name]['version'], $modules_online[$name]['version']); 669 if ($vercomp < 0) { 670 echo '<span class="alert">'.sprintf(_('Disabled; Online upgrade available (%s)'),$modules_online[$name]['version']).'</span>'; 671 } else if ($vercomp > 0) { 672 echo sprintf(_('Disabled; Newer than online version (%s)'), $modules_online[$name]['version']); 673 } else { 674 echo _('Disabled; up to date'); 675 } 676 } else { 677 echo 'Disabled'; 678 } 679 break; 680 case MODULE_STATUS_NEEDUPGRADE: 681 echo '<span class="alert">'.sprintf(_('Disabled; Pending upgrade to %s'),$modules_local[$name]['version']).'</span>'; 682 break; 683 case MODULE_STATUS_BROKEN: 684 echo '<span class="alert">'._('Broken').'</span>'; 685 break; 686 default: 687 // check for online upgrade 688 if (isset($modules_online[$name]['version'])) { 689 $vercomp = version_compare_freepbx($modules_local[$name]['version'], $modules_online[$name]['version']); 690 if ($vercomp < 0) { 691 echo '<span class="alert">'.sprintf(_('Online upgrade available (%s)'), $modules_online[$name]['version']).'</span>'; 692 } else if ($vercomp > 0) { 693 echo sprintf(_('Newer than online version (%s)'),$modules_online[$name]['version']); 694 } else { 695 echo _('Enabled and up to date'); 696 } 697 } else if (isset($modules_online)) { 698 // we're connected to online, but didn't find this module 699 echo _('Enabled; Not available online'); 700 } else { 701 echo _('Enabled'); 702 } 703 break; 704 } 705 echo "</span>\n"; 706 707 708 echo "\t\t\t<span class=\"clear\"> </span>\n"; 709 echo "\t\t</div>\n"; 710 711 // ---- end of module header 712 713 714 // ---- drop-down tab box thingy: 715 716 echo "\t\t<div class=\"moduleinfopane\" id=\"infopane_".prep_id($name)."\" >\n"; 717 echo "\t\t\t<div class=\"tabber\">\n"; 718 719 if (isset($modules_online[$name]['attention']) && !empty($modules_online[$name]['attention'])) { 720 echo "\t\t\t\t<div class=\"tabbertab\" title=\""._("Attention")."\">\n"; 721 echo nl2br($modules_online[$name]['attention']); 722 echo "\t\t\t\t</div>\n"; 723 } 724 725 echo "\t\t\t\t<div class=\"tabbertab actiontab\" title=\""._("Action")."\">\n"; 726 727 echo '<input type="radio" checked="CHECKED" id="noaction_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="0" /> '. 728 '<label for="noaction_'.prep_id($name).'">'._('No Action').'</label> <br />'; 729 switch ($modules[$name]['status']) { 730 731 case MODULE_STATUS_NOTINSTALLED: 732 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 733 if (isset($modules_local[$name])) { 734 echo '<input type="radio" id="install_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="install" /> '. 735 '<label for="install_'.prep_id($name).'">'._('Install').'</label> <br />'; 736 } else { 737 echo '<input type="radio" id="upgrade_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="downloadinstall" /> '. 738 '<label for="upgrade_'.prep_id($name).'">'._('Download and Install').'</label> <br />'; 739 } 740 } 741 break; 742 case MODULE_STATUS_DISABLED: 743 echo '<input type="radio" id="enable_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="enable" /> '. 744 '<label for="enable_'.prep_id($name).'">'._('Enable').'</label> <br />'; 745 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 746 echo '<input type="radio" id="uninstall_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="uninstall" /> '. 747 '<label for="uninstall_'.prep_id($name).'">'._('Uninstall').'</label> <br />'; 748 if (isset($modules_online[$name]['version'])) { 749 $vercomp = version_compare_freepbx($modules_local[$name]['version'], $modules_online[$name]['version']); 750 if ($vercomp < 0) { 751 echo '<input type="radio" id="upgrade_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="upgrade" /> '. 752 '<label for="upgrade_'.prep_id($name).'">'.sprintf(_('Download and Upgrade to %s, and Enable'),$modules_online[$name]['version']).'</label> <br />'; 753 } 754 } 755 } 756 break; 757 case MODULE_STATUS_NEEDUPGRADE: 758 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 759 echo '<input type="radio" id="install_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="install" /> '. 760 '<label for="install_'.prep_id($name).'">'.sprintf(_('Upgrade to %s and Enable'),$modules_local[$name]['version']).'</label> <br />'; 761 echo '<input type="radio" id="uninstall_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="uninstall" /> '. 762 '<label for="uninstall_'.prep_id($name).'">'._('Uninstall').'</label> <br />'; 763 } 764 break; 765 case MODULE_STATUS_BROKEN: 766 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 767 echo '<input type="radio" id="install_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="install" /> '. 768 '<label for="install_'.prep_id($name).'">'._('Install').'</label> <br />'; 769 echo '<input type="radio" id="uninstall_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="uninstall" /> '. 770 '<label for="uninstall_'.prep_id($name).'">'._('Uninstall').'</label> <br />'; 771 } 772 break; 773 default: 774 // check for online upgrade 775 if (isset($modules_online[$name]['version'])) { 776 $vercomp = version_compare_freepbx($modules_local[$name]['version'], $modules_online[$name]['version']); 777 if ($vercomp < 0) { 778 if (!EXTERNAL_PACKAGE_MANAGEMENT) { 779 echo '<input type="radio" id="upgrade_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="upgrade" /> '. 780 '<label for="upgrade_'.prep_id($name).'">'.sprintf(_('Download and Upgrade to %s'), $modules_online[$name]['version']).'</label> <br />'; 781 } 782 } 783 } 784 if (enable_option($name,'candisable')) { 785 echo '<input type="radio" id="disable_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="disable" /> '. 786 '<label for="disable_'.prep_id($name).'">'._('Disable').'</label> <br />'; 787 } 788 if (!EXTERNAL_PACKAGE_MANAGEMENT && enable_option($name,'canuninstall')) { 789 echo '<input type="radio" id="uninstall_'.prep_id($name).'" name="moduleaction['.prep_id($name).']" value="uninstall" /> '. 790 '<label for="uninstall_'.prep_id($name).'">'._('Uninstall').'</label> <br />'; 791 } 792 break; 793 } 794 echo "\t\t\t\t</div>\n"; 795 796 echo "\t\t\t\t<div class=\"tabbertab\" title=\""._("Description")."\">\n"; 797 if (isset($modules[$name]['description']) && !empty($modules[$name]['description'])) { 798 echo "<h5>".sprintf(_("Description for version %s"),$modules[$name]['version'])."</h5>"; 799 echo nl2br($modules[$name]['description']); 800 } else { 801 echo _("No description is available."); 802 } 803 if (isset($modules[$name]['info']) && !empty($modules[$name]['info'])) { 804 echo '<p>'._('More info').': <a href="'.$modules[$name]['info'].'" target="_new">'.$modules[$name]['info'].'</a></p>'; 805 } else { 806 echo '<p>'._('More info').': <a href="'."$freepbx_help_url&freepbx_module=".urlencode($name).'" target="help">'._("Get help for ").$modules[$name]['name'].'</a></p>'; 807 } 808 echo "\t\t\t\t</div>\n"; 809 810 if (isset($modules[$name]['changelog']) && !empty($modules[$name]['changelog'])) { 811 echo "\t\t\t\t<div class=\"tabbertab\" title=\""._("Changelog")."\">\n"; 812 echo "<h5>".sprintf(_("Change Log for version %s"), $modules[$name]['version'])."</h5>"; 813 814 // convert "1.x.x:" and "*1.x.x*" into bold, and do nl2br 815 // TODO: need to fix this to convert 1.x.xbetax.x, 1.x.xalphax.x, 1.x.xrcx.x, 1.x.xRCx.x formats as well 816 // 817 $changelog = nl2br($modules[$name]['changelog']); 818 $changelog = preg_replace('/(\d+(\.\d+|\.\d+beta\d+|\.\d+alpha\d+|\.\d+rc\d+|\.\d+RC\d+)+):/', '<strong>$0</strong>', $changelog); 819 $changelog = preg_replace('/\*(\d+(\.\d+|\.\d+beta\d+|\.\d+alpha\d+|\.\d+rc\d+|\.\d+RC\d+)+)\*/', '<strong>$1:</strong>', $changelog); 820 821 // convert '#xxx', 'ticket xxx', 'bug xxx' to ticket links and rxxx to changeset links in trac 822 // 823 $changelog = preg_replace_callback('/(?<!\w)(?:#|bug |ticket )([^&]\d{3,4})(?!\w)/i', 'trac_replace_ticket', $changelog); 824 $changelog = preg_replace_callback('/(?<!\w)r(\d+)(?!\w)/', 'trac_replace_changeset', $changelog); 825 $changelog = preg_replace_callback('/(?<!\w)\[(\d+)\](?!\w)/', 'trac_replace_changeset', $changelog); 826 827 echo $changelog; 828 echo "\t\t\t\t</div>\n"; 829 } 830 831 if (isset($amp_conf['DEVEL']) && $amp_conf['DEVEL'] == 'true') { 832 echo "\t\t\t\t<div class=\"tabbertab\" title=\""._("Debug")."\">\n"; 833 echo "\t\t\t\t<h5>".$name."</h5><pre>\n"; 834 print_r($modules_local[$name]); 835 echo "</pre>"; 836 if (isset($modules_online)) { 837 echo "\t\t\t\t<h5>Online info</h5><pre>\n"; 838 print_r($modules_online[$name]); 839 echo "</pre>\n"; 840 } 841 echo "\t\t\t\t<h5>combined</h5><pre>\n"; 842 print_r($modules[$name]); 843 echo "</pre>\n"; 844 echo "\t\t\t\t</div>\n"; 845 } 846 847 echo "\t\t\t</div>\n"; 848 echo "\t\t</div>\n"; 849 850 // ---- end of drop-down tab box 851 852 echo "\t\t</li>\n"; 853 } 854 855 if ($numdisplayed == 0) { 856 if (isset($modules_online) && count($modules_online) > 0) { 857 echo _("All available modules are up-to-date and installed."); 858 } else { 859 echo _("No modules to display."); 860 } 861 } 862 863 echo "\t</ul></div>\n"; 864 echo "</div>"; 865 866 echo "<div class=\"modulebuttons\">"; 867 if ($online) { 868 echo "\t<a href=\"javascript:void(null);\" onclick=\"check_download_all();\">"._("Download all")."</a>"; 869 echo "\t<a href=\"javascript:void(null);\" onclick=\"check_upgrade_all();\">"._("Upgrade all")."</a>"; 870 } 871 echo "\t<input type=\"reset\" value=\""._("Reset")."\" />"; 872 echo "\t<input type=\"submit\" value=\""._("Process")."\" name=\"process\" />"; 873 echo "</div>"; 874 875 echo "</form>"; 876 break; 877 } 878 879 if ($quietmode) { 880 echo '</body></html>'; 881 } 882 874 function pageReload(){ 875 return ""; 876 //return "<script language=\"Javascript\">document.location='".$_SERVER['PHP_SELF']."?".$_SERVER['QUERY_STRING']."&foo=".rand()."'</script>"; 877 } 883 878 ?> freepbx/trunk/amp_conf/htdocs/admin/views/freepbx_admin.php
r5760 r6600 13 13 $sort_name = Array(); 14 14 $sort_type = Array(); 15 $framework_text_domain = Array(); 15 16 // Sorting menu by category and name 16 17 foreach ($fpbx_menu as $key => $row) { … … 19 20 $sort_name[$key] = $row['name']; 20 21 $sort_type[$key] = $row['type']; 22 23 if (extension_loaded('gettext') && is_dir("modules/".$key."/i18n")) { 24 bindtextdomain($key,"modules/".$key."/i18n"); 25 bind_textdomain_codeset($key, 'utf8'); 26 $framework_text_domain[$key] = true; 27 } else { 28 $framework_text_domain[$key] = false; 29 } 21 30 } 22 31 … … 95 104 96 105 echo "\t<li class=\"".implode(' ',$li_classes)."\">"; 106 if ($framework_text_domain[$key]) { 107 $label_text = dgettext($key,$row['name']); 108 if ($label_text == $row['name']) { 109 $label_text = _($label_text); 110 } 111 } else { 112 $label_text = _($row['name']); 113 } 97 114 if (isset($row['disabled']) && $row['disabled']) { 98 echo _($row['name']);115 echo $label_text; 99 116 } else { 100 echo '<a href="'.$href.'" '.$extra_attributes.' >'. _($row['name'])."</a>";117 echo '<a href="'.$href.'" '.$extra_attributes.' >'. $label_text . "</a>"; 101 118 } 102 119 echo "</li>\n"; freepbx/trunk/amp_conf/htdocs/recordings/includes/display.php
r1395 r6600 171 171 function displayNavigationBlock($m,$q,$url_opts,$start,$span,$total) { 172 172 173 $start = $start=='' ? 0 : $start;174 $span = $span=='' ? 15 : $span;173 $start = ($start=='' || !ctype_digit($start)) ? 0 : $start; 174 $span = ($span=='' || !ctype_digit($span)) ? 15 : $span; 175 175 176 176 $total_pages = ceil($total/$span); freepbx/trunk/amp_conf/htdocs/recordings/includes/main.conf.php
r6539 r6600 263 263 $ASTERISK_PROTOCOLS['sip']['config_files'] = "/etc/asterisk/sip.conf;/etc/asterisk/sip_additional.conf"; 264 264 $ASTERISK_PROTOCOLS['zap']['table'] = "zap"; 265 $ASTERISK_PROTOCOLS['zap']['config_files'] = "/etc/asterisk/zapata.conf;/etc/asterisk/zapata_additional.conf ";265 $ASTERISK_PROTOCOLS['zap']['config_files'] = "/etc/asterisk/zapata.conf;/etc/asterisk/zapata_additional.conf;/etc/asterisk/chan_dahdi.conf;/etc/asterisk/chan_dahdi_additional.conf"; 266 266 267 267 # Settings for Follow-Me Select Boxes in seconds freepbx/trunk/amp_conf/htdocs/recordings/modules/callmonitor.module
r6511 r6600 115 115 $duration_filter = getArgument($args,'duration_filter'); 116 116 117 $start = $start==''? 0 : $start;118 $span = $span==''? 15 : $span;117 $start = ($start=='' || !ctype_digit($start)) ? 0 : $start; 118 $span = ($span=='' || !ctype_digit($span)) ? 15 : $span; 119 119 $order = $order=='' ? 'calldate' : $order; 120 $sort = $sort=='' ? 'desc' : $sort;120 $sort = ($sort=='' || strtolower($sort) == 'desc') ? 'desc' : 'asc'; 121 121 122 122 $displayname = $_SESSION['ari_user']['displayname']; … … 205 205 // table body 206 206 $playbackRow = 2; // Index to keep track of where playback control rows should be inserted. 207 foreach($data as $key=>$value) {207 if (is_array($data)) foreach($data as $key=>$value) { 208 208 209 209 // recording file … … 407 407 } 408 408 409 foreach($data as $data_key => $data_value) {409 if (is_array($data)) foreach($data as $data_key => $data_value) { 410 410 411 411 $recording=''; … … 573 573 function getSearchText($q,$duration_filter) { 574 574 575 $duration_filter = ctype_digit($duration_filter) ? $duration_filter : 0; 576 575 577 // search text 576 578 if ($q!='*' && $q!=NULL) { 579 580 $dbh = $_SESSION['dbh_cdr']; 577 581 $searchText .= "WHERE "; 578 582 $tok = strtok($q," \n\t"); 583 $tok = $dbh->escapeSimple($tok); 579 584 while ($tok) { 580 585 $searchText .= " (calldate regexp '" . $tok . "' … … 590 595 )"; 591 596 $tok = strtok(" \n\t"); 597 $tok = $dbh->escapeSimple($tok); 592 598 if ($tok) { 593 599 $searchText .= " AND"; … … 684 690 685 691 $dbh = $_SESSION['dbh_cdr']; 692 $order = $dbh->escapeSimple($order); 686 693 $sql = "SELECT * 687 694 FROM " . $ASTERISKCDR_DBTABLE . " freepbx/trunk/amp_conf/htdocs/recordings/modules/followme.module
r6029 r6600 655 655 656 656 if (isset($_SESSION['dbh_asterisk'])) { 657 $db = $_SESSION['dbh_asterisk']; 657 658 658 659 //format for SQL database … … 660 661 661 662 $sql = "UPDATE findmefollow SET grptime = '" . $follow_me_listring_time . "', grplist = '". 662 str_replace("'", "''",trim($follow_me_list)) . "', pre_ring = '" . $follow_me_prering_time .663 $db->escapeSimple(trim($follow_me_list)) . "', pre_ring = '" . $follow_me_prering_time . 663 664 "', needsconf = '" . $follow_me_confirm . "' WHERE grpnum = $exten LIMIT 1"; 664 665 $results = $_SESSION['dbh_asterisk']->query($sql); freepbx/trunk/amportal.conf
r6539 r6600 199 199 # the stats are updated based on the STATS interval but a few items are checked 200 200 # less frequently (such as Astersisk Uptime) based on the INFO value 201 202 # ZAP2DAHDICOMPAT=true|false 203 # DEFAULT VALUE: false 204 # If set to true, FreePBX will check if you have chan_dadhi installed. If so, it will 205 # automatically use all your ZAP configuration settings (devices and trunks) and 206 # silently convert them, under the covers, to DAHDI so no changes are needed. The 207 # GUI will continue to refer to these as ZAP but it will use the proper DAHDI channels. 208 # This will also keep Zap Channel DIDs working.
