[ Index ] |
PHP Cross Reference of Joomla 4.2.2 documentation |
[Summary view] [Print] [Text view]
1 <?php 2 3 /** 4 * @package Joomla.Administrator 5 * @subpackage com_tags 6 * 7 * @copyright (C) 2013 Open Source Matters, Inc. <https://www.joomla.org> 8 * @license GNU General Public License version 2 or later; see LICENSE.txt 9 */ 10 11 namespace Joomla\Component\Tags\Administrator\Model; 12 13 use Joomla\CMS\Component\ComponentHelper; 14 use Joomla\CMS\Factory; 15 use Joomla\CMS\MVC\Factory\MVCFactoryInterface; 16 use Joomla\CMS\MVC\Model\ListModel; 17 use Joomla\CMS\Tag\TagServiceInterface; 18 use Joomla\Database\DatabaseQuery; 19 use Joomla\Database\ParameterType; 20 21 // phpcs:disable PSR1.Files.SideEffects 22 \defined('_JEXEC') or die; 23 // phpcs:enable PSR1.Files.SideEffects 24 25 /** 26 * Tags Component Tags Model 27 * 28 * @since 3.1 29 */ 30 class TagsModel extends ListModel 31 { 32 /** 33 * Constructor. 34 * 35 * @param MVCFactoryInterface $factory The factory. 36 * 37 * @param array $config An optional associative array of configuration settings. 38 * 39 * @since 1.6 40 */ 41 public function __construct($config = array(), MVCFactoryInterface $factory = null) 42 { 43 if (empty($config['filter_fields'])) { 44 $config['filter_fields'] = array( 45 'id', 46 'a.id', 47 'title', 48 'a.title', 49 'alias', 50 'a.alias', 51 'published', 52 'a.published', 53 'access', 54 'a.access', 55 'access_level', 56 'language', 57 'a.language', 58 'checked_out', 59 'a.checked_out', 60 'checked_out_time', 61 'a.checked_out_time', 62 'created_time', 63 'a.created_time', 64 'created_user_id', 65 'a.created_user_id', 66 'lft', 67 'a.lft', 68 'rgt', 69 'a.rgt', 70 'level', 71 'a.level', 72 'path', 73 'a.path', 74 'countTaggedItems', 75 ); 76 } 77 78 parent::__construct($config, $factory); 79 } 80 81 /** 82 * Method to auto-populate the model state. 83 * 84 * Note. Calling getState in this method will result in recursion. 85 * 86 * @param string $ordering An optional ordering field. 87 * @param string $direction An optional direction (asc|desc). 88 * 89 * @return void 90 * 91 * @since 3.1 92 */ 93 protected function populateState($ordering = 'a.lft', $direction = 'asc') 94 { 95 $extension = $this->getUserStateFromRequest($this->context . '.filter.extension', 'extension', 'com_content', 'cmd'); 96 97 $this->setState('filter.extension', $extension); 98 $parts = explode('.', $extension); 99 100 // Extract the component name 101 $this->setState('filter.component', $parts[0]); 102 103 // Extract the optional section name 104 $this->setState('filter.section', (count($parts) > 1) ? $parts[1] : null); 105 106 // Load the parameters. 107 $params = ComponentHelper::getParams('com_tags'); 108 $this->setState('params', $params); 109 110 // List state information. 111 parent::populateState($ordering, $direction); 112 } 113 114 /** 115 * Method to get a store id based on model configuration state. 116 * 117 * This is necessary because the model is used by the component and 118 * different modules that might need different sets of data or different 119 * ordering requirements. 120 * 121 * @param string $id A prefix for the store id. 122 * 123 * @return string A store id. 124 * 125 * @since 3.1 126 */ 127 protected function getStoreId($id = '') 128 { 129 // Compile the store id. 130 $id .= ':' . $this->getState('filter.extension'); 131 $id .= ':' . $this->getState('filter.search'); 132 $id .= ':' . $this->getState('filter.level'); 133 $id .= ':' . $this->getState('filter.access'); 134 $id .= ':' . $this->getState('filter.published'); 135 $id .= ':' . $this->getState('filter.language'); 136 137 return parent::getStoreId($id); 138 } 139 140 /** 141 * Method to create a query for a list of items. 142 * 143 * @return string 144 * 145 * @since 3.1 146 */ 147 protected function getListQuery() 148 { 149 // Create a new query object. 150 $db = $this->getDatabase(); 151 $query = $db->getQuery(true); 152 $user = Factory::getUser(); 153 154 // Select the required fields from the table. 155 $query->select( 156 $this->getState( 157 'list.select', 158 'a.id, a.title, a.alias, a.note, a.published, a.access, a.description' . 159 ', a.checked_out, a.checked_out_time, a.created_user_id' . 160 ', a.path, a.parent_id, a.level, a.lft, a.rgt' . 161 ', a.language' 162 ) 163 ); 164 $query->from($db->quoteName('#__tags', 'a')) 165 ->where($db->quoteName('a.alias') . ' <> ' . $db->quote('root')); 166 167 // Join over the language 168 $query->select( 169 [ 170 $db->quoteName('l.title', 'language_title'), 171 $db->quoteName('l.image', 'language_image'), 172 ] 173 ) 174 ->join('LEFT', $db->quoteName('#__languages', 'l'), $db->quoteName('l.lang_code') . ' = ' . $db->quoteName('a.language')); 175 176 // Join over the users for the checked out user. 177 $query->select($db->quoteName('uc.name', 'editor')) 178 ->join('LEFT', $db->quoteName('#__users', 'uc'), $db->quoteName('uc.id') . ' = ' . $db->quoteName('a.checked_out')); 179 180 // Join over the users for the author. 181 $query->select($db->quoteName('ua.name', 'author_name')) 182 ->join('LEFT', $db->quoteName('#__users', 'ua'), $db->quoteName('ua.id') . ' = ' . $db->quoteName('a.created_user_id')) 183 ->select($db->quoteName('ug.title', 'access_title')) 184 ->join('LEFT', $db->quoteName('#__viewlevels', 'ug'), $db->quoteName('ug.id') . ' = ' . $db->quoteName('a.access')); 185 186 // Count Items 187 $subQueryCountTaggedItems = $db->getQuery(true); 188 $subQueryCountTaggedItems 189 ->select('COUNT(' . $db->quoteName('tag_map.content_item_id') . ')') 190 ->from($db->quoteName('#__contentitem_tag_map', 'tag_map')) 191 ->where($db->quoteName('tag_map.tag_id') . ' = ' . $db->quoteName('a.id')); 192 $query->select('(' . (string) $subQueryCountTaggedItems . ') AS ' . $db->quoteName('countTaggedItems')); 193 194 // Filter on the level. 195 if ($level = (int) $this->getState('filter.level')) { 196 $query->where($db->quoteName('a.level') . ' <= :level') 197 ->bind(':level', $level, ParameterType::INTEGER); 198 } 199 200 // Filter by access level. 201 if ($access = (int) $this->getState('filter.access')) { 202 $query->where($db->quoteName('a.access') . ' = :access') 203 ->bind(':access', $access, ParameterType::INTEGER); 204 } 205 206 // Implement View Level Access 207 if (!$user->authorise('core.admin')) { 208 $groups = $user->getAuthorisedViewLevels(); 209 $query->whereIn($db->quoteName('a.access'), $groups); 210 } 211 212 // Filter by published state 213 $published = (string) $this->getState('filter.published'); 214 215 if (is_numeric($published)) { 216 $published = (int) $published; 217 $query->where($db->quoteName('a.published') . ' = :published') 218 ->bind(':published', $published, ParameterType::INTEGER); 219 } elseif ($published === '') { 220 $query->whereIn($db->quoteName('a.published'), [0, 1]); 221 } 222 223 // Filter by search in title 224 $search = $this->getState('filter.search'); 225 226 if (!empty($search)) { 227 if (stripos($search, 'id:') === 0) { 228 $ids = (int) substr($search, 3); 229 $query->where($db->quoteName('a.id') . ' = :id') 230 ->bind(':id', $ids, ParameterType::INTEGER); 231 } else { 232 $search = '%' . str_replace(' ', '%', trim($search)) . '%'; 233 $query->extendWhere( 234 'AND', 235 [ 236 $db->quoteName('a.title') . ' LIKE :title', 237 $db->quoteName('a.alias') . ' LIKE :alias', 238 $db->quoteName('a.note') . ' LIKE :note', 239 240 ], 241 'OR' 242 ); 243 $query->bind(':title', $search) 244 ->bind(':alias', $search) 245 ->bind(':note', $search); 246 } 247 } 248 249 // Filter on the language. 250 if ($language = $this->getState('filter.language')) { 251 $query->where($db->quoteName('a.language') . ' = :language') 252 ->bind(':language', $language); 253 } 254 255 // Add the list ordering clause 256 $listOrdering = $this->getState('list.ordering', 'a.lft'); 257 $listDirn = $db->escape($this->getState('list.direction', 'ASC')); 258 259 if ($listOrdering == 'a.access') { 260 $query->order('a.access ' . $listDirn . ', a.lft ' . $listDirn); 261 } else { 262 $query->order($db->escape($listOrdering) . ' ' . $listDirn); 263 } 264 265 return $query; 266 } 267 268 /** 269 * Method to get an array of data items. 270 * 271 * @return mixed An array of data items on success, false on failure. 272 * 273 * @since 3.0.1 274 */ 275 public function getItems() 276 { 277 $items = parent::getItems(); 278 279 if ($items != false) { 280 $extension = $this->getState('filter.extension'); 281 282 $this->countItems($items, $extension); 283 } 284 285 return $items; 286 } 287 288 /** 289 * Method to load the countItems method from the extensions 290 * 291 * @param \stdClass[] &$items The category items 292 * @param string $extension The category extension 293 * 294 * @return void 295 * 296 * @since 3.5 297 */ 298 public function countItems(&$items, $extension) 299 { 300 $parts = explode('.', $extension); 301 302 if (count($parts) < 2) { 303 return; 304 } 305 306 $component = Factory::getApplication()->bootComponent($parts[0]); 307 308 if ($component instanceof TagServiceInterface) { 309 $component->countTagItems($items, $extension); 310 } 311 } 312 313 /** 314 * Manipulate the query to be used to evaluate if this is an Empty State to provide specific conditions for this extension. 315 * 316 * @return DatabaseQuery 317 * 318 * @since 4.0.0 319 */ 320 protected function getEmptyStateQuery() 321 { 322 $query = parent::getEmptyStateQuery(); 323 324 $db = $this->getDatabase(); 325 326 $query->where($db->quoteName('alias') . ' != ' . $db->quote('root')); 327 328 return $query; 329 } 330 }
title
Description
Body
title
Description
Body
title
Description
Body
title
Body
Generated: Wed Sep 7 05:41:13 2022 | Chilli.vc Blog - For Webmaster,Blog-Writer,System Admin and Domainer |