PageRenderTime 36ms CodeModel.GetById 4ms RepoModel.GetById 0ms app.codeStats 0ms

/plugins/system/jsntplframework/libraries/joomlashine/widget/sample.php

https://bitbucket.org/pastor399/newcastleunifc
PHP | 745 lines | 276 code | 83 blank | 386 comment | 24 complexity | 5036c392a39c6629de468df399e4cfab MD5 | raw file
  1. <?php
  2. /**
  3. * @version $Id$
  4. * @package JSNExtension
  5. * @subpackage JSNTPLFramework
  6. * @author JoomlaShine Team <support@joomlashine.com>
  7. * @copyright Copyright (C) 2012 JoomlaShine.com. All Rights Reserved.
  8. * @license GNU/GPL v2 or later http://www.gnu.org/licenses/gpl-2.0.html
  9. *
  10. * Websites: http://www.joomlashine.com
  11. * Technical Support: Feedback - http://www.joomlashine.com/contact-us/get-support.html
  12. */
  13. // No direct access to this file
  14. defined('_JEXEC') or die('Restricted access');
  15. /**
  16. * Sample data installation
  17. *
  18. * @package JSNTPLFramework
  19. * @subpackage Template
  20. * @since 1.0.0
  21. */
  22. class JSNTplWidgetSample extends JSNTplWidgetBase
  23. {
  24. /**
  25. * Template detailed information
  26. * @var array
  27. */
  28. protected $template = array();
  29. /**
  30. * Display agreement screen to ensure start sample
  31. * data installation process
  32. *
  33. * @return void
  34. */
  35. public function confirmAction ()
  36. {
  37. // Render confirm view
  38. $this->render('confirm', array('template' => $this->template));
  39. }
  40. /**
  41. * Render installation screen to display all steps
  42. * we will walking through for install sample data
  43. *
  44. * @return void
  45. */
  46. public function installAction ()
  47. {
  48. $sampleVersion = JSNTplHelper::getJoomlaVersion(2, false);
  49. $fileUrl = 'http://www.joomlashine.com/joomla-templates/';
  50. $fileUrl .= str_replace('_', '-', $this->template['name']) . '-sample-data-j' . $sampleVersion . '.zip';
  51. // Render confirm view
  52. $this->render('install', array(
  53. 'template' => $this->template,
  54. 'fileUrl' => $fileUrl
  55. ));
  56. }
  57. /**
  58. * This method will be install sample data from
  59. * uploaded package
  60. *
  61. * @return void
  62. */
  63. public function uploadInstallAction ()
  64. {
  65. try {
  66. // Move uploaded file to temporary folder
  67. if (isset($_FILES['package']))
  68. {
  69. $package = $_FILES['package'];
  70. $config = JFactory::getConfig();
  71. $tmpPath = $config->get('tmp_path');
  72. $destination = $tmpPath . '/' . $this->template['name'] . '_sampledata.zip';
  73. if (!preg_match('/.zip$/i', $package['name'])) {
  74. throw new Exception(JText::_('JSN_TPLFW_ERROR_UPLOAD_SAMPLE_DATA_PACKAGE_TYPE'));
  75. }
  76. if (move_uploaded_file($package['tmp_name'], $destination)) {
  77. // Import library
  78. jimport('joomla.filesystem.archive');
  79. $path = pathinfo($destination, PATHINFO_DIRNAME) . '/' . pathinfo($destination, PATHINFO_FILENAME);
  80. JPath::clean($path);
  81. JArchive::extract($destination, $path);
  82. $this->installDataAction();
  83. }
  84. }
  85. $response = json_encode(array(
  86. 'type' => 'success',
  87. 'data' => $this->getResponse()
  88. ));
  89. echo "<script type=\"text/javascript\">window.parent.uploadSampleDataCallback({$response})</script>";
  90. jexit();
  91. }
  92. catch (Exception $ex) {
  93. $responseJson = json_encode(array(
  94. 'type' => 'error',
  95. 'data' => $ex->getMessage()
  96. ));
  97. echo "<script type=\"text/javascript\">window.parent.uploadSampleDataCallback({$responseJson})</script>";
  98. jexit();
  99. }
  100. }
  101. /**
  102. * Sample data package will be downloaded to temporary
  103. * folder in this action
  104. *
  105. * @return void
  106. */
  107. public function downloadPackageAction ()
  108. {
  109. if (!JSNTplHelper::isDisabledFunction('set_time_limit')) {
  110. set_time_limit(0);
  111. }
  112. $config = JFactory::getConfig();
  113. $sampleVersion = JSNTplHelper::getJoomlaVersion(2, false);
  114. $httpClient = JSNTplHttpClient::createRequest();
  115. $fileUrl = 'http://www.joomlashine.com/joomla-templates/';
  116. $fileUrl .= str_replace('_', '-', $this->template['name']) . '-sample-data-j' . $sampleVersion . '.zip';
  117. $tmpPath = $config->get('tmp_path');
  118. // Download file to temporary folder
  119. $downloadResult = $httpClient->download($fileUrl, $tmpPath . "/{$this->template['name']}_sampledata.zip");
  120. // Check download response headers
  121. if ($downloadResult->headers['content-type'] != 'application/zip' ||
  122. $downloadResult->code != '200') {
  123. throw new Exception(JText::_('JSN_TPLFW_ERROR_DOWNLOAD_CANNOT_LOCATED_FILE'));
  124. }
  125. $listExtensions = $this->_extractExtensions($tmpPath . "/{$this->template['name']}_sampledata.zip");
  126. $this->setResponse($listExtensions);
  127. }
  128. /**
  129. * Action to execute queries from sample data file
  130. *
  131. * @return void
  132. */
  133. public function installDataAction ()
  134. {
  135. $config = JFactory::getConfig();
  136. $tmpPath = $config->get('tmp_path');
  137. $xmlFiles = glob("{$tmpPath}/{$this->template['name']}_sampledata/*.xml");
  138. if (empty($xmlFiles))
  139. throw new Exception(JText::_('JSN_TPLFW_ERROR_CANNOT_EXTRACT_SAMPLE_DATA_PACKAGE'));
  140. // Load XML document
  141. $xml = simplexml_load_file(current($xmlFiles));
  142. $version = (string) $xml['version'];
  143. // Retrieve template manifest cache
  144. $manifest = JSNTplHelper::getManifestCache($this->template['name']);
  145. if (version_compare($manifest->version, $version, '<')) {
  146. $this->setResponse(array(
  147. 'outOfDate' => true,
  148. 'message' => JText::sprintf('JSN_TPLFW_ERROR_SAMPLE_DATA_OUT_OF_DATED', $manifest->version)
  149. ));
  150. return;
  151. }
  152. // Temporary backup data
  153. $this->_backupThirdPartyModules();
  154. $this->_backupThirdPartyMenus();
  155. // Start transaction before manipulate database
  156. $this->dbo->transactionStart();
  157. // Delete admin modules
  158. $this->_deleteThirdPartyAdminModules();
  159. // Disable execution timeout
  160. if (!JSNTplHelper::isDisabledFunction('set_time_limit')) {
  161. set_time_limit(0);
  162. }
  163. $attentions = array();
  164. // Loop each extension to execute queries
  165. foreach ($xml->xpath('//extension') as $extension)
  166. {
  167. if (isset($extension['author']) && $extension['author'] == 'joomlashine')
  168. {
  169. $extensionType = (string) $extension['type'];
  170. $namePrefix = array('component' => 'com_', 'module' => 'mod_');
  171. $extensionName = isset($namePrefix[(string) $extension['type']])
  172. ? $namePrefix[$extensionType] . $extension['name']
  173. : (string) $extension['name'];
  174. // Checking joomlashine's extension is installed
  175. $canInstall = JSNTplHelper::isInstalledExtension($extensionName);
  176. if ($canInstall == false && $extensionType == 'component') {
  177. // Add to attention list when extension is not installed
  178. $attentions[] = array(
  179. 'id' => (string) $extension['name'],
  180. 'name' => (string) $extension['description'],
  181. 'url' => (string) $extension['producturl']
  182. );
  183. }
  184. }
  185. else {
  186. $canInstall = true;
  187. $extensionName = 'com_' . ((string) $extension['name']);
  188. }
  189. if ($canInstall === true)
  190. {
  191. try {
  192. // Execute sample data queries
  193. foreach ($extension->xpath("task[@name=\"dbinstall\"]/parameters/parameter") as $query)
  194. {
  195. $this->dbo->setQuery((string) $query);
  196. // Execute query
  197. if (!$this->dbo->{$this->queryMethod}())
  198. throw new Exception((string) $query);
  199. }
  200. }
  201. catch (Exception $ex) {}
  202. }
  203. }
  204. $this->_restoreThirdPartyData();
  205. $this->_rebuildMenus();
  206. $styleId = $this->request->getInt('styleId');
  207. // Make other template to not default
  208. $this->dbo->setQuery("UPDATE #__template_styles SET home=0 WHERE client_id=0 AND home=1 LIMIT 1");
  209. $this->dbo->{$this->queryMethod}();
  210. // Make installed template to default
  211. $this->dbo->setQuery("UPDATE #__template_styles SET home=1 WHERE id={$styleId} LIMIT 1");
  212. $this->dbo->{$this->queryMethod}();
  213. // Commit database change
  214. $this->dbo->transactionCommit();
  215. // Clean up temporary data
  216. JInstallerHelper::cleanupInstall("{$tmpPath}/{$this->template['name']}_sampledata.zip", "{$tmpPath}/{$this->template['name']}_sampledata");
  217. $this->setResponse(array(
  218. 'attention' => $attentions
  219. ));
  220. }
  221. /**
  222. * This action will be install extension to Joomla
  223. *
  224. * @return void
  225. */
  226. // public function installExtensionAction ()
  227. // {
  228. // set_time_limit(0);
  229. // $id = $this->request->getString('id');
  230. // if (empty($id)) {
  231. // throw new Exception('Invalid extension ID: ' . $id);
  232. // }
  233. // // Disable debug system
  234. // $config = JFactory::getConfig();
  235. // $config->set('debug', 0);
  236. // $action = JUri::root();
  237. // $action.= sprintf('administrator/index.php?widget=sample&action=install-extension-file&id=%s', $id);
  238. // $action.= sprintf('&%s=%s', $this->session->getName(), $this->session->getId());
  239. // $action.= sprintf('&template=%s', $this->template['name']);
  240. // $http = JSNTplHttpClient::createRequest();
  241. // $response = $http->get($action);
  242. // $decodedContent = json_decode(trim($response->content));
  243. // if ($decodedContent != null && isset($decodedContent->type)) {
  244. // if ($decodedContent->type == 'success')
  245. // return;
  246. // else
  247. // throw new Exception($decodedContent->data);
  248. // }
  249. // else if (strpos($response->content, '&view=installer')) {
  250. // return;
  251. // }
  252. // else {
  253. // throw new Exception("Cannot install extension: {$response->content}");
  254. // }
  255. // $this->setResponse($response->content);
  256. // }
  257. /**
  258. * Action to handle install extension request
  259. *
  260. * @return void
  261. */
  262. public function installExtensionAction ()
  263. {
  264. if (!JSNTplHelper::isDisabledFunction('set_time_limit')) {
  265. set_time_limit(0);
  266. }
  267. $user = JFactory::getUser();
  268. $id = $this->request->getString('id');
  269. $config = JFactory::getConfig();
  270. $tmpPath = $config->get('tmp_path');
  271. // Disable debug system
  272. $config->set('debug', 0);
  273. // Path to sample data file
  274. $xmlFiles = glob("{$tmpPath}/{$this->template['name']}_sampledata/*.xml");
  275. if (empty($xmlFiles))
  276. throw new Exception(JText::_('JSN_TPLFW_ERROR_CANNOT_EXTRACT_SAMPLE_DATA_PACKAGE'));
  277. // Load XML document
  278. $xml = simplexml_load_file(current($xmlFiles));
  279. $extensions = $xml->xpath("//extension[@identifiedname=\"{$id}\"]");
  280. if (!empty($extensions)) {
  281. $extension = current($extensions);
  282. $name = (string) $extension['name'];
  283. $type = (string) $extension['type'];
  284. switch ($type) {
  285. case 'component': $name = 'com_' . $name; break;
  286. case 'module': $name = 'mod_' . $name; break;
  287. }
  288. $this->_cleanExtensionAssets($name);
  289. }
  290. // Download package from lightcart
  291. $packageFile = JSNTplApiLightcart::downloadPackage($id, 'FREE', null, null, "{$tmpPath}/{$this->template['name']}_sampledata/");
  292. if (!is_file($packageFile)) {
  293. throw new Exception("Package file not found: {$packageFile}");
  294. }
  295. // Load extension installation library
  296. jimport('joomla.installer.helper');
  297. // Rebuild menu structure
  298. $this->_rebuildMenus();
  299. $unpackedInfo = JInstallerHelper::unpack($packageFile);
  300. $installer = JInstaller::getInstance();
  301. if (empty($unpackedInfo) || !isset($unpackedInfo['dir'])) {
  302. throw new Exception(JText::_('JSN_TPLFW_ERROR_CANNOT_EXTRACT_EXTENSION_PACKAGE_FILE'));
  303. }
  304. $installResult = $installer->install($unpackedInfo['dir']);
  305. if ($installResult === false) {
  306. foreach (JError::getErrors() as $error) {
  307. throw $error;
  308. }
  309. }
  310. // Clean up temporary data
  311. JInstallerHelper::cleanupInstall($packageFile, $unpackedInfo['dir']);
  312. $this->_activeExtension(array(
  313. 'type' => $type,
  314. 'name' => $name
  315. ));
  316. // Rebuild menu structure
  317. $this->_rebuildMenus();
  318. }
  319. /**
  320. * Action to clean files & database for install failure extension
  321. *
  322. * @return void
  323. */
  324. public function cleanUpAction ()
  325. {
  326. $id = $this->request->getString('id');
  327. // Retrieve temporary path
  328. $config = JFactory::getConfig();
  329. $tmpPath = $config->get('tmp_path');
  330. // Path to sample data file
  331. $xmlFiles = glob("{$tmpPath}/{$this->template['name']}_sampledata/*.xml");
  332. if (empty($xmlFiles))
  333. throw new Exception(JText::_('JSN_TPLFW_ERROR_CANNOT_EXTRACT_SAMPLE_DATA_PACKAGE'));
  334. // Load XML document
  335. $xml = simplexml_load_file(current($xmlFiles));
  336. // Retrieve extension information
  337. $extensions = $xml->xpath("//extension[@identifiedname=\"{$id}\"]");
  338. if (empty($extensions)) {
  339. return;
  340. }
  341. $extension = current($extensions);
  342. // $dependencies = $extension->dependency->children();
  343. // var_dump($extension);
  344. // foreach ($dependencies as $dependency) {
  345. // $dependency = (string) $dependency;
  346. // if ($dependency == 'jsnframework') {
  347. // continue;
  348. // }
  349. // }
  350. }
  351. /**
  352. * Auto enable extension after installed
  353. *
  354. * @param array $extension Extension information that will enabled
  355. *
  356. * @return void
  357. */
  358. private function _activeExtension ($extension)
  359. {
  360. $namePrefix = array('component' => 'com_', 'module' => 'mod_', 'plugin' => '');
  361. $extensionName = $extension['name'];
  362. if (isset($namePrefix[$extension['type']]))
  363. $extensionName = $namePrefix[$extension['type']] . $extension['name'];
  364. $extensionFolder = '';
  365. if (preg_match('/^plugin-([a-z0-9]+)$/i', $extension['type'], $matched)) {
  366. $extensionFolder = $matched[1];
  367. }
  368. $this->dbo->setQuery(sprintf("UPDATE #__extensions SET enabled=1 WHERE element='%s' AND folder='%s'", $extensionName, $extensionFolder));
  369. if (!$this->dbo->{$this->queryMethod}())
  370. throw new Exception($this->dbo->getError());
  371. }
  372. /**
  373. * Parse extension list can installation from sample data
  374. * package
  375. *
  376. * @param string $packageFile Sample data package
  377. * @return array
  378. */
  379. private function _extractExtensions ($packageFile)
  380. {
  381. // Import library
  382. jimport('joomla.filesystem.archive');
  383. $path = pathinfo($packageFile, PATHINFO_DIRNAME) . '/' . pathinfo($packageFile, PATHINFO_FILENAME);
  384. JPath::clean($path);
  385. JArchive::extract($packageFile, $path);
  386. // Find extracted files
  387. $sampleDataFiles = glob("{$path}/*.xml");
  388. if (!is_array($sampleDataFiles) || count($sampleDataFiles) == 0)
  389. throw new Exception(JText::_('JSN_TPLFW_ERROR_CANNOT_EXTRACT_SAMPLE_DATA_PACKAGE'));
  390. // Load XML file
  391. $sampleData = simplexml_load_file(current($sampleDataFiles));
  392. $components = array();
  393. /**
  394. * Looping to each extension type=component to get information
  395. * and dependencies
  396. */
  397. foreach ($sampleData->xpath('//extension[@author="joomlashine"][@type="component"]') as $component)
  398. {
  399. $attrs = (array) $component->attributes();
  400. $attrs = $attrs['@attributes'];
  401. $attrs['name'] = sprintf('com_%s', $attrs['name']);
  402. $attrs['state'] = $this->_getExtensionState($attrs['name'], $attrs['version']);
  403. $attrs['depends'] = array();
  404. foreach ($component->dependency->parameter as $name) {
  405. $dependency = $sampleData->xpath("//extension[@name=\"{$name}\"]");
  406. if (empty($dependency))
  407. continue;
  408. $dependency = current($dependency);
  409. $dependencyAttrs = (array) $dependency->attributes();
  410. $dependencyAttrs = $dependencyAttrs['@attributes'];
  411. $dependencyAttrs['state'] = $this->_getExtensionState($dependencyAttrs['name'], $dependencyAttrs['version']);
  412. if ($dependencyAttrs['type'] == 'module') {
  413. $dependencyAttrs['name'] = sprintf('mod_%s', $dependencyAttrs['name']);
  414. }
  415. $attrs['depends'][] = $dependencyAttrs;
  416. }
  417. $components[] = $attrs;
  418. }
  419. return $components;
  420. }
  421. /**
  422. * This method will be used to find an extension that determined
  423. * by name.
  424. *
  425. * Return "install" when extension does not installed
  426. * Return "update" when extension is installed and is out of date
  427. * Return "installed" when extension is installed and is up to date
  428. *
  429. * @param string $name The name of extension
  430. * @param string $version Version number that used to determine state
  431. *
  432. * @return string
  433. */
  434. private function _getExtensionState ($name, $version)
  435. {
  436. $installedExtensions = JSNTplHelper::findInstalledExtensions();
  437. if (!isset($installedExtensions[$name]))
  438. return 'install';
  439. if (version_compare($installedExtensions[$name]->version, $version, '<'))
  440. return 'update';
  441. return 'installed';
  442. }
  443. /**
  444. * Backup data for third party extensions
  445. * before install sample data
  446. *
  447. * @return void
  448. */
  449. private function _backupThirdPartyModules ()
  450. {
  451. $builtInModules = array(
  452. 'mod_login', 'mod_stats', 'mod_users_latest',
  453. 'mod_footer', 'mod_stats', 'mod_menu', 'mod_articles_latest', 'mod_languages', 'mod_articles_category',
  454. 'mod_whosonline', 'mod_articles_popular', 'mod_articles_archive', 'mod_articles_categories',
  455. 'mod_articles_news', 'mod_related_items', 'mod_search', 'mod_random_image', 'mod_banners',
  456. 'mod_wrapper', 'mod_feed', 'mod_breadcrumbs', 'mod_syndicate', 'mod_custom', 'mod_weblinks'
  457. );
  458. $query = $this->dbo->getQuery(true);
  459. $query->select('*')
  460. ->from('#__modules')
  461. ->where(sprintf('module NOT IN (\'%s\')', implode('\', \'', $builtInModules)))
  462. ->where('id NOT IN (2, 3, 4, 6, 7, 8, 9, 10, 12, 13, 14, 15, 70)')
  463. ->order('client_id ASC');
  464. $this->dbo->setQuery($query);
  465. $this->temporaryModules = $this->dbo->loadAssocList();
  466. }
  467. /**
  468. * Backup menus data for third party extensions
  469. *
  470. * @return void
  471. */
  472. private function _backupThirdPartyMenus ()
  473. {
  474. $query = $this->dbo->getQuery(true);
  475. $query->select('*')
  476. ->from('#__menu')
  477. ->where('client_id=1')
  478. ->where('parent_id=1')
  479. ->order('id ASC');
  480. $this->dbo->setQuery($query);
  481. $this->temporaryMenus = array();
  482. foreach ($this->dbo->loadAssocList() as $row)
  483. {
  484. // Fetch children menus
  485. $query = $this->dbo->getQuery(true);
  486. $query->select('*')
  487. ->from('#__menu')
  488. ->where('client_id=1')
  489. ->where('parent_id=' . $row['id']);
  490. $this->dbo->setQuery($query);
  491. $childrenMenus = $this->dbo->loadAssocList();
  492. // Save temporary menus data
  493. $this->temporaryMenus[] = array(
  494. 'data' => $row,
  495. 'children' => $childrenMenus
  496. );
  497. }
  498. }
  499. /**
  500. * Remove all third party modules in administrator
  501. *
  502. * @return void
  503. */
  504. private function _deleteThirdPartyAdminModules ()
  505. {
  506. $this->dbo->setQuery('DELETE FROM #__modules WHERE `id` NOT IN (2, 3, 4, 8, 9, 10, 12, 13, 14, 15) AND `client_id` = 1');
  507. if (!$this->dbo->{$this->queryMethod}())
  508. throw new Exception($this->dbo->getError());
  509. }
  510. /**
  511. * Restore data for third party extensions
  512. * after install sample data
  513. *
  514. * @return void
  515. */
  516. private function _restoreThirdPartyData ()
  517. {
  518. // Execute temporary queries
  519. foreach ($this->temporaryModules as $module)
  520. {
  521. unset($module['id']);
  522. $tblModule = JTable::getInstance('module');
  523. $tblModule->bind($module);
  524. if (!$tblModule->store())
  525. throw new Exception($tblModule->getError());
  526. }
  527. // Restore administrator menu
  528. foreach ($this->temporaryMenus as $menu)
  529. {
  530. unset($menu['data']['id']);
  531. $mainmenu = JTable::getInstance('menu');
  532. $mainmenu->setLocation(1, 'last-child');
  533. $mainmenu->bind($menu['data']);
  534. if (!$mainmenu->store())
  535. throw new Exception($mainmenu->getError());
  536. if (!empty($menu['children']))
  537. {
  538. foreach ($menu['children'] as $children)
  539. {
  540. $children['id'] = null;
  541. $children['parent_id'] = $mainmenu->id;
  542. $submenu = JTable::getInstance('menu');
  543. $submenu->setLocation($mainmenu->id, 'last-child');
  544. $submenu->bind($children);
  545. if (!$submenu->store())
  546. throw new Exception($submenu->getError());
  547. }
  548. }
  549. }
  550. }
  551. /**
  552. * Rebuild menu structure
  553. *
  554. * @return boolean
  555. */
  556. private function _rebuildMenus ()
  557. {
  558. $table = JTable::getInstance('Menu', 'JTable');
  559. if (!$table->rebuild())
  560. throw new Exception($table->getError());
  561. $query = $this->dbo->getQuery(true);
  562. $query->select('id, params')
  563. ->from('#__menu')
  564. ->where('params NOT LIKE ' . $this->dbo->quote('{%'))
  565. ->where('params <> ' . $this->dbo->quote(''));
  566. $this->dbo->setQuery($query);
  567. $items = $this->dbo->loadObjectList();
  568. if ($error = $this->dbo->getErrorMsg())
  569. throw new Exception($error);
  570. foreach ($items as &$item)
  571. {
  572. $registry = new JRegistry;
  573. $registry->loadString($item->params);
  574. $this->dbo->setQuery('UPDATE #__menu SET params = ' . $this->dbo->quote((string) $registry) . ' WHERE id=' . (int) $item->id);
  575. if (!$this->dbo->{$this->queryMethod}())
  576. throw new Exception($this->dbo->getError());
  577. unset($registry);
  578. }
  579. // Clean the cache
  580. $this->_cleanCache('com_modules');
  581. $this->_cleanCache('mod_menu');
  582. return true;
  583. }
  584. /**
  585. * Remove component's related records in assets table
  586. *
  587. * @param string $name The component name
  588. *
  589. * @return void
  590. */
  591. private function _cleanExtensionAssets ($name)
  592. {
  593. $this->dbo->setQuery("DELETE FROM #__assets WHERE name LIKE '{$name}'");
  594. $this->dbo->{$this->queryMethod}();
  595. }
  596. /**
  597. * Clean cache data for an extension
  598. *
  599. * @param string $extension Name of extension to clean cache
  600. * @return void
  601. */
  602. private function _cleanCache ($extension)
  603. {
  604. $conf = JFactory::getConfig();
  605. $options = array(
  606. 'defaultgroup' => $extension,
  607. 'cachebase' => $conf->get('cache_path', JPATH_SITE . '/cache')
  608. );
  609. jimport('joomla.cache.cache');
  610. $cache = JCache::getInstance('callback', $options);
  611. $cache->clean();
  612. }
  613. }