PageRenderTime 27ms CodeModel.GetById 33ms RepoModel.GetById 1ms app.codeStats 0ms

/libraries/legacy/module/helper.php

https://github.com/LouisLandry/joomla-platform
PHP | 518 lines | 321 code | 76 blank | 121 comment | 47 complexity | aa8fabfad4cfd8a1e8d0599b35ebb6a4 MD5 | raw file
Possible License(s): GPL-2.0, LGPL-2.1, BSD-3-Clause
  1. <?php
  2. /**
  3. * @package Joomla.Legacy
  4. * @subpackage Module
  5. *
  6. * @copyright Copyright (C) 2005 - 2012 Open Source Matters, Inc. All rights reserved.
  7. * @license GNU General Public License version 2 or later; see LICENSE
  8. */
  9. defined('JPATH_PLATFORM') or die;
  10. /**
  11. * Module helper class
  12. *
  13. * @package Joomla.Legacy
  14. * @subpackage Module
  15. * @since 11.1
  16. */
  17. abstract class JModuleHelper
  18. {
  19. /**
  20. * Get module by name (real, eg 'Breadcrumbs' or folder, eg 'mod_breadcrumbs')
  21. *
  22. * @param string $name The name of the module
  23. * @param string $title The title of the module, optional
  24. *
  25. * @return object The Module object
  26. *
  27. * @since 11.1
  28. */
  29. public static function &getModule($name, $title = null)
  30. {
  31. $result = null;
  32. $modules =& self::_load();
  33. $total = count($modules);
  34. for ($i = 0; $i < $total; $i++)
  35. {
  36. // Match the name of the module
  37. if ($modules[$i]->name == $name || $modules[$i]->module == $name)
  38. {
  39. // Match the title if we're looking for a specific instance of the module
  40. if (!$title || $modules[$i]->title == $title)
  41. {
  42. // Found it
  43. $result = &$modules[$i];
  44. break;
  45. }
  46. }
  47. }
  48. // If we didn't find it, and the name is mod_something, create a dummy object
  49. if (is_null($result) && substr($name, 0, 4) == 'mod_')
  50. {
  51. $result = new stdClass;
  52. $result->id = 0;
  53. $result->title = '';
  54. $result->module = $name;
  55. $result->position = '';
  56. $result->content = '';
  57. $result->showtitle = 0;
  58. $result->control = '';
  59. $result->params = '';
  60. }
  61. return $result;
  62. }
  63. /**
  64. * Get modules by position
  65. *
  66. * @param string $position The position of the module
  67. *
  68. * @return array An array of module objects
  69. *
  70. * @since 11.1
  71. */
  72. public static function &getModules($position)
  73. {
  74. $position = strtolower($position);
  75. $result = array();
  76. $input = JFactory::getApplication()->input;
  77. $modules =& self::_load();
  78. $total = count($modules);
  79. for ($i = 0; $i < $total; $i++)
  80. {
  81. if ($modules[$i]->position == $position)
  82. {
  83. $result[] = &$modules[$i];
  84. }
  85. }
  86. if (count($result) == 0)
  87. {
  88. if ($input->getBool('tp') && JComponentHelper::getParams('com_templates')->get('template_positions_display'))
  89. {
  90. $result[0] = self::getModule('mod_' . $position);
  91. $result[0]->title = $position;
  92. $result[0]->content = $position;
  93. $result[0]->position = $position;
  94. }
  95. }
  96. return $result;
  97. }
  98. /**
  99. * Checks if a module is enabled
  100. *
  101. * @param string $module The module name
  102. *
  103. * @return boolean
  104. *
  105. * @since 11.1
  106. */
  107. public static function isEnabled($module)
  108. {
  109. $result = self::getModule($module);
  110. return !is_null($result);
  111. }
  112. /**
  113. * Render the module.
  114. *
  115. * @param object $module A module object.
  116. * @param array $attribs An array of attributes for the module (probably from the XML).
  117. *
  118. * @return string The HTML content of the module output.
  119. *
  120. * @since 11.1
  121. */
  122. public static function renderModule($module, $attribs = array())
  123. {
  124. static $chrome;
  125. if (constant('JDEBUG'))
  126. {
  127. JProfiler::getInstance('Application')->mark('beforeRenderModule ' . $module->module . ' (' . $module->title . ')');
  128. }
  129. $app = JFactory::getApplication();
  130. // Record the scope.
  131. $scope = $app->scope;
  132. // Set scope to component name
  133. $app->scope = $module->module;
  134. // Get module parameters
  135. $params = new JRegistry;
  136. $params->loadString($module->params);
  137. // Get module path
  138. $module->module = preg_replace('/[^A-Z0-9_\.-]/i', '', $module->module);
  139. $path = JPATH_BASE . '/modules/' . $module->module . '/' . $module->module . '.php';
  140. // Load the module
  141. if (file_exists($path))
  142. {
  143. $lang = JFactory::getLanguage();
  144. // 1.5 or Core then 1.6 3PD
  145. $lang->load($module->module, JPATH_BASE, null, false, false) ||
  146. $lang->load($module->module, dirname($path), null, false, false) ||
  147. $lang->load($module->module, JPATH_BASE, $lang->getDefault(), false, false) ||
  148. $lang->load($module->module, dirname($path), $lang->getDefault(), false, false);
  149. $content = '';
  150. ob_start();
  151. include $path;
  152. $module->content = ob_get_contents() . $content;
  153. ob_end_clean();
  154. }
  155. // Load the module chrome functions
  156. if (!$chrome)
  157. {
  158. $chrome = array();
  159. }
  160. include_once JPATH_THEMES . '/system/html/modules.php';
  161. $chromePath = JPATH_THEMES . '/' . $app->getTemplate() . '/html/modules.php';
  162. if (!isset($chrome[$chromePath]))
  163. {
  164. if (file_exists($chromePath))
  165. {
  166. include_once $chromePath;
  167. }
  168. $chrome[$chromePath] = true;
  169. }
  170. // Make sure a style is set
  171. if (!isset($attribs['style']))
  172. {
  173. $attribs['style'] = 'none';
  174. }
  175. // Dynamically add outline style
  176. if ($app->input->getBool('tp') && JComponentHelper::getParams('com_templates')->get('template_positions_display'))
  177. {
  178. $attribs['style'] .= ' outline';
  179. }
  180. foreach (explode(' ', $attribs['style']) as $style)
  181. {
  182. $chromeMethod = 'modChrome_' . $style;
  183. // Apply chrome and render module
  184. if (function_exists($chromeMethod))
  185. {
  186. $module->style = $attribs['style'];
  187. ob_start();
  188. $chromeMethod($module, $params, $attribs);
  189. $module->content = ob_get_contents();
  190. ob_end_clean();
  191. }
  192. }
  193. // Revert the scope
  194. $app->scope = $scope;
  195. if (constant('JDEBUG'))
  196. {
  197. JProfiler::getInstance('Application')->mark('afterRenderModule ' . $module->module . ' (' . $module->title . ')');
  198. }
  199. return $module->content;
  200. }
  201. /**
  202. * Get the path to a layout for a module
  203. *
  204. * @param string $module The name of the module
  205. * @param string $layout The name of the module layout. If alternative layout, in the form template:filename.
  206. *
  207. * @return string The path to the module layout
  208. *
  209. * @since 11.1
  210. */
  211. public static function getLayoutPath($module, $layout = 'default')
  212. {
  213. $template = JFactory::getApplication()->getTemplate();
  214. $defaultLayout = $layout;
  215. if (strpos($layout, ':') !== false)
  216. {
  217. // Get the template and file name from the string
  218. $temp = explode(':', $layout);
  219. $template = ($temp[0] == '_') ? $template : $temp[0];
  220. $layout = $temp[1];
  221. $defaultLayout = ($temp[1]) ? $temp[1] : 'default';
  222. }
  223. // Build the template and base path for the layout
  224. $tPath = JPATH_THEMES . '/' . $template . '/html/' . $module . '/' . $layout . '.php';
  225. $bPath = JPATH_BASE . '/modules/' . $module . '/tmpl/' . $defaultLayout . '.php';
  226. $dPath = JPATH_BASE . '/modules/' . $module . '/tmpl/default.php';
  227. // If the template has a layout override use it
  228. if (file_exists($tPath))
  229. {
  230. return $tPath;
  231. }
  232. elseif (file_exists($bPath))
  233. {
  234. return $bPath;
  235. }
  236. else
  237. {
  238. return $dPath;
  239. }
  240. }
  241. /**
  242. * Load published modules.
  243. *
  244. * @return array
  245. *
  246. * @since 11.1
  247. */
  248. protected static function &_load()
  249. {
  250. static $clean;
  251. if (isset($clean))
  252. {
  253. return $clean;
  254. }
  255. $app = JFactory::getApplication();
  256. $Itemid = $app->input->getInt('Itemid');
  257. $user = JFactory::getUser();
  258. $groups = implode(',', $user->getAuthorisedViewLevels());
  259. $lang = JFactory::getLanguage()->getTag();
  260. $clientId = (int) $app->getClientId();
  261. $db = JFactory::getDbo();
  262. $query = $db->getQuery(true);
  263. $query->select('m.id, m.title, m.module, m.position, m.content, m.showtitle, m.params, mm.menuid');
  264. $query->from('#__modules AS m');
  265. $query->join('LEFT', '#__modules_menu AS mm ON mm.moduleid = m.id');
  266. $query->where('m.published = 1');
  267. $query->join('LEFT', '#__extensions AS e ON e.element = m.module AND e.client_id = m.client_id');
  268. $query->where('e.enabled = 1');
  269. $date = JFactory::getDate();
  270. $now = $date->toSql();
  271. $nullDate = $db->getNullDate();
  272. $query->where('(m.publish_up = ' . $db->Quote($nullDate) . ' OR m.publish_up <= ' . $db->Quote($now) . ')');
  273. $query->where('(m.publish_down = ' . $db->Quote($nullDate) . ' OR m.publish_down >= ' . $db->Quote($now) . ')');
  274. $query->where('m.access IN (' . $groups . ')');
  275. $query->where('m.client_id = ' . $clientId);
  276. $query->where('(mm.menuid = ' . (int) $Itemid . ' OR mm.menuid <= 0)');
  277. // Filter by language
  278. if ($app->isSite() && $app->getLanguageFilter())
  279. {
  280. $query->where('m.language IN (' . $db->Quote($lang) . ',' . $db->Quote('*') . ')');
  281. }
  282. $query->order('m.position, m.ordering');
  283. // Set the query
  284. $db->setQuery($query);
  285. $clean = array();
  286. try
  287. {
  288. $modules = $db->loadObjectList();
  289. }
  290. catch (RuntimeException $e)
  291. {
  292. JLog::add(JText::sprintf('JLIB_APPLICATION_ERROR_MODULE_LOAD', $e->getMessage()), JLog::WARNING, 'jerror');
  293. return $clean;
  294. }
  295. // Apply negative selections and eliminate duplicates
  296. $negId = $Itemid ? -(int) $Itemid : false;
  297. $dupes = array();
  298. for ($i = 0, $n = count($modules); $i < $n; $i++)
  299. {
  300. $module = &$modules[$i];
  301. // The module is excluded if there is an explicit prohibition
  302. $negHit = ($negId === (int) $module->menuid);
  303. if (isset($dupes[$module->id]))
  304. {
  305. // If this item has been excluded, keep the duplicate flag set,
  306. // but remove any item from the cleaned array.
  307. if ($negHit)
  308. {
  309. unset($clean[$module->id]);
  310. }
  311. continue;
  312. }
  313. $dupes[$module->id] = true;
  314. // Only accept modules without explicit exclusions.
  315. if (!$negHit)
  316. {
  317. $module->name = substr($module->module, 4);
  318. $module->style = null;
  319. $module->position = strtolower($module->position);
  320. $clean[$module->id] = $module;
  321. }
  322. }
  323. unset($dupes);
  324. // Return to simple indexing that matches the query order.
  325. $clean = array_values($clean);
  326. return $clean;
  327. }
  328. /**
  329. * Module cache helper
  330. *
  331. * Caching modes:
  332. * To be set in XML:
  333. * 'static' One cache file for all pages with the same module parameters
  334. * 'oldstatic' 1.5 definition of module caching, one cache file for all pages
  335. * with the same module id and user aid,
  336. * 'itemid' Changes on itemid change, to be called from inside the module:
  337. * 'safeuri' Id created from $cacheparams->modeparams array,
  338. * 'id' Module sets own cache id's
  339. *
  340. * @param object $module Module object
  341. * @param object $moduleparams Module parameters
  342. * @param object $cacheparams Module cache parameters - id or url parameters, depending on the module cache mode
  343. *
  344. * @return string
  345. *
  346. * @since 11.1
  347. *
  348. * @link JFilterInput::clean()
  349. */
  350. public static function moduleCache($module, $moduleparams, $cacheparams)
  351. {
  352. if (!isset($cacheparams->modeparams))
  353. {
  354. $cacheparams->modeparams = null;
  355. }
  356. if (!isset($cacheparams->cachegroup))
  357. {
  358. $cacheparams->cachegroup = $module->module;
  359. }
  360. $user = JFactory::getUser();
  361. $cache = JFactory::getCache($cacheparams->cachegroup, 'callback');
  362. $conf = JFactory::getConfig();
  363. // Turn cache off for internal callers if parameters are set to off and for all logged in users
  364. if ($moduleparams->get('owncache', null) === '0' || $conf->get('caching') == 0 || $user->get('id'))
  365. {
  366. $cache->setCaching(false);
  367. }
  368. // Module cache is set in seconds, global cache in minutes, setLifeTime works in minutes
  369. $cache->setLifeTime($moduleparams->get('cache_time', $conf->get('cachetime') * 60) / 60);
  370. $wrkaroundoptions = array('nopathway' => 1, 'nohead' => 0, 'nomodules' => 1, 'modulemode' => 1, 'mergehead' => 1);
  371. $wrkarounds = true;
  372. $view_levels = md5(serialize($user->getAuthorisedViewLevels()));
  373. switch ($cacheparams->cachemode)
  374. {
  375. case 'id':
  376. $ret = $cache->get(
  377. array($cacheparams->class, $cacheparams->method),
  378. $cacheparams->methodparams,
  379. $cacheparams->modeparams,
  380. $wrkarounds,
  381. $wrkaroundoptions
  382. );
  383. break;
  384. case 'safeuri':
  385. $secureid = null;
  386. if (is_array($cacheparams->modeparams))
  387. {
  388. $uri = JRequest::get();
  389. $safeuri = new stdClass;
  390. foreach ($cacheparams->modeparams as $key => $value)
  391. {
  392. // Use int filter for id/catid to clean out spamy slugs
  393. if (isset($uri[$key]))
  394. {
  395. $noHtmlFilter = JFilterInput::getInstance();
  396. $safeuri->$key = $noHtmlFilter->clean($uri[$key], $value);
  397. }
  398. }
  399. }
  400. $secureid = md5(serialize(array($safeuri, $cacheparams->method, $moduleparams)));
  401. $ret = $cache->get(
  402. array($cacheparams->class, $cacheparams->method),
  403. $cacheparams->methodparams,
  404. $module->id . $view_levels . $secureid,
  405. $wrkarounds,
  406. $wrkaroundoptions
  407. );
  408. break;
  409. case 'static':
  410. $ret = $cache->get(
  411. array($cacheparams->class,
  412. $cacheparams->method),
  413. $cacheparams->methodparams,
  414. $module->module . md5(serialize($cacheparams->methodparams)),
  415. $wrkarounds,
  416. $wrkaroundoptions
  417. );
  418. break;
  419. // Provided for backward compatibility, not really useful.
  420. case 'oldstatic':
  421. $ret = $cache->get(
  422. array($cacheparams->class, $cacheparams->method),
  423. $cacheparams->methodparams,
  424. $module->id . $view_levels,
  425. $wrkarounds,
  426. $wrkaroundoptions
  427. );
  428. break;
  429. case 'itemid':
  430. default:
  431. $ret = $cache->get(
  432. array($cacheparams->class, $cacheparams->method),
  433. $cacheparams->methodparams,
  434. $module->id . $view_levels . JFactory::getApplication()->input->getInt('Itemid', null),
  435. $wrkarounds,
  436. $wrkaroundoptions
  437. );
  438. break;
  439. }
  440. return $ret;
  441. }
  442. }