[ Index ]

PHP Cross Reference of Joomla 2.5.4 DE

title

Body

[close]

/libraries/joomla/application/component/ -> modellist.php (source)

   1  <?php
   2  /**
   3   * @package     Joomla.Platform
   4   * @subpackage  Application
   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  
  10  defined('JPATH_PLATFORM') or die;
  11  
  12  jimport('joomla.application.component.model');
  13  
  14  /**
  15   * Model class for handling lists of items.
  16   *
  17   * @package     Joomla.Platform
  18   * @subpackage  Application
  19   * @since       11.1
  20   */
  21  class JModelList extends JModel
  22  {
  23      /**
  24       * Internal memory based cache array of data.
  25       *
  26       * @var    array
  27       * @since  11.1
  28       */
  29      protected $cache = array();
  30  
  31      /**
  32       * Context string for the model type.  This is used to handle uniqueness
  33       * when dealing with the getStoreId() method and caching data structures.
  34       *
  35       * @var    string
  36       * @since  11.1
  37       */
  38      protected $context = null;
  39  
  40      /**
  41       * Valid filter fields or ordering.
  42       *
  43       * @var    array
  44       * @since  11.1
  45       */
  46      protected $filter_fields = array();
  47  
  48      /**
  49       * An internal cache for the last query used.
  50       *
  51       * @var    JDatabaseQuery
  52       * @since  11.1
  53       */
  54      protected $query = array();
  55  
  56      /**
  57       * Constructor.
  58       *
  59       * @param   array  $config  An optional associative array of configuration settings.
  60       *
  61       * @see     JController
  62       * @since   11.1
  63       */
  64  	public function __construct($config = array())
  65      {
  66          parent::__construct($config);
  67  
  68          // Add the ordering filtering fields white list.
  69          if (isset($config['filter_fields']))
  70          {
  71              $this->filter_fields = $config['filter_fields'];
  72          }
  73  
  74          // Guess the context as Option.ModelName.
  75          if (empty($this->context))
  76          {
  77              $this->context = strtolower($this->option . '.' . $this->getName());
  78          }
  79      }
  80  
  81      /**
  82       * Method to cache the last query constructed.
  83       *
  84       * This method ensures that the query is constructed only once for a given state of the model.
  85       *
  86       * @return  JDatabaseQuery  A JDatabaseQuery object
  87       *
  88       * @since   11.1
  89       */
  90  	protected function _getListQuery()
  91      {
  92          // Capture the last store id used.
  93          static $lastStoreId;
  94  
  95          // Compute the current store id.
  96          $currentStoreId = $this->getStoreId();
  97  
  98          // If the last store id is different from the current, refresh the query.
  99          if ($lastStoreId != $currentStoreId || empty($this->query))
 100          {
 101              $lastStoreId = $currentStoreId;
 102              $this->query = $this->getListQuery();
 103          }
 104  
 105          return $this->query;
 106      }
 107  
 108      /**
 109       * Method to get an array of data items.
 110       *
 111       * @return  mixed  An array of data items on success, false on failure.
 112       *
 113       * @since   11.1
 114       */
 115  	public function getItems()
 116      {
 117          // Get a storage key.
 118          $store = $this->getStoreId();
 119  
 120          // Try to load the data from internal storage.
 121          if (isset($this->cache[$store]))
 122          {
 123              return $this->cache[$store];
 124          }
 125  
 126          // Load the list items.
 127          $query = $this->_getListQuery();
 128          $items = $this->_getList($query, $this->getStart(), $this->getState('list.limit'));
 129  
 130          // Check for a database error.
 131          if ($this->_db->getErrorNum())
 132          {
 133              $this->setError($this->_db->getErrorMsg());
 134              return false;
 135          }
 136  
 137          // Add the items to the internal cache.
 138          $this->cache[$store] = $items;
 139  
 140          return $this->cache[$store];
 141      }
 142  
 143      /**
 144       * Method to get a JDatabaseQuery object for retrieving the data set from a database.
 145       *
 146       * @return  JDatabaseQuery   A JDatabaseQuery object to retrieve the data set.
 147       *
 148       * @since   11.1
 149       */
 150  	protected function getListQuery()
 151      {
 152          $db = $this->getDbo();
 153          $query = $db->getQuery(true);
 154  
 155          return $query;
 156      }
 157  
 158      /**
 159       * Method to get a JPagination object for the data set.
 160       *
 161       * @return  JPagination  A JPagination object for the data set.
 162       *
 163       * @since   11.1
 164       */
 165  	public function getPagination()
 166      {
 167          // Get a storage key.
 168          $store = $this->getStoreId('getPagination');
 169  
 170          // Try to load the data from internal storage.
 171          if (isset($this->cache[$store]))
 172          {
 173              return $this->cache[$store];
 174          }
 175  
 176          // Create the pagination object.
 177          jimport('joomla.html.pagination');
 178          $limit = (int) $this->getState('list.limit') - (int) $this->getState('list.links');
 179          $page = new JPagination($this->getTotal(), $this->getStart(), $limit);
 180  
 181          // Add the object to the internal cache.
 182          $this->cache[$store] = $page;
 183  
 184          return $this->cache[$store];
 185      }
 186  
 187      /**
 188       * Method to get a store id based on the model configuration state.
 189       *
 190       * This is necessary because the model is used by the component and
 191       * different modules that might need different sets of data or different
 192       * ordering requirements.
 193       *
 194       * @param   string  $id  An identifier string to generate the store id.
 195       *
 196       * @return  string  A store id.
 197       *
 198       * @since   11.1
 199       */
 200  	protected function getStoreId($id = '')
 201      {
 202          // Add the list state to the store id.
 203          $id .= ':' . $this->getState('list.start');
 204          $id .= ':' . $this->getState('list.limit');
 205          $id .= ':' . $this->getState('list.ordering');
 206          $id .= ':' . $this->getState('list.direction');
 207  
 208          return md5($this->context . ':' . $id);
 209      }
 210  
 211      /**
 212       * Method to get the total number of items for the data set.
 213       *
 214       * @return  integer  The total number of items available in the data set.
 215       *
 216       * @since   11.1
 217       */
 218  	public function getTotal()
 219      {
 220          // Get a storage key.
 221          $store = $this->getStoreId('getTotal');
 222  
 223          // Try to load the data from internal storage.
 224          if (isset($this->cache[$store]))
 225          {
 226              return $this->cache[$store];
 227          }
 228  
 229          // Load the total.
 230          $query = $this->_getListQuery();
 231          $total = (int) $this->_getListCount($query);
 232  
 233          // Check for a database error.
 234          if ($this->_db->getErrorNum())
 235          {
 236              $this->setError($this->_db->getErrorMsg());
 237              return false;
 238          }
 239  
 240          // Add the total to the internal cache.
 241          $this->cache[$store] = $total;
 242  
 243          return $this->cache[$store];
 244      }
 245  
 246      /**
 247       * Method to get the starting number of items for the data set.
 248       *
 249       * @return  integer  The starting number of items available in the data set.
 250       *
 251       * @since   11.1
 252       */
 253  	public function getStart()
 254      {
 255          $store = $this->getStoreId('getstart');
 256  
 257          // Try to load the data from internal storage.
 258          if (isset($this->cache[$store]))
 259          {
 260              return $this->cache[$store];
 261          }
 262  
 263          $start = $this->getState('list.start');
 264          $limit = $this->getState('list.limit');
 265          $total = $this->getTotal();
 266          if ($start > $total - $limit)
 267          {
 268              $start = max(0, (int) (ceil($total / $limit) - 1) * $limit);
 269          }
 270  
 271          // Add the total to the internal cache.
 272          $this->cache[$store] = $start;
 273  
 274          return $this->cache[$store];
 275      }
 276  
 277      /**
 278       * Method to auto-populate the model state.
 279       *
 280       * This method should only be called once per instantiation and is designed
 281       * to be called on the first call to the getState() method unless the model
 282       * configuration flag to ignore the request is set.
 283       *
 284       * Note. Calling getState in this method will result in recursion.
 285       *
 286       * @param   string  $ordering   An optional ordering field.
 287       * @param   string  $direction  An optional direction (asc|desc).
 288       *
 289       * @return  void
 290       *
 291       * @since   11.1
 292       */
 293  	protected function populateState($ordering = null, $direction = null)
 294      {
 295          // If the context is set, assume that stateful lists are used.
 296          if ($this->context)
 297          {
 298              $app = JFactory::getApplication();
 299  
 300              $value = $app->getUserStateFromRequest('global.list.limit', 'limit', $app->getCfg('list_limit'));
 301              $limit = $value;
 302              $this->setState('list.limit', $limit);
 303  
 304              $value = $app->getUserStateFromRequest($this->context . '.limitstart', 'limitstart', 0);
 305              $limitstart = ($limit != 0 ? (floor($value / $limit) * $limit) : 0);
 306              $this->setState('list.start', $limitstart);
 307  
 308              // Check if the ordering field is in the white list, otherwise use the incoming value.
 309              $value = $app->getUserStateFromRequest($this->context . '.ordercol', 'filter_order', $ordering);
 310              if (!in_array($value, $this->filter_fields))
 311              {
 312                  $value = $ordering;
 313                  $app->setUserState($this->context . '.ordercol', $value);
 314              }
 315              $this->setState('list.ordering', $value);
 316  
 317              // Check if the ordering direction is valid, otherwise use the incoming value.
 318              $value = $app->getUserStateFromRequest($this->context . '.orderdirn', 'filter_order_Dir', $direction);
 319              if (!in_array(strtoupper($value), array('ASC', 'DESC', '')))
 320              {
 321                  $value = $direction;
 322                  $app->setUserState($this->context . '.orderdirn', $value);
 323              }
 324              $this->setState('list.direction', $value);
 325          }
 326          else
 327          {
 328              $this->setState('list.start', 0);
 329              $this->state->set('list.limit', 0);
 330          }
 331      }
 332  
 333      /**
 334       * Gets the value of a user state variable and sets it in the session
 335       *
 336       * This is the same as the method in JApplication except that this also can optionally
 337       * force you back to the first page when a filter has changed
 338       *
 339       * @param   string   $key        The key of the user state variable.
 340       * @param   string   $request    The name of the variable passed in a request.
 341       * @param   string   $default    The default value for the variable if not found. Optional.
 342       * @param   string   $type       Filter for the variable, for valid values see {@link JFilterInput::clean()}. Optional.
 343       * @param   boolean  $resetPage  If true, the limitstart in request is set to zero
 344       *
 345       * @return  The request user state.
 346       *
 347       * @since   11.1
 348       */
 349  	public function getUserStateFromRequest($key, $request, $default = null, $type = 'none', $resetPage = true)
 350      {
 351          $app = JFactory::getApplication();
 352          $old_state = $app->getUserState($key);
 353          $cur_state = (!is_null($old_state)) ? $old_state : $default;
 354          $new_state = JRequest::getVar($request, null, 'default', $type);
 355  
 356          if (($cur_state != $new_state) && ($resetPage))
 357          {
 358              JRequest::setVar('limitstart', 0);
 359          }
 360  
 361          // Save the new value only if it is set in this request.
 362          if ($new_state !== null)
 363          {
 364              $app->setUserState($key, $new_state);
 365          }
 366          else
 367          {
 368              $new_state = $cur_state;
 369          }
 370  
 371          return $new_state;
 372      }
 373  }


Generated: Tue Apr 3 11:40:28 2012 Cross-referenced by PHPXref 0.7.1