Squiz Matrix  4.12.2
 All Data Structures Namespaces Functions Variables Pages
backend.inc
1 <?php
18 require_once SQ_FUDGE_PATH.'/general/general.inc';
19 
20 
33 class Backend extends MySource_Object
34 {
35 
41  var $out;
42 
43 
48  function Backend()
49  {
50  $this->MySource_Object();
51 
52  }//end constructor
53 
54 
63  function getBackendUrl($target='main')
64  {
65  return current_url().'?SQ_BACKEND_PAGE='.$target;
66 
67  }//end getBackendUrl()
68 
69 
76  function paint()
77  {
78 
79  header('Content-Type: text/html; charset='.SQ_CONF_DEFAULT_CHARACTER_SET);
80  if (SQ_IN_LIMBO) {
81 
82  if (!isset($_REQUEST['limbo_assetid'])) {
83  if (isset($_REQUEST['assetid'])) {
84  $_REQUEST['limbo_assetid'] = $_REQUEST['assetid'];
85  } else {
86  $limbo_asset = $GLOBALS['SQ_SYSTEM']->am->getAssetFromURL();
87  if (is_null($limbo_asset)) return;
88  $_REQUEST['limbo_assetid'] = $limbo_asset->id;
89  }
90  }
91 
92  if (!isset($_REQUEST['assetid'])) {
93  $_REQUEST['assetid'] = $_REQUEST['limbo_assetid'];
94  }
95 
96  }//end if in limbo
97 
98 
99  // now we should have an assetid - if we dont there is really nothing we can do
100  // unless someone has been kind enough to give us a URL like ?a=xx
101  if (!isset($_REQUEST['assetid']) && isset($_REQUEST['a'])) {
102  $_REQUEST['assetid'] = $_REQUEST['a'];
103  }
104  if (isset($_REQUEST['assetid'])) {
105  $printing_assetid = (SQ_IN_LIMBO) ? $_REQUEST['limbo_assetid'] : $_REQUEST['assetid'];
106  $printing_asset = $GLOBALS['SQ_SYSTEM']->am->getAsset($printing_assetid);
107  if (is_null($printing_asset)) {
108  trigger_localised_error('SYS0195', E_USER_WARNING, $printing_assetid);
109  return;
110  }
111  // lets ask the asset itself if we are allowed access to its backend interface
112  if (!$printing_asset->backendAccess()) {
113  $GLOBALS['SQ_SYSTEM']->paintLogin(translate('login'), translate('cannot_access_asset', $printing_asset->name));
114  return;
115  }
116  } else {
117  // we are not looking at any asset in particular - probably just trying to get into the
118  // backend to do some editing - so need a user with backend access
119  if (!$GLOBALS['SQ_SYSTEM']->user->canAccessBackend()) {
120  $GLOBALS['SQ_SYSTEM']->paintLogin('Login', translate('must_be_backend_user'));
121  return;
122  }
123  }
124 
125  if (isset($_REQUEST['a'])) {
126  $frontend_asset = $GLOBALS['SQ_SYSTEM']->am->getAsset($_REQUEST['a']);
127  if (is_null($frontend_asset)) {
128  trigger_localised_error('SYS0195', E_USER_WARNING, $_REQUEST['a']);
129  return;
130  }
131  $frontend_asset->printFrontend();
132  exit();
133  }
134 
135  // if we are in limbo, we are going to mix the frontend with the backend
136  // so we need to do things a little differently
137  if (empty($_REQUEST['SQ_BACKEND_PAGE']) && isset($_REQUEST['ignore_frames']) && $_REQUEST['ignore_frames'] == '1') {
138  // ignore_frames check, only print main
139  $_REQUEST['SQ_BACKEND_PAGE'] = 'main';
140  }
141 
142  if (isset($_REQUEST['asset_ei_screen'])) {
143  // if we are in limbo, and asset_ei_screen is defined
144  // we need to set backend page to 'main', so that _printMain can work correctly
145  // and user can add '<a href="?asset_ei_screen=metadata">Metadata Screen</a>'
146  // in their limbo layout content (e.g. for tabbed screen menu)
147  if (SQ_IN_LIMBO && !isset($_REQUEST['SQ_BACKEND_PAGE'])) {
148  $_REQUEST['SQ_BACKEND_PAGE'] = 'main';
149  // note: SQ_BACKEND_PAGE can be frames, if the user enter the query string manually
150  }
151  }
152 
153  if (SQ_DESIGN_NO_FRAME && SQ_IN_LIMBO) {
154  $_REQUEST['SQ_BACKEND_PAGE'] = 'main';
155  }//end if
156 
157  if (empty($_REQUEST['SQ_BACKEND_PAGE']) || $_REQUEST['SQ_BACKEND_PAGE'] == 'frames') {
158  $this->_printFrames();
159 
160  } else if ($_REQUEST['SQ_BACKEND_PAGE'] == 'asset_map_request') {
161  require_once SQ_LIB_PATH.'/asset_map/asset_map.inc';
162  $asset_map = new Asset_Map();
163  $asset_map->process($this);
164 
165  } else {
166  // Require backend outputter for the Force-Acquire page, so it at
167  // least has a design to use
168  if (SQ_IN_LIMBO && (($_REQUEST['SQ_BACKEND_PAGE'] == 'main') && (array_get_index($_REQUEST, 'am_section', '') != 'forceably_acquire_lock'))) {
169  // use limbo outputter for main frame
170  require_once SQ_INCLUDE_PATH.'/limbo_outputter.inc';
171  $this->out = new Limbo_Outputter();
172  } else {
173  // use backend outputter for other frames
174  require_once SQ_INCLUDE_PATH.'/backend_outputter.inc';
175  $this->out = new Backend_Outputter();
176  }
177 
178  if (isset($_REQUEST['SQ_BACKEND_PAGE'])) {
179  // make sure to set persistant SQ_BACKEND_PAGE
180  $this->out->addFormActionGetVar('SQ_BACKEND_PAGE', $_REQUEST['SQ_BACKEND_PAGE'], TRUE);
181  }
182 
183 
184  switch ($_REQUEST['SQ_BACKEND_PAGE']) {
185  case 'header':
186  $this->_printHeader();
187  break;
188 
189  case 'sidenav':
190  $this->_printSideNav();
191  break;
192 
193  case 'main':
194  $this->_printMain();
195  break;
196 
197  case 'resizer' :
198  $this->_printNavResizer();
199  break;
200 
201  default:
202  trigger_localised_error('SYS0097', E_USER_ERROR, $_REQUEST['SQ_BACKEND_PAGE']);
203 
204  }//end switch
205 
206  if (!SQ_IN_LIMBO || (($_REQUEST['SQ_BACKEND_PAGE'] != 'main') || (array_get_index($_REQUEST, 'am_section', '') == 'forceably_acquire_lock'))) {
207  // main frame printing is handled by the asset itself
208  // EXCEPT if the main frame is being used to print out
209  // 'force-acquire locks'
210  $this->out->paint();
211  }
212 
213  }//end else
214 
215  }//end paint()
216 
217 
224  function _printFrames()
225  {
226  $main_extras = '';
227  if (!isset($_REQUEST['assetid'])) {
228  $url_asset = $GLOBALS['SQ_SYSTEM']->am->getAssetFromURL(current_protocol(), NULL, TRUE, TRUE);
229  if (!is_null($url_asset)) {
230  $main_extras = '&assetid='.$url_asset->id.'&sq_from_frontend=1';
231  }
232  }
233 
234  $query_vars = Array();
235  parse_str($_SERVER['QUERY_STRING'], $query_vars);
236  if (!empty($query_vars)) {
237  // At this point, SQ_BACKEND_PAGE shouldn't be overriden other than 'main' for
238  // main frame URL. We can possibly have endlessly nested backend frames if the
239  // value was set to be 'frames'
240  if (isset($query_vars['SQ_BACKEND_PAGE'])) {
241  unset($query_vars['SQ_BACKEND_PAGE']);
242  }
243 
244  // append additional user defined query string
245  // (e.g. for trigger condition 'url matches')
246  foreach ($query_vars as $key => $value) {
247  if ($key == 'SQ_ACTION') continue;
248  $main_extras .= '&'.urlencode($key).'='.urlencode($value);
249  }
250  }
251 
252  $main_url = strip_url($_SERVER['PHP_SELF']).'?SQ_BACKEND_PAGE=main'.$main_extras;
253 
254  $frame_urls = Array(
255  'header' => $_SERVER['PHP_SELF'].'?SQ_BACKEND_PAGE=header',
256  'main' => $main_url,
257  'sidenav' => $_SERVER['PHP_SELF'].'?SQ_BACKEND_PAGE=sidenav',
258  'resizer' => $_SERVER['PHP_SELF'].'?SQ_BACKEND_PAGE=resizer',
259  );
260  $limbo_hipo = SQ_IN_LIMBO && (strpos($main_url, 'SQ_ACTION=hipo') !== FALSE);
261 
262  // Get the preference for whether or not to hide frames in Simple Edit
263  $limbo_hide_frames = SQ_IN_LIMBO && $GLOBALS['SQ_SYSTEM']->getUserPrefs('user', 'SQ_USER_LIMBO_HIDE_FRAMES');
264 
265  // then, override the preference with the URL option
266  if (isset($_GET['hide_frames'])) {
267  $limbo_hide_frames = $limbo_hide_frames && $_GET['hide_frames'];
268  }//end if
269 
270  // Give the page the appropriate title based on whether we are in limbo or backend
271  if (SQ_IN_LIMBO) {
272  $page_title = translate('page_title_simple_edit_interface', SQ_SYSTEM_LONG_NAME);
273  } else {
274  $page_title = translate('page_title_admin_interface', SQ_SYSTEM_LONG_NAME);
275  }
276 
277  ?>
278  <html>
279  <head>
280  <title><?php echo $page_title; ?></title>
281  <meta http-equiv="Content-Type" content="text/html; charset=<?php echo SQ_CONF_DEFAULT_CHARACTER_SET; ?>">
282  <link rel="shortcut icon" href=<?php echo '"'.sq_web_path('lib').'/web/images/icons/favicon.ico"'; ?>/>
283  <?php
284  if ($limbo_hipo) {
285  ?>
286  <script language="Javascript" type="text/javascript">
287  document.location = "<?php echo $main_url; ?>";
288  </script>
289  <?php
290  }
291  ?>
292  </head>
293  <?php
294  if (!$limbo_hipo) {
295  // if hide_frames is set, hide the header and remove the resizer
296  // i.e. one less column in the second frameset
297  // see _printMain() for more info
298  $header_height = $limbo_hide_frames ? 0 : 28;
299  $am_width = $GLOBALS['SQ_SYSTEM']->getUserPrefs('user', 'SQ_USER_ASSET_MAP_WIDTH');
300  $sidenav_width = SQ_IN_LIMBO ? 0 : ($am_width+5);
301  $resizer_width = $limbo_hide_frames ? 0 : 10;
302  $frameset_cols = $sidenav_width.','.$resizer_width.',*';
303  ?>
304  <frameset rows="<?php echo $header_height; ?>,*" frameborder="0" border="0">
305  <frame src="<?php echo $frame_urls['header']; ?>" name="sq_header" scrolling="no" marginwidth="0" marginheight="0">
306  <frameset cols="<?php echo $frameset_cols; ?>" frameborder="0" border="0" id ="main_frameset">
307  <frame src="<?php echo $frame_urls['sidenav']; ?>" name="sq_sidenav" scrolling="no" marginwidth="0" marginheight="0">
308  <frame src="<?php echo $frame_urls['resizer']; ?>" name="sq_resizer" scrolling="no" marginwidth="0" marginheight="0">
309  <frame src="<?php echo $frame_urls['main']; ?>" name="sq_main" marginwidth="0" marginheight="0" scrolling="yes">
310  </frameset>
311  </frameset>
312  <?php
313  }
314  ?>
315  </html>
316  <?php
317 
318  }//end _printFrames()
319 
320 
327  function _printHeader()
328  {
329  if (isset($_GET['sq_popups_blocked'])) {
330  $_SESSION['sq_popups_blocked'] = (int) $_GET['sq_popups_blocked'];
331  }
332  $popups_blocked = (!isset($_SESSION['sq_popups_blocked']) || $_SESSION['sq_popups_blocked']);
333  $dhtml_messages = Array();
334 
335  if ($GLOBALS['SQ_SYSTEM']->am->installed('search_manager')) {
336  $asset_search_default = translate('asset_search_default_keyword');
337  } else {
338  $asset_search_default = translate('asset_search_default');
339  }
340 
341  $this->out->openRaw();
342  ?>
343  <script language="JavaScript" type="text/javascript" src="<?php echo sq_web_path('lib') ?>/js/general.js"></script>
344  <script language="JavaScript" type="text/javascript">
345  // number of seconds before refreshing frame
346  var REFRESH_UPDATE = <?php echo max(10, (int) SQ_CONF_REFRESH_INTERVAL); ?>;
347  var MAX_UPDATE = <?php echo max(10, (int) SQ_CONF_LOCK_LENGTH - 60); ?>;
348 
349  var popups_blocked = '<?php echo (int) $popups_blocked; ?>';
350 
351  // Do we want to delay the header (which we will until all messages
352  // have been run through
353  var delay_header = false;
354 
355  // Has the header been delayed?
356  var header_delayed = 0;
357 
366  function reloadHeader(force) {
367  if (arguments.length == 0) force = false;
368 
369  var current_assetid = '';
370  var lock_type = '';
371 
372  // get the current message div
373  msgDiv = parent.frames["sq_main"].document.getElementById("new_message_popup");
374 
375  // If we are being forced to reload, due to hitting the lock
376  // length limit, close the current div and stop any delay
377  if (force) {
378  cancelMsgDiv();
379  delay_header = false;
380  }
381 
382  if (!msgDiv || msgDiv.style.display == "none") {
383  delay_header = false;
384  }
385 
386  if (delay_header) {
387  header_delayed = true;
388  // Check every 10 seconds so that if we've clicked off the
389  // page, we can at still update this
390  reload_timeout = setTimeout("reloadHeader()", 10 * 1000);
391  return;
392  }
393 
394  if (parent.frames["sq_main"] && parent.frames["sq_main"].get_form_element_value && parent.frames["sq_main"].SQ_DOCUMENT_LOADED) {
395  current_assetid = parent.frames["sq_main"].get_form_element_value('backend_assetid');
396  lock_type = parent.frames["sq_main"].get_form_element_value('sq_lock_type');
397  <?php
398  if (SQ_IN_LIMBO) {
399  ?>
400  limbo_lock_type = parent.frames["sq_main"].get_form_element_value('sq_limbo_lock_type');
401  <?php
402  }//end if in limbo
403  ?>
404  }
405  var url = '<?php echo $this->getBackendUrl('header'); ?>'
406  + '&current_assetid=' + current_assetid
407  + '&sq_lock_type=' + lock_type
408  <?php
409  if (SQ_IN_LIMBO) {
410  ?>
411  + '&sq_limbo_lock_type=' + limbo_lock_type
412  <?php
413  }//end if in limbo
414  ?>
415  + '&sq_popups_blocked=' + popups_blocked;
416  document.location = url;
417  }
418  </script>
419  <?php
420  $this->out->addOnLoad('reload_timeout = setTimeout("reloadHeader()", REFRESH_UPDATE * 1000);');
421  $this->out->addOnLoad('reload_force_timeout = setTimeout("reloadHeader(true)", MAX_UPDATE * 1000);');
422 
423  if (!SQ_IN_LIMBO && isset($_SESSION['backend_header_last_refresh'])) {
424  // check for updates to the asset tree
425  $date = db_extras_todate(MatrixDAL::getDbType(), ':update_date', FALSE);
426  $where = 'updated > '.$date;
427  $where = $GLOBALS['SQ_SYSTEM']->constructRollbackWhereClause($where);
428  $sql = 'SELECT assetid FROM '.SQ_TABLE_RUNNING_PREFIX.'ast '.$where;
429 
430  try {
431  $query = MatrixDAL::preparePdoQuery($sql);
432  MatrixDAL::bindValueToPdo($query, 'update_date', ts_iso8601($_SESSION['backend_header_last_refresh']));
433  $updated_assetids = MatrixDAL::executePdoAssoc($query, 0);
434  } catch (Exception $e) {
435  throw new Exception('Unable to get updated assetids in _printHeader due to database error: '.$e->getMessage());
436  }//end catch
437 
438  if (!empty($updated_assetids)) {
439  $this->out->addOnLoad('
440  if (parent.frames["sq_sidenav"] && parent.frames["sq_sidenav"].reload_assets) {
441  parent.frames["sq_sidenav"].reload_assets("'.addslashes(implode(',', $updated_assetids)).'");
442  }
443  ');
444  }
445  }//end if
446 
447 
448  // refresh lock held on current page
449  if (!empty($_GET['current_assetid']) && !empty($_GET['sq_lock_type'])) {
450  $GLOBALS['SQ_SYSTEM']->am->updateLock($_GET['current_assetid'], $_GET['sq_lock_type']);
451 
452  // If we are in Limbo, we may need to refresh more locks
453  if (SQ_IN_LIMBO && !empty($_GET['sq_limbo_lock_type'])) {
454  foreach (@unserialize(urldecode($_GET['sq_limbo_lock_type'])) as $limbo_lock_types) {
455  if ($limbo_lock_types != $_GET['sq_lock_type']) {
456  $GLOBALS['SQ_SYSTEM']->am->updateLock($_GET['current_assetid'], $limbo_lock_types);
457  }//end if
458  }//end foreach
459  }//end if
460  }//end if
461 
462 
464  // ASSET ID/URL/KEYWORD SEARCH //
466  if (!empty($_POST['asset_search']) && $_POST['asset_search'] != $asset_search_default) {
467  include_once SQ_LIB_PATH.'/backend_search/backend_search.inc';
468 
469  $_POST['asset_search'] = trim($_POST['asset_search']);
470 
471  $assetid_match = FALSE;
472  $url_match = FALSE;
473 
474  // check for a url first
475  $searched_asset = $GLOBALS['SQ_SYSTEM']->am->getAssetFromURL(NULL, strip_url($_POST['asset_search'], TRUE), TRUE, TRUE);
476  if (is_null($searched_asset) && assert_valid_assetid($_POST['asset_search'], '', TRUE, FALSE)) {
477  // check for assetid second
478  $searched_asset = $GLOBALS['SQ_SYSTEM']->am->getAsset($_POST['asset_search'], '', TRUE);
479  if (!is_null($searched_asset)) $assetid_match = TRUE;
480  } else {
481  $url_match = TRUE;
482  }
483 
484  $result_list = Array();
485  if (!is_null($searched_asset)) {
486  $this->out->addOnLoad('
487  if (parent.frames["sq_main"]) {
488  parent.frames["sq_main"].location = "'.$_SERVER['PHP_SELF'].'?SQ_BACKEND_PAGE=main&backend_section=am&am_section=edit_asset&assetid='.urlencode($searched_asset->id).'";
489  }
490  ');
491  } else {
492  $search_terms = $_POST['asset_search'];
493  try {
494  $results = Backend_Search::processSearch($search_terms);
495  } catch (Exception $e) {
496  $error_msg = $e->getMessage();
497  log_error('Search for "'.$_POST['asset_search'].'" failed due to error: '.$error_msg, E_USER_WARNING);
498  $results = Array();
499  }
500 
501  $js_code = '';
502 
503  if (empty($results)) {
504  $msg = (!empty($error_msg)) ? 'failed_searching_for_error' : 'failed_searching_for';
505  $html = $this->_getDHTMLMessage(translate('search_failed'), translate($msg, addslashes($_POST['asset_search'])), 'search-failed', 'info');
506  $dhtml_messages['search_failed'] = Array('html' => str_replace("\n", '', $html), 'width' => '400', 'timeout' => 6.0);
507  } else {
508  $detail_lines[] = '<strong>'.'Matched on Keyword ('.count($results).' asset'.(count($results) == 1 ? '' : 's').'):'.'</strong>';
509  $i = 0;
510 
511  foreach ($results as $result_assetid => $result_detail) {
512  $this_detail = Array();
513 
514  foreach ($result_detail as $result_component_name => $result_component) {
515  foreach ($result_component as $name => $value) {
516 
517  $name_detail = '';
518  switch ($result_component_name) {
519  case 'contents':
520  $name_detail = 'Asset Contents';
521  break;
522 
523  case 'metadata':
524  $name_detail = ($result_component_name == 'schema' ? 'Default ' : '').'Metadata: ';
525 
526  // Find a friendly name for the metadata field, if there
527  // is none then use the standard name of the field itself
528  $attr_values = $GLOBALS['SQ_SYSTEM']->am->getAttributeValuesByName('friendly_name', 'metadata_field', Array($name));
529  if (empty($attr_values)) {
530  $name_detail .= $value['name'];
531  } else {
532  $name_detail .= $attr_values[$name];
533  }
534 
535  $value = $value[0]['value'];
536  break;
537  case 'schema':
538  $name_detail = ($result_component_name == 'schema' ? 'Default ' : '').'Metadata: ';
539 
540  // Find a friendly name for the metadata field, if there
541  // is none then use the standard name of the field itself
542  $attr_values = $GLOBALS['SQ_SYSTEM']->am->getAttributeValuesByName('friendly_name', 'metadata_field', Array($name));
543  if (empty($attr_values)) {
544  $name_detail .= $value['name'];
545  } else {
546  $name_detail .= $attr_values[$name];
547  }
548 
549  $value = $value['value'];
550  break;
551 
552  case 'attributes':
553  $name_detail = 'Attribute: '.ucwords(str_replace('_', ' ', $name));
554  break;
555  }
556 
557  $words = preg_split('/[\r\n\t \|\&\~\/]+/', $search_terms);
558  $value = strip_tags($value);
559 
560  preg_match_all('/('.addslashes(implode('|', $words)).')/i', $value, $matches, PREG_SET_ORDER | PREG_OFFSET_CAPTURE);
561 
562  if (count($matches) > 0) {
563 
564  // We go backwards, because that way we don't invalidate
565  // our offsets. This section ellipsisises the bits between
566  // matches so that there's 15 characters either side of
567  // matches.
568 
569  // Last match position
570  if ($matches[count($matches) - 1][0][1] < strlen($value) - 15) {
571  $value = substr_replace($value, '...', $matches[count($matches) - 1][0][1] + 15);
572  }
573 
574  for ($i = count($matches) - 1; $i > 0; $i--) {
575  $previous_match = $matches[$i - 1][0];
576  $this_match = $matches[$i][0];
577 
578  $prev_pos = $previous_match[1] + strlen($previous_match[0]);
579  $next_pos = $this_match[1];
580 
581  if (($next_pos - $prev_pos) > 30) {
582  $value = substr_replace($value, '...', $prev_pos + 15, ($next_pos - $prev_pos) - 30);
583  }
584  }
585 
586  // First match position
587  if ($matches[0][0][1] > 15) {
588  $value = substr_replace($value, '...', 0, $matches[0][0][1] - 15);
589  }
590 
591  // Cut it down to a certain number of characters anyway
592  $value = ellipsisize($value, 120);
593 
594  $value = preg_replace('/('.addslashes(implode('|', $words)).')/i', '<span class="sq-backend-search-results-highlight">$1</span>', $value);
595 
596  // remove
597  $this_detail[] = $name_detail.'<br/><em>'.str_replace("\r", '', str_replace("\n", '<br/>', $value)).'</em>';
598  }//end if
599  }//end foreach
600  }//end foreach
601 
602  $result_list[] = Array(
603  'tag_line' => get_asset_tag_line($result_assetid, 'details'),
604  'detail' => implode($this_detail, '<br/>'),
605  );
606  }//end foreach
607  }//end else
608 
609  $keyword_match_line = Array();
610 
611  if (!empty($result_list)) {
612  $results_per_page = min(count($result_list), $GLOBALS['SQ_SYSTEM']->getUserPrefs('search_manager', 'SQ_SEARCH_BACKEND_PAGE_SIZE'));
613 
614  if (count($result_list) > $results_per_page) {
615  $keyword_match_line[] = '<div align="center">
616  <a href="" onclick="jumpToSearchResults(current = 0); return false;" title="Go back to first page">&lt;&lt;</a> &nbsp;
617  <a href="" onclick="jumpToSearchResults(current = Math.max(current - '.$results_per_page.', 0)); return false;" title="Go back one page">&lt;</a> &nbsp;
618  <strong>( <span id="sq-search-results-page-start">1</span> - <span id="sq-search-results-page-end">'.min(count($result_list), $results_per_page).'</span> )</strong> &nbsp;
619  <a href="" onclick="jumpToSearchResults(current = Math.min(current + '.$results_per_page.', Math.floor((parent.frames['."'sq_main'".'].keyword_search_results.length - 1) / '.$results_per_page.') * '.$results_per_page.')); return false;" title="Go forward one page">&gt;</a> &nbsp;
620  <a href="" onclick="jumpToSearchResults(current = Math.floor((parent.frames['."'sq_main'".'].keyword_search_results.length - 1) / '.$results_per_page.') * '.$results_per_page.'); return false;" title="Go forward to last page">&gt;&gt;</a></a></div>';
621  }
622 
623  $i = 0;
624  $js_code .= 'with (parent.frames["sq_main"]) { current = 0; results_per_page = '.$results_per_page.'; keyword_search_results = [];';
625 
626  foreach ($result_list as $result) {
627  $i++;
628  if ($i <= $results_per_page) {
629  $this_line = '<div><div id="sq-search-results-expand-'.$i.'" class="sq-search-results-expand-div"><a href="#" id="sq-search-results-expand-link-'.$i.'" class="sq-search-results-expand-link" onclick="if (this.innerHTML == \'+\') {document.getElementById(\'sq-search-results-detail-'.$i.'\').style.display = \'block\'; this.innerHTML = \'-\';} else {document.getElementById(\'sq-search-results-detail-'.$i.'\').style.display = \'none\'; this.innerHTML = \'+\';} return false;">+</a></div>';
630  $this_line .= '<div id="sq-search-results-entry-'.$i.'" class="sq-search-results-entry">';
631  $this_line .= $result['tag_line'].'<br/><div id="sq-search-results-detail-'.$i.'" class="sq-search-results-detail">'.$result['detail'].'</div></div></div>';
632  $keyword_match_line[] = $this_line;
633  }
634 
635  $js_code .= "\n".'keyword_search_results['.($i-1).'] = "'.addslashes(trim($result['tag_line'].'<br/><div id=\'sq-search-results-detail-'.((($i-1) % $results_per_page) + 1).'\' style=\'display:none\'>'.$result['detail'])).'</div>";';
636 
637  }
638 
639  $js_code .= '}';
640 
641  $detail_lines[] = implode('', $keyword_match_line);
642 
643  $html = $this->_getDHTMLMessage(translate('search_results'), $detail_lines, 'search-results');
644  $dhtml_messages['search_results'] = Array('html' => str_replace("\n", '', preg_replace('|<script.*</script>|U', '', $html)), 'width' => '300', 'timeout' => 0);
645  }//end if
646 
647  }//end else
648  }//end if
649 
650 
651  // check for any new internal messages if we are not in LIMBO
652  if (!SQ_IN_LIMBO) {
653 
655  // POPUP BLOCKING MESSAGE //
657 
658  if ($popups_blocked) {
659  $html = $this->_getDHTMLMessage(translate('popups_blocked'), translate('disable_popup_blocking'), 'popups-blocked', 'stop', 32, 32);
660  $dhtml_messages['popups_blocked'] = Array('html' => str_replace("\n", '', $html), 'width' => '400', 'timeout' => 6.0);
661  }
662 
664  // HIPO STALLED JOBS MESSAGE //
666 
667  $hh = $GLOBALS['SQ_SYSTEM']->getHipoHerder();
668  // We need to hide the Matrix errors that occur in the header (hence hiding all the buttons) see Bug #2964
669  $alljobs = @$hh->getJobsForUser($GLOBALS['SQ_SYSTEM']->user->id);
670 
671  // determine how many jobs have been running for more than 5 minutes
672  $stalledjobs = 0;
673  $now = time();
674  for ($i = 0; $i < count($alljobs); $i++) {
675  $job_last_updated = $alljobs[$i]['last_updated'];
676  $job_last_updated_timestamp = strtotime($job_last_updated);
677  if (($now - $job_last_updated_timestamp) >= 300) {
678  $stalledjobs++;
679  }
680  }
681 
682  if ($stalledjobs != 0) {
683  $html = $this->_getDHTMLMessage(translate('hipo_jobs_stalled'), translate('hipo_jobs_count', $GLOBALS['SQ_SYSTEM']->user->name, $stalledjobs), 'new-message', 'stop', 32, 32);
684  $dhtml_messages['hipo_jobs_stalled'] = Array('html' => str_replace("\n", '', $html), 'width' => '400', 'timeout' => 6.0);
685  }
687  // INTERNAL MESSAGE POPUP //
689 
690  $ms = $GLOBALS['SQ_SYSTEM']->getMessagingService();
691 
692  $msgs_from = (isset($_SESSION['backend_header_last_refresh'])) ? $_SESSION['backend_header_last_refresh'] : NULL;
693  $from = time() - 28800;
694  $loading_start = time();
695  $read_messages = $ms->getMessages($GLOBALS['SQ_SYSTEM']->user->id, NULL, Array(SQ_MSG_READ), Array(), $from, NULL, NULL, Array(), 0, TRUE);
696  $messages = $ms->getMessages($GLOBALS['SQ_SYSTEM']->user->id, NULL, Array(SQ_MSG_UNREAD), Array(), NULL, NULL, NULL, Array(), 0, TRUE);
697  $loading_time = time() - $loading_start;
698 
699  // remind user to clean up internal messages if it's taking too slow to load
700  if($loading_time >= 30) {
701  $html = $this->_getDHTMLMessage('Too slow to load messages','The Internal Messages is taking too long to load. Try running the <a href="http://manuals.matrix.squizsuite.net/server-administrator/chapters/remove-internal-messages-script" target="_blank">Remove Internal Message Script</a> to clean up internal messages within your system.', 'new-message', 'stop', 48, 48);
702  $dhtml_messages['warning_messsage'] = Array('html' =>str_replace("\n", '', $html), 'width' => '400', 'timeout' => 12.0);
703  }
704 
705 
706  if (!empty($messages)) {
707  $html = $this->_getDHTMLMessage(translate('new_messages'), translate('new_messages_count', htmlspecialchars($GLOBALS['SQ_SYSTEM']->user->name, ENT_COMPAT, SQ_CONF_DEFAULT_CHARACTER_SET), $messages), 'new-message', 'mail', 31, 37);
708  $dhtml_messages['new_messages'] = Array('html' => str_replace("\n", '', $html), 'width' => '220', 'timeout' => 6.0);
709  }
710 
711 
712 
713  }//end if not in LIMBO
714 
715  if (!empty($dhtml_messages)) {
716  ?>
717  <script language="Javascript" type="text/javascript">
718 
719  <?php
720  if (!SQ_IN_LIMBO) {
721  ?>
722  // update inbox message
723  if (parent.frames["sq_sidenav"] != null && parent.frames["sq_sidenav"].document.getElementById('sq_messages_text') != null) {
724  parent.frames["sq_sidenav"].document.getElementById('sq_messages_text').innerHTML="<?php echo translate('inbox_new_messages', $messages, ($read_messages+$messages)); ?>";
725  }
726  <?php
727  }
728  ?>
729 
730  var msgDiv = null;
731  var screenMenu = null;
732  var screenMenuFiller = null;
733 
734  var delay = 30; // milliseconds between movements
735  var myTimer = null;
736  var counter = null; // number of times to move the div
737  var messageIndex = 0;
738 
739  var divTop = 0;
740  var divLeft = 0;
741  var smTop = 0;
742  var smLeft = 0;
743 
744  // Time-out of current popup in milliseconds - if zero, the
745  // popup can only be dismissed by the user
746  var currentTimeout = 0;
747 
748  // This function now moves the div between 1 and 10 pixels
749  // depending on how far away the DIV is from stopping
750  function moveIt() {
751  to_move = Math.max(Math.min(Math.abs(divTop) * 0.08, 10), 2);
752  divTop += to_move;
753  msgDiv.style.top = (divTop + parent.frames["sq_main"].document.body.scrollTop) + "px";
754  if (divTop >= -0.1 && myTimer != null) {
755  clearInterval(myTimer);
756 
757  if (currentTimeout != 0) {
758  setTimeout("cancelMsgDiv()", currentTimeout);
759  }
760  }
761  }
762 
763  function showMsgDiv() {
764  if (screenMenu) {
765  if (window.navigator.userAgent.indexOf('MSIE') > 0) {
766  screenMenuFiller.style.width = screenMenu.offsetWidth;
767  screenMenuFiller.style.height = screenMenu.offsetHeight;
768  screenMenuFiller.style.display = "block";
769  screenMenu.style.display = "none";
770  }
771  screenMenu.style.MozOpacity = "0";
772  }
773 
774  msgDiv.style.visibility = "hidden";
775  msgDiv.style.display = "block";
776  counter = msgDiv.offsetHeight;
777 
778  divTop = (counter * -1);
779  msgDiv.style.top = divTop + "px";
780  msgDiv.style.visibility = "visible";
781 
782  myTimer = setInterval("moveIt()", delay);
783  }
784 
785  function cancelMsgDiv() {
786  clearInterval(myTimer);
787  msgDiv.style.display = "none";
788  if (screenMenu) {
789  if (window.navigator.userAgent.indexOf('MSIE') > 0) {
790  screenMenu.style.display = "block";
791  screenMenuFiller.width = "0px";
792  screenMenuFiller.height = "0px";
793  screenMenuFiller.style.display = "none";
794  }
795  screenMenu.style.MozOpacity = "1";
796  }
797  showNextMessage();
798  }
799 
800  function showNextMessage() {
801  if (!popupContents[messageIndex]) {
802  delay_header = false;
803  if (header_delayed) reloadHeader();
804  return;
805  }
806 
807  delay_header = true;
808 
809  msgDiv.innerHTML = popupContents[messageIndex]['html'];
810  currentTimeout = popupContents[messageIndex]['timeout'];
811  msgDiv.style.width = popupContents[messageIndex]['width'] + "px";
812  msgDiv.style.right = "10px";
813 
814  setTimeout("showMsgDiv()", 500);
815  messageIndex++;
816 
817  // Remove any "search in progress" message
818  top.frames["sq_main"].document.getElementById("sq-search-wait-popup").style.display = "none";
819  }
820 
821  var popupContents = new Array();
822  <?php
823  $i = 0;
824  foreach ($dhtml_messages as $code => $message) {
825  if ($code == 'popups_blocked') continue;
826  ?>
827  popupContents[<?php echo $i; ?>] = Array();
828  popupContents[<?php echo $i; ?>]['html'] = '<?php echo addslashes($message['html']); ?>';
829  popupContents[<?php echo $i; ?>]['width'] = '<?php echo addslashes($message['width']); ?>';
830  popupContents[<?php echo $i; ?>]['timeout'] = '<?php echo addslashes(array_get_index($message, 'timeout', 0) * 1000); ?>';
831  <?php
832  $i++;
833  }
834  ?>
835 
836  if (parent.frames["sq_main"].document.body && parent.frames["sq_main"].SQ_DOCUMENT_LOADED) {
837 
838  msgDiv = parent.frames["sq_main"].document.getElementById("new_message_popup");
839  screenMenu = parent.frames["sq_main"].document.getElementById("sq_screen_menu");
840  screenMenuFiller = parent.frames["sq_main"].document.getElementById("sq_screen_menu_filler");
841  if (msgDiv == null) {
842  msgDiv = parent.frames["sq_main"].document.createElement("div");
843  msgDiv.id = "new_message_popup";
844  msgDiv.style.position = "absolute";
845  msgDiv.style.display = "block";
846  msgDiv.style.top = "-1000px";
847  msgDiv.style.right = "-1000px";
848  msgDiv.style.zIndex = "10";
849  parent.frames["sq_main"].document.body.appendChild(msgDiv);
850  }
851 
852  messageIndex = 0;
853  <?php
854  if (!empty($js_code)) {
855  echo str_replace("\n", ' ', $js_code);
856  }
857 
858  if (isset($dhtml_messages['popups_blocked'])) {
859  ?>
860  var popup = window.open('', 'sq_popup_test', 'width=1px,height=1px,top=0,left=0');
861  if (!popup) {
862  msgDiv.innerHTML = '<?php echo addslashes($dhtml_messages['popups_blocked']['html']); ?>';
863  setTimeout("showMsgDiv()", 500);
864  divLeft = parent.frames["sq_main"].document.body.offsetWidth + parent.frames["sq_main"].document.body.scrollLeft - <?php echo $dhtml_messages['popups_blocked']['width']; ?> - 20;
865  msgDiv.style.width = "<?php echo addslashes($dhtml_messages['popups_blocked']['width']); ?>px";
866  msgDiv.style.right = "10px";
867  REFRESH_UPDATE = 20;
868  } else {
869  popup.close();
870  popups_blocked = '0';
871  showNextMessage();
872  }
873  <?php
874  } else {
875  ?>
876  // show the first message
877  showNextMessage();
878  <?php
879  }
880  ?>
881  }
882 
883  </script>
884  <?php
885  }//end if empty msgs
886 
887  if (SQ_ROLLBACK_VIEW) {
888  $now = strtotime($_SESSION['sq_rollback_view']['rollback_time']);
889  } else {
890  $now = time();
891  }
892 
893  ?>
894  <style type="text/css">
895  body { background: #342939; }
896  </style>
897  <table cellpadding="1" border="0" cellspacing="1" width="100%">
898  <tr>
899  <td nowrap class="sq-backend-header-item" valign="middle">
900  <img src="<?php echo sq_web_path('lib'); ?>/web/images/blank.gif" width="5" height="1" />
901  <a href="#" onclick="Javascript: reloadHeader(); return false;"><?php echo translate('logged_in_as', htmlspecialchars($GLOBALS['SQ_SYSTEM']->user->name, ENT_COMPAT, SQ_CONF_DEFAULT_CHARACTER_SET)); ?></a> -
902  <?php
903  // check warranty (if a warranty key exists)
904  if (defined('SQ_LICENCE_WARRANTY_KEY')) {
905  $wkey_snippet = substr(base64_decode(SQ_LICENCE_WARRANTY_KEY), 0, 6);
906  $ikey_snippet = substr(SQ_LICENCE_INSTALL_KEY, 0, 6);
907 
908  $expiry_date = substr(base64_decode(SQ_LICENCE_WARRANTY_KEY), 14);
909  $current_date = date('Ymd');
910  if ((SQ_LICENCE_WARRANTY_KEY === '') || ($current_date > $expiry_date) || ($wkey_snippet !== $ikey_snippet)) {
911  $message = translate('licence_type_no_warranty');
912  } else {
913  $message = translate('licence_type_warranty_valid');
914  }
915  } else {
916  // no warranty
917  $message = translate('licence_type_no_warranty');
918  }
919  echo $message;
920  ?>
921  </td>
922  <td nowrap class="sq-backend-header-item" valign="middle" align="right">
923  <?php
924  if (!isset($_SESSION['login_as_invoker_username']) && ($GLOBALS['SQ_SYSTEM']->userRoot() || $GLOBALS['SQ_SYSTEM']->userSystemAdmin())) {
925  ?>
926  <table cellpadding="0" border="0" cellspacing="0" id="login_as_form" style="display: none; height: 23px;" align="right">
927  <tr>
928  <td nowrap valign="middle">
929  <script>
930  function submit_login_as()
931  {
932  var login_as_user = document.getElementById('user').value;
933  if ((login_as_user.length > 0) && (login_as_user != 'root') && (login_as_user != '<?php htmlentities($GLOBALS['SQ_SYSTEM']->user->attr('username'), ENT_COMPAT, SQ_CONF_DEFAULT_CHARACTER_SET); ?>')) {
934  top.location = './?SQ_ACTION=login_as&user='+login_as_user;
935  }
936  }
937 
938  function show_login_as_form()
939  {
940  document.getElementById('login_as_form').style.display = 'block';
941  document.getElementById('tool_buttons').style.display = 'none';
942  }
943 
944  function hide_login_as_form()
945  {
946  document.getElementById('login_as_form').style.display = 'none';
947  document.getElementById('tool_buttons').style.display = 'block';
948  }
949  </script>
950  <?php
951  echo '<span class="sq-backend-header-item">'.translate('login_as').'</span>';
952  text_box('user', '', 22, 0, TRUE, 'class="sq-backend-header-search-box" onkeypress="if (event.keyCode == 13) submit_login_as();"');
953  ?>
954  <input type="button" style="height: 20px;" value="Login" onclick="submit_login_as();" />
955  <input type="button" style="height: 20px;" value="Cancel" onclick="hide_login_as_form();" />
956  </td>
957  </tr>
958  </table>
959  <?php
960  }
961  ?>
962  <table cellpadding="0" border="0" cellspacing="0" id="tool_buttons" align="right">
963  <tr>
964  <td nowrap valign="middle">
965  <?php
966  echo '<span class="sq-backend-header-item">'.translate('quick_search').'</span>';
967  text_box('asset_search', (!empty($_POST['asset_search'])) ? $_POST['asset_search'] : $asset_search_default, 30, 0, empty($_POST['asset_search']), 'class="sq-backend-header-search-box" onkeypress="if (event.keyCode == 13) form.submit();"');
968 
969  echo '<input type="image" class="sq-backend-header-search-button" alt="Go" src="'.sq_web_path('lib').'/web/images/icons/header/search.png" onClick="form.submit();">';
970  ?>
971  </td>
972  <td nowrap>
973  <?php
974  $options = Array();
975  if (!SQ_IN_LIMBO) {
976  if ($GLOBALS['SQ_SYSTEM']->userRoot() || $GLOBALS['SQ_SYSTEM']->userSystemAdmin()) {
977  $options[] = Array(
978  'url' => $this->getBackendUrl('main').'&backend_section=config',
979  'target' => 'sq_main',
980  'title' => translate('system_configuration'),
981  'icon' => 'system_config.png',
982  );
983  }
984 
985  $options[] = Array(
986  'url' => $this->getBackendUrl('main').'&backend_section=tools',
987  'target' => 'sq_main',
988  'title' => translate('tools'),
989  'icon' => 'whereami.png',
990  );
991 
992  $options[] = Array(
993  'url' => $this->getBackendUrl('main').'&backend_section=hipo_herder',
994  'target' => 'sq_main',
995  'title' => translate('hipo_herder'),
996  'icon' => 'hipo_herder.png',
997  );
998 
999  if ($GLOBALS['SQ_SYSTEM']->userRoot() || $GLOBALS['SQ_SYSTEM']->userSystemAdmin()) {
1000  $options[] = Array(
1001  'url' => $this->getBackendUrl('main').'&backend_section=sys_maintenance',
1002  'target' => 'sq_main',
1003  'title' => translate('system_maintenance'),
1004  'icon' => 'system_maintenance.png',
1005  );
1006  }
1007 
1008  $options[] = Array(
1009  'url' => $this->getBackendUrl('main').'&backend_section=am',
1010  'target' => 'sq_main',
1011  'title' => translate('asset_tree'),
1012  'icon' => 'asset_tree.png',
1013  );
1014 
1015  if (!isset($_SESSION['login_as_invoker_username']) && ($GLOBALS['SQ_SYSTEM']->userRoot() || $GLOBALS['SQ_SYSTEM']->userSystemAdmin())) {
1016  $options[] = Array(
1017  'target' => '_top',
1018  'title' => translate('login_as'),
1019  'icon' => 'login_as.png',
1020  'onclick' => 'document.getElementById("tool_buttons").style.display = "none"; document.getElementById("login_as_form").style.display = "block"; document.getElementById("user").focus();',
1021  );
1022  }
1023 
1024  $logout_button_tooltip = translate('logout');
1025  $logout_icon = 'logout.png';
1026 
1027  // Change the "Logout" button to a "Logout and resume as ..." button when we are temporarily logged in as another user
1028  if (isset($_SESSION['login_as_invoker_username'])) {
1029  $logout_button_tooltip = translate('logout_and_resume', htmlentities($_SESSION['login_as_invoker_username'], ENT_COMPAT, SQ_CONF_DEFAULT_CHARACTER_SET));
1030  $logout_icon = 'logout_and_resume.png';
1031  }
1032 
1033  $options[] = Array(
1034  'url' => $_SERVER['PHP_SELF'].'?SQ_ACTION=logout',
1035  'target' => '_top',
1036  'title' => $logout_button_tooltip,
1037  'icon' => $logout_icon,
1038  );
1039 
1040  } else {
1041 
1042  if (!isset($_SESSION['login_as_invoker_username']) && ($GLOBALS['SQ_SYSTEM']->userRoot() || $GLOBALS['SQ_SYSTEM']->userSystemAdmin())) {
1043  $options[] = Array(
1044  'target' => '_top',
1045  'title' => translate('login_as'),
1046  'icon' => 'login_as.png',
1047  'onclick' => 'show_login_as_form();',
1048  );
1049  }
1050 
1051  if (isset($_SESSION['login_as_invoker_username'])) {
1052  $options[] = Array(
1053  'target' => '_top',
1054  'title' => translate('logout_and_resume', $_SESSION['login_as_invoker_username']),
1055  'icon' => 'logout_and_resume.png',
1056  );
1057  }
1058 
1059  $options[] = Array(
1060  'url' => current_url(TRUE, TRUE),
1061  'target' => '_top',
1062  'title' => 'Exit Editing Mode',
1063  'icon' => 'exit_limbo.png',
1064  );
1065 
1066  }
1067 
1068  foreach ($options as $option) {
1069  if (isset($option['url'])) {
1070  ?><a href="<?php echo $option['url'];?>"<?php
1071  } else {
1072  ?><a nohref <?php
1073  }?>
1074  class="sq-backend-header-item"
1075  title="<?php echo htmlspecialchars($option['title']);?>"
1076  onMouseOver="window.status = '<?php echo htmlspecialchars($option['title']);?>'; return true;"
1077  onMouseOut = "window.status = ''; return true;"
1078  style="cursor: pointer;"
1079  <?php echo (isset($option['target'])) ? 'target="'.$option['target'].'"' : ''; ?>
1080  <?php echo (isset($option['onclick'])) ? 'onClick="'.htmlspecialchars($option['onclick']).'"' : ''; ?>
1081  <?php echo (isset($option['extras'])) ? $option['extras'] : ''; ?>
1082 
1083  ><script language="JavaScript" type="text/javascript">sq_print_icon("<?php echo $this->out->filesPath('/images/icons/header/'.$option['icon']); ?>", "20", "20", "<?php echo htmlspecialchars($option['title']);?>");</script></a>
1084  &nbsp;&nbsp;<?php
1085  }
1086  ?>
1087  </td>
1088  </tr>
1089  </table>
1090  </td>
1091  </tr>
1092  </table>
1093  <?php
1094 
1095  $this->out->closeRaw();
1096 
1097  $_SESSION['backend_header_last_refresh'] = time();
1098 
1099  }//end _printHeader()
1100 
1101 
1108  function _printSideNav()
1109  {
1110  $this->out->openRaw();
1111  $include_list = $GLOBALS['SQ_SYSTEM']->lm->getJavascriptIncludes();
1112  $include_list[] = sq_web_path('lib').'/js/general.js';
1113  foreach ($include_list as $link) {
1114  echo '<script type="text/javascript" src="'.$link.'"></script>'."\n";
1115  }
1116  ?>
1117  <style type="text/css">
1118  body {
1119  background: #342939;
1120  height: 100%;
1121  }
1122 
1123  .sidenav-tab-start {
1124  background: url("<?php echo sq_web_path('lib'); ?>/web/images/sidenav_tab_start.png") no-repeat;
1125  }
1126  .sidenav-tab-start-active {
1127  background: url("<?php echo sq_web_path('lib'); ?>/web/images/sidenav_active_tab_start.png") no-repeat;
1128  }
1129  .sidenav-tab, .sidenav-tab-icon {
1130  background: url("<?php echo sq_web_path('lib'); ?>/web/images/sidenav_tab_bg.png");
1131  }
1132  .sidenav-tab-active, .sidenav-tab-icon-active {
1133  background: url("<?php echo sq_web_path('lib'); ?>/web/images/sidenav_active_tab_bg.png");
1134  }
1135  .sidenav-tab-end {
1136  background: url("<?php echo sq_web_path('lib'); ?>/web/images/sidenav_tab_end.png") no-repeat;
1137  }
1138  .sidenav-tab-end-active {
1139  background: url("<?php echo sq_web_path('lib'); ?>/web/images/sidenav_active_tab_end.png") no-repeat;
1140  }
1141 
1142  .sidenav-tab-icon, .sidenav-tab-icon-active {
1143  padding-left: 5px;
1144  }
1145 
1146  .sidenav-tab a, .sidenav-tab-active a {
1147  font-family: Arial;
1148  font-size: 10px;
1149  color: #000000;
1150  padding-left: 2px;
1151  padding-right: 8px;
1152  text-decoration: none;
1153  }
1154 
1155  #asset_map {
1156  margin: 0px;
1157  border: 1px solid #342939;
1158  padding: 0px;
1159  width: 100%;
1160  }
1161 
1162  #my_space {
1163  width: 100%;
1164  background-color: #FFFFFF;
1165  padding: 0px;
1166  margin: 0px;
1167  border: 1px solid #FFFFFF;
1168  }
1169  .myspace-section {
1170  background-color: #FFFFFF;
1171  border: 1px solid #A2A2A2;
1172  margin: 2px;
1173  width: 273px;
1174  }
1175  .myspace-section td, .myspace-section a {
1176  font-family: Arial;
1177  font-size: 9px;
1178  color: #666666;
1179  text-decoration: none;
1180  }
1181  .myspace-section-header, .myspace-section-header a {
1182  font-size: 12px;
1183  font-weight: bold;
1184  text-decoration: none;
1185  }
1186  </style>
1187  <script type="text/javascript">
1188  var oldTabName = 'asset_map';
1189  var tabNames = Array('asset_map', 'my_space');
1190 
1191  function switchSideNav(tabName)
1192  {
1193  var tabElement = null;
1194 
1195  // show the correct DIV
1196  for (var i=0; i < tabNames.length; i++) {
1197  if (tabNames[i] != tabName) {
1198  tabElement = document.getElementById(tabNames[i]);
1199  tabElement.style.visibility = 'hidden';
1200  }
1201  }
1202 
1203  tabElement = document.getElementById(tabName);
1204  tabElement.style.visibility = 'visible';
1205 
1206  // switch the tabs
1207  var tabStart = document.getElementById(oldTabName + '_tab_start');
1208  tabStart.className = 'sidenav-tab-start';
1209  var tabEnd = document.getElementById(oldTabName + '_tab_end');
1210  tabEnd.className = 'sidenav-tab-end';
1211  var tabIcon = document.getElementById(oldTabName + '_tab_icon');
1212  tabIcon.className = 'sidenav-tab-icon';
1213  var tab = document.getElementById(oldTabName + '_tab');
1214  tab.className = 'sidenav-tab';
1215 
1216  tabStart = document.getElementById(tabName + '_tab_start');
1217  tabStart.className = 'sidenav-tab-start-active';
1218  tabEnd = document.getElementById(tabName + '_tab_end');
1219  tabEnd.className = 'sidenav-tab-end-active';
1220  tabIcon = document.getElementById(tabName + '_tab_icon');
1221  tabIcon.className = 'sidenav-tab-icon-active';
1222  tab = document.getElementById(tabName + '_tab');
1223  tab.className = 'sidenav-tab-active';
1224 
1225  // save this tab name for next time
1226  oldTabName = tabName;
1227 
1228  }//end switchSideNav()
1229  </script>
1230 
1231  <?php
1232  if (SQ_IN_LIMBO) {
1233  ?>
1234  <table cellspacing="0" cellpadding="0" border="0" width="100%" height="100%">
1235  <tr>
1236  <td class="sq-backend-header-item" style="width: 100%;"><img style="margin-left: 21px; margin-bottom: 5px;" src="<?php echo sq_web_path('lib'); ?>/web/images/icons/asset_map/matrix_logo.gif" alt="MySource Matrix" /></td>
1237  </tr>
1238  <tr>
1239  <td height="100%" valign="top">&nbsp;</td>
1240  </tr>
1241  <tr>
1242  <td class="sq-backend-header-item" style="padding-bottom: 5px;">
1243  <a href="<?php echo SQ_SYSTEM_URL;?>" class="sq-backend-header-item" target="_blank" style="text-decoration:none;"><?php echo SQ_SYSTEM_LONG_NAME;?></a>
1244  </td>
1245  </tr>
1246  </table>
1247  <div id="asset_map" style="position: absolute; top: 27px; left: 6px; visibility: visible; border-top: 0px none; border-left: 0px none;">
1248  <?php
1249  require_once SQ_LIB_PATH.'/asset_map/asset_map.inc';
1250  $asset_map = new Asset_Map();
1251  $am_width = $GLOBALS['SQ_SYSTEM']->getUserPrefs('user', 'SQ_USER_ASSET_MAP_WIDTH');
1252  $asset_map->embedAssetMap('simple', $am_width);
1253  ?>
1254  </div>
1255  <?php
1256  } else {
1257  // we are on the backend
1258  ?>
1259  <table cellspacing="0" cellpadding="0" border="0" width="100%" height="100%">
1260  <tr>
1261  <td class="sq-backend-header-item" style="width: 100%;"><img style="margin-left: 21px; margin-bottom: 5px;" src="<?php echo sq_web_path('lib'); ?>/web/images/icons/asset_map/matrix_logo.gif" alt="MySource Matrix" /></td>
1262  </tr>
1263  <tr>
1264  <td height="100%" valign="top">
1265  <table cellspacing="0" cellpadding="0">
1266  <tr>
1267  <td><img src="<?php echo sq_web_path('lib'); ?>/web/images/blank.gif" width="24" height="1" /></td>
1268 
1269  <td class="sidenav-tab-start-active" id="asset_map_tab_start"><img src="<?php echo sq_web_path('lib'); ?>/web/images/blank.gif" width="2" height="20" /></td>
1270  <td class="sidenav-tab-icon-active" id="asset_map_tab_icon"><script language="JavaScript" type="text/javascript">sq_print_icon("<?php echo sq_web_path('lib'); ?>/web/images/icons/asset_map/tree.png", "14", "14", "");</script></td>
1271  <td class="sidenav-tab-active" id="asset_map_tab"><a href="#" onClick="Javascript: switchSideNav('asset_map'); return false;"><?php echo translate('asset_map'); ?></a></td>
1272  <td class="sidenav-tab-end-active" id="asset_map_tab_end"><img src="<?php echo sq_web_path('lib'); ?>/web/images/blank.gif" width="3" height="20" /></td>
1273 
1274  <td class="sidenav-tab-start" id="my_space_tab_start"><img src="<?php echo sq_web_path('lib'); ?>/web/images/blank.gif" width="2" height="20" /></td>
1275  <td class="sidenav-tab-icon" id="my_space_tab_icon"><script language="JavaScript" type="text/javascript">sq_print_icon("<?php echo sq_web_path('lib'); ?>/web/images/icons/asset_map/myspace.png", "14", "14", "");</script></td>
1276  <td class="sidenav-tab" id="my_space_tab"><a href="#" onClick="Javascript: switchSideNav('my_space'); return false;"><?php echo translate('my_space'); ?></a></td>
1277  <td class="sidenav-tab-end" id="my_space_tab_end"><img src="<?php echo sq_web_path('lib'); ?>/web/images/blank.gif" width="3" height="20" /></td>
1278  </tr>
1279  </table>
1280  </td>
1281  </tr>
1282  <tr>
1283  <td class="sq-backend-header-item" style="padding-bottom: 5px;">
1284  <a href="<?php echo SQ_SYSTEM_URL;?>" class="sq-backend-header-item" target="_blank" style="text-decoration:none;" <?php
1285  if (defined('SQ_LICENCE_INSTALL_KEY')) {
1286  echo ' title="Install Key: '.SQ_LICENCE_INSTALL_KEY.'"';
1287  }
1288  ?>><?php echo SQ_SYSTEM_LONG_NAME;?></a>
1289  </td>
1290  </tr>
1291  </table>
1292 
1293  <div id="asset_map" style="position: absolute; top: 47px; left: 6px; visibility: visible; border-top: 0px none; border-left: 0px none;">
1294  <?php
1295  require_once SQ_LIB_PATH.'/asset_map/asset_map.inc';
1296  $asset_map = new Asset_Map();
1297  $am_width = $GLOBALS['SQ_SYSTEM']->getUserPrefs('user', 'SQ_USER_ASSET_MAP_WIDTH');
1298  $asset_map->embedAssetMap('complex', $am_width);
1299  ?>
1300  </div>
1301  <div id="my_space" style="position: absolute; top: 44px; left: 0px; visibility: hidden;">
1302  <?php
1303  $user = $GLOBALS['SQ_SYSTEM']->user;
1304  $inbox_link = $GLOBALS['SQ_SYSTEM']->am->getLink($user->id, SQ_LINK_TYPE_2, 'inbox', TRUE, NULL, 'major', '1');
1305 
1306  if (empty($inbox_link)) {
1307  $inbox_url = '';
1308  } else {
1309  $inbox_asset = $GLOBALS['SQ_SYSTEM']->am->getAsset($inbox_link['minorid'], $inbox_link['minor_type_code']);
1310  $inbox_url = $inbox_asset->getBackendHref('details');
1311  $new_message_url = $inbox_asset->getBackendHref('new_message');
1312  $sent_url = $inbox_asset->getBackendHref('sent');
1313  $trash_url = $inbox_asset->getBackendHref('trash');
1314  }
1315 
1316  $details_url = $user->getBackendHref('details');
1317 
1318  // get all unread messages and read messages that are less than 8 hours old
1319  if (!empty($inbox_url)) {
1320  $ms = $GLOBALS['SQ_SYSTEM']->getMessagingService();
1321  $from = time() - 28800; // 8 hours ago
1322  $read_messages = $ms->getMessages($GLOBALS['SQ_SYSTEM']->currentUserId(), NULL, Array(SQ_MSG_READ), Array(), $from, NULL, 'short_name', Array(), 0, TRUE);
1323  $unread_messages = $ms->getMessages($GLOBALS['SQ_SYSTEM']->currentUserId(), NULL, Array(SQ_MSG_UNREAD), Array(), NULL, NULL, 'short_name', Array(), 0, TRUE);
1324 
1325  $messages = $read_messages + $unread_messages;
1326  ?>
1327  <table class="myspace-section">
1328  <tr>
1329  <td valign="top"><a href="<?php echo $_SERVER['PHP_SELF'].$inbox_url; ?>" target="sq_main"><img src="<?php echo sq_web_path('lib'); ?>/web/images/icons/asset_map/inbox_icon.png" align="left" border="0" /></a></td>
1330  <td width="100%">
1331  <p><a href="<?php echo $_SERVER['PHP_SELF'].$inbox_url; ?>" target="sq_main"><span class="myspace-section-header"><?php echo translate('my_inbox'); ?></span><br /><span id="sq_messages_text"><?php echo translate('inbox_new_messages', $unread_messages, $messages); ?></span></a></p>
1332  <p><a href="<?php echo $_SERVER['PHP_SELF'].$inbox_url; ?>" target="sq_main"><span class="myspace-section-header"><?php echo translate('inbox_actions'); ?></span><br />
1333  <a href="<?php echo $_SERVER['PHP_SELF'].$inbox_url; ?>" target="sq_main">+ <?php echo translate('inbox_view'); ?></a><br />
1334  <a href="<?php echo $_SERVER['PHP_SELF'].$new_message_url; ?>" target="sq_main">+ <?php echo translate('inbox_send'); ?></a><br />
1335  <a href="<?php echo $_SERVER['PHP_SELF'].$sent_url; ?>" target="sq_main">+ <?php echo translate('inbox_view_sent'); ?></a><br />
1336  <a href="<?php echo $_SERVER['PHP_SELF'].$trash_url; ?>" target="sq_main">+ <?php echo translate('inbox_view_trash'); ?></a></p>
1337  </td>
1338  </tr>
1339  </table>
1340  <?php
1341  }//end if user has an inbox
1342 
1343  ?>
1344  <table class="myspace-section">
1345  <tr>
1346  <td valign="top"><a href="<?php echo $_SERVER['PHP_SELF'].$details_url; ?>" target="sq_main"><img src="<?php echo sq_web_path('lib'); ?>/web/images/icons/asset_map/mydetails_icon.png" align="left" border="0" /></a></td>
1347  <td width="100%">
1348  <span class="myspace-section-header"><a href="<?php echo $_SERVER['PHP_SELF'].$details_url; ?>" target="sq_main"><?php echo translate('my_details'); ?></span><br /><?php echo translate('details_edit'); ?></a>
1349  </td>
1350  </tr>
1351  </table>
1352  </div>
1353  <?php
1354  }//end else if not in limbo
1355 
1356  $this->out->closeRaw();
1357 
1358  }//end _printSideNav()
1359 
1360 
1367  function _printNavResizer()
1368  {
1369  $this->out->openRaw();
1370 
1371  ?>
1372  <style>
1373  body {
1374  background: #342939;
1375  height: 100%;
1376  }
1377  </style>
1378 
1379  <script language="Javascript" type="text/javascript">
1380  var clickSize = 50;
1381  var fset = top.document.getElementById('main_frameset');
1382  hidden = <?php var_export(SQ_IN_LIMBO); ?>;
1383  <?php $am_width = $GLOBALS['SQ_SYSTEM']->getUserPrefs('user', 'SQ_USER_ASSET_MAP_WIDTH') + 5; ?>
1384 
1385  function toggleFrame() {
1386  if (hidden == false) {
1387  if (fset.cols == "<?php echo $am_width; ?>,10,*") {
1388  fset.cols = "0,10,*";
1389  } else if (fset.cols == "<?php echo $am_width; ?>,0,*") {
1390  fset.cols = "0,0,*";
1391  }
1392  hidden = true;
1393  } else {
1394  if (fset.cols == "0,10,*") {
1395  fset.cols = "<?php echo $am_width; ?>,10,*";
1396  } else if (fset.cols == "0,0,*") {
1397  fset.cols = "<?php echo $am_width; ?>,0,*";
1398  }
1399  hidden = false;
1400  }
1401  }
1402  </script>
1403 
1404  <table border="0" cellspacing="0" cellpadding="0" width="100%" height="100%" background="<?php echo $this->out->filesPath('/images/flash_resizer/background.gif'); ?>">
1405  <tr>
1406  <td valign="top"><img src="<?php echo $this->out->filesPath('/images/flash_resizer/top.gif'); ?>" width="9" height="25" border="0" alt="" /></td>
1407  </tr>
1408  <tr height="100%">
1409  <td valign="middle"><a class="sq-backend-header-item" style="padding: 0px;" href="#" onClick="Javascript: toggleFrame()"><img src="<?php echo $this->out->filesPath('/images/flash_resizer/bar.gif'); ?>" width="9" height="72" border="0" alt="<<" /></a></td>
1410  </tr>
1411  </table>
1412 
1413  <script language="Javascript" type="text/javascript">
1414  document.main_form.style.width = "100%";
1415  document.main_form.style.height = "100%";
1416  </script>
1417  <?php
1418 
1419  $this->out->closeRaw();
1420 
1421  }//end _printNavResizer()
1422 
1423 
1430  function _printMain()
1431  {
1432 
1433  // verify nonce secuirty token to make sure the user submitting the request is using Matrix's backend interface
1434  if((SQ_IN_BACKEND || SQ_IN_LIMBO) && isset($_POST['process_form'])) {
1435  if(!isset($_POST['token'])) {
1436  trigger_error('Security token not found');
1437  return;
1438  }
1439  $token = get_unique_token();
1440  if($_POST['token'] !== $token) {
1441  trigger_error('Invalid security token');
1442  return;
1443  }
1444  }
1445 
1446 
1447  if (empty($_REQUEST['backend_section'])) {
1448  $_REQUEST['backend_section'] = 'am';
1449  }
1450  if (empty($_REQUEST['assetid'])) {
1451  $_REQUEST['assetid'] = '';
1452  }
1453 
1454  $this->out->addFormActionGetVar('backend_section', $_REQUEST['backend_section']);
1455 
1456  // if we are in rollback view, print a warning message
1457  if (SQ_ROLLBACK_VIEW) {
1458  $this->out->openRaw();
1459  $GLOBALS['SQ_SYSTEM']->printRollbackWarning();
1460  $this->out->closeRaw();
1461  }
1462 
1463  // add an onLoad event that checks if the current window is in the frameset
1464  // and redirects the user to the frameset version if they are not
1465  if (empty($_REQUEST['ignore_frames'])) {
1466  // if hide_frames and limbo_assetid are set, pass the parameter
1467  $hide_frames = (isset($_REQUEST['hide_frames']) && $_REQUEST['hide_frames']) ? 'hide_frames=1&' : '';
1468  if(SQ_IN_LIMBO) {
1469  $limbo_assetid = (isset($_GET['limbo_assetid'])) ? 'limbo_assetid='.rawurlencode($_GET['limbo_assetid']).'&' : '';
1470  } else if (SQ_IN_BACKEND) {
1471  $limbo_assetid = (isset($_GET['assetid'])) ? 'assetid='.rawurlencode($_GET['assetid']).'&' : '';
1472  }
1473 
1474  // if the user enter the ei screen manually, we need to print the frames as well
1475  $asset_ei_screen = (isset($_GET['asset_ei_screen'])) ? 'asset_ei_screen='.rawurlencode($_GET['asset_ei_screen'] ): '';
1476  if (SQ_IN_LIMBO) {
1477  $asset_ei_screen .= '&SQ_BACKEND_PAGE=frames';
1478  }
1479  $extra = '/?'.$hide_frames.$limbo_assetid.$asset_ei_screen;
1480 
1481  if(isset($_GET['backend_section'])) $extra .= '&backend_section='.rawurlencode($_GET['backend_section']);
1482 
1483  if(isset($_GET['am_section'])) $extra .= '&am_section='.rawurlencode($_GET['am_section']);
1484 
1485  if(isset($_GET['backend_section'])) $extra .= '&backend_section='.rawurlencode($_GET['backend_section']);
1486 
1487  $redirect_url = strip_url(current_url()).$extra;
1488  // bug fix : #4831 While in Rollback mode Asset Map is hidden
1489  // if we are in backend we dont need to worry about hiding frames
1490  if (!SQ_DESIGN_NO_FRAME || strpos($redirect_url ,SQ_CONF_BACKEND_SUFFIX) !== FALSE) {
1491  $this->out->addOnLoad('if (!parent.frames["sq_header"]) { sq_redirect("'.$redirect_url.'"); }');
1492  }//end if
1493  }
1494 
1495  switch ($_REQUEST['backend_section']) {
1496  case 'config' :
1497  require_once SQ_INCLUDE_PATH.'/system_config_edit_interface.inc';
1498  $cfg_ei = new System_Config_Edit_Interface();
1499  $cfg_ei->paint($this);
1500  break;
1501 
1502  case 'tools' :
1503  require_once SQ_INCLUDE_PATH.'/tools.inc';
1504  $tools = new Tools();
1505  $tools->paintBackend($this);
1506  break;
1507 
1508  case 'maps' :
1509  require_once SQ_SYSTEM_ROOT.'/core/maps/maps.inc';
1510  $maps = new Maps();
1511  $maps->paintBackend($this);
1512  break;
1513 
1514  case 'hipo_herder' :
1515  $hh = $GLOBALS['SQ_SYSTEM']->getHipoHerder();
1516  $hh->paintBackend($this);
1517  break;
1518 
1519  case 'sys_maintenance' :
1520  require_once SQ_INCLUDE_PATH.'/system_maintenance.inc';
1521  $sys_maintenance = new System_Maintenance();
1522  $sys_maintenance->paintBackend($this);
1523  break;
1524 
1525  case 'am' :
1526  $GLOBALS['SQ_SYSTEM']->am->paintBackend($this);
1527  break;
1528 
1529  default :
1530  trigger_localised_error('SYS0098', E_USER_ERROR, $_REQUEST['backend_section']);
1531 
1532  }//end switch
1533 
1534  }//end _printMain()
1535 
1536 
1555  function _getDHTMLMessage($title, $detail, $style='new-message', $icon='', $icon_width=16, $icon_height=16)
1556  {
1557  if (!is_array($detail)) $detail = Array($detail);
1558 
1559  $html = '
1560  <table class="sq-backend-'.$style.'-table">
1561  <tr>
1562  ';
1563  if (!empty($icon)) {
1564  $html .= ' <td rowspan="'.(1 + count($detail)).'" width="'.$icon_width.'" valign="middle" class="sq-backend-'.$style.'-heading">'.sq_get_icon(sq_web_path('lib').'/web/images/icons/'.$icon.'.png', $icon_width, $icon_height, '', '', 'align="absmiddle"').'</td>';
1565  }
1566  $html .= '
1567  <td class="sq-backend-'.$style.'-heading" nowrap="nowrap">'.$title.'</td>
1568  <td class="sq-backend-'.$style.'-heading" align="right">[<a class="sq-backend-'.$style.'-heading" href="#" onClick="Javascript: parent.frames[\'sq_header\'].cancelMsgDiv(); return false;">x</a>]</td>
1569  </tr>
1570  ';
1571 
1572  foreach ($detail as $detail_line) {
1573  $html .= '
1574  <tr>
1575  <td class="sq-backend-'.$style.'-body" colspan="2">'.$detail_line.'</td>
1576  </tr>';
1577  }
1578  $html .= '</table>';
1579  return $html;
1580 
1581  }//end _getDHTMLMessage()
1582 
1583 
1584 
1585 }//end class
1586 
1587 ?>