Joomla Platform  13.1
Documentation des API du framework Joomla Platform
 Tout Classes Espaces de nommage Fichiers Fonctions Variables Pages
callback.php
Aller à la documentation de ce fichier.
1 <?php
2 /**
3  * @package Joomla.Platform
4  * @subpackage Cache
5  *
6  * @copyright Copyright (C) 2005 - 2013 Open Source Matters, Inc. All rights reserved.
7  * @license GNU General Public License version 2 or later; see LICENSE
8  */
9 
10 defined('JPATH_PLATFORM') or die;
11 
12 /**
13  * Joomla! Cache callback type object
14  *
15  * @package Joomla.Platform
16  * @subpackage Cache
17  * @since 11.1
18  */
20 {
21  /**
22  * Executes a cacheable callback if not found in cache else returns cached output and result
23  *
24  * Since arguments to this function are read with func_get_args you can pass any number of
25  * arguments to this method
26  * as long as the first argument passed is the callback definition.
27  *
28  * The callback definition can be in several forms:
29  * - Standard PHP Callback array see <http://php.net/callback> [recommended]
30  * - Function name as a string eg. 'foo' for function foo()
31  * - Static method name as a string eg. 'MyClass::myMethod' for method myMethod() of class MyClass
32  *
33  * @return mixed Result of the callback
34  *
35  * @since 11.1
36  */
37  public function call()
38  {
39  // Get callback and arguments
40  $args = func_get_args();
41  $callback = array_shift($args);
42 
43  return $this->get($callback, $args);
44  }
45 
46  /**
47  * Executes a cacheable callback if not found in cache else returns cached output and result
48  *
49  * @param mixed $callback Callback or string shorthand for a callback
50  * @param array $args Callback arguments
51  * @param string $id Cache id
52  * @param boolean $wrkarounds True to use wrkarounds
53  * @param array $woptions Workaround options
54  *
55  * @return mixed Result of the callback
56  *
57  * @since 11.1
58  */
59  public function get($callback, $args = array(), $id = false, $wrkarounds = false, $woptions = array())
60  {
61 
62  // Normalize callback
63  if (is_array($callback))
64  {
65  // We have a standard php callback array -- do nothing
66  }
67  elseif (strstr($callback, '::'))
68  {
69  // This is shorthand for a static method callback classname::methodname
70  list ($class, $method) = explode('::', $callback);
71  $callback = array(trim($class), trim($method));
72  }
73  elseif (strstr($callback, '->'))
74  {
75  /*
76  * This is a really not so smart way of doing this... we provide this for backward compatability but this
77  * WILL! disappear in a future version. If you are using this syntax change your code to use the standard
78  * PHP callback array syntax: <http://php.net/callback>
79  *
80  * We have to use some silly global notation to pull it off and this is very unreliable
81  */
82  list ($object_123456789, $method) = explode('->', $callback);
83  global $$object_123456789;
84  $callback = array($$object_123456789, $method);
85  }
86  else
87  {
88  // We have just a standard function -- do nothing
89  }
90 
91  if (!$id)
92  {
93  // Generate an ID
94  $id = $this->_makeId($callback, $args);
95  }
96 
97  $data = $this->cache->get($id);
98 
99  $locktest = new stdClass;
100  $locktest->locked = null;
101  $locktest->locklooped = null;
102 
103  if ($data === false)
104  {
105  $locktest = $this->cache->lock($id);
106  if ($locktest->locked == true && $locktest->locklooped == true)
107  {
108  $data = $this->cache->get($id);
109  }
110  }
111 
112  $coptions = array();
113 
114  if ($data !== false)
115  {
116 
117  $cached = unserialize(trim($data));
118  $coptions['mergehead'] = isset($woptions['mergehead']) ? $woptions['mergehead'] : 0;
119  $output = ($wrkarounds == false) ? $cached['output'] : JCache::getWorkarounds($cached['output'], $coptions);
120  $result = $cached['result'];
121  if ($locktest->locked == true)
122  {
123  $this->cache->unlock($id);
124  }
125 
126  }
127  else
128  {
129 
130  if (!is_array($args))
131  {
132  $Args = !empty($args) ? array(&$args) : array();
133  }
134  else
135  {
136  $Args = &$args;
137  }
138 
139  if ($locktest->locked == false)
140  {
141  $locktest = $this->cache->lock($id);
142  }
143 
144  if (isset($woptions['modulemode']) && $woptions['modulemode'] == 1)
145  {
146  $document = JFactory::getDocument();
147  $coptions['modulemode'] = 1;
148  $coptions['headerbefore'] = $document->getHeadData();
149  }
150  else
151  {
152  $coptions['modulemode'] = 0;
153  }
154 
155  ob_start();
156  ob_implicit_flush(false);
157 
158  $result = call_user_func_array($callback, $Args);
159  $output = ob_get_contents();
160 
161  ob_end_clean();
162 
163  $cached = array();
164 
165  $coptions['nopathway'] = isset($woptions['nopathway']) ? $woptions['nopathway'] : 1;
166  $coptions['nohead'] = isset($woptions['nohead']) ? $woptions['nohead'] : 1;
167  $coptions['nomodules'] = isset($woptions['nomodules']) ? $woptions['nomodules'] : 1;
168 
169  $cached['output'] = ($wrkarounds == false) ? $output : JCache::setWorkarounds($output, $coptions);
170  $cached['result'] = $result;
171 
172  // Store the cache data
173  $this->cache->store(serialize($cached), $id);
174  if ($locktest->locked == true)
175  {
176  $this->cache->unlock($id);
177  }
178  }
179 
180  echo $output;
181  return $result;
182  }
183 
184  /**
185  * Generate a callback cache id
186  *
187  * @param callback $callback Callback to cache
188  * @param array $args Arguments to the callback method to cache
189  *
190  * @return string MD5 Hash : function cache id
191  *
192  * @since 11.1
193  */
194  protected function _makeId($callback, $args)
195  {
196  if (is_array($callback) && is_object($callback[0]))
197  {
198  $vars = get_object_vars($callback[0]);
199  $vars[] = strtolower(get_class($callback[0]));
200  $callback[0] = $vars;
201  }
202 
203  return md5(serialize(array($callback, $args)));
204  }
205 }