vendor/pimcore/pimcore/lib/Model/Listing/AbstractListing.php line 595

Open in your IDE?
  1. <?php
  2. /**
  3.  * Pimcore
  4.  *
  5.  * This source file is available under two different licenses:
  6.  * - GNU General Public License version 3 (GPLv3)
  7.  * - Pimcore Commercial License (PCL)
  8.  * Full copyright and license information is available in
  9.  * LICENSE.md which is distributed with this source code.
  10.  *
  11.  *  @copyright  Copyright (c) Pimcore GmbH (http://www.pimcore.org)
  12.  *  @license    http://www.pimcore.org/license     GPLv3 and PCL
  13.  */
  14. namespace Pimcore\Model\Listing;
  15. use Doctrine\DBAL\Connection;
  16. use Doctrine\DBAL\Query\QueryBuilder;
  17. use Pimcore\Db;
  18. use Pimcore\Db\Helper;
  19. use Pimcore\Model\AbstractModel;
  20. use Pimcore\Model\Listing\Dao\AbstractDao;
  21. /**
  22.  * @method AbstractDao getDao()
  23.  * @method QueryBuilder getQueryBuilder()
  24.  */
  25. abstract class AbstractListing extends AbstractModel implements \Iterator\Countable
  26. {
  27.     /**
  28.      * @var array
  29.      */
  30.     protected $order = [];
  31.     /**
  32.      * @var array
  33.      */
  34.     protected $orderKey = [];
  35.     /**
  36.      * @var int|null
  37.      */
  38.     protected $limit;
  39.     /**
  40.      * @var int|null
  41.      */
  42.     protected $offset;
  43.     /**
  44.      * @var string|null
  45.      */
  46.     protected $condition;
  47.     /**
  48.      * @var array
  49.      */
  50.     protected $conditionVariables = [];
  51.     /**
  52.      * @var array|null
  53.      */
  54.     protected $conditionVariablesFromSetCondition;
  55.     /**
  56.      * @var string|null
  57.      */
  58.     protected $groupBy;
  59.     /**
  60.      * @var array
  61.      */
  62.     protected $validOrders = [
  63.         'ASC',
  64.         'DESC',
  65.     ];
  66.     /**
  67.      * @var array
  68.      */
  69.     protected $conditionParams = [];
  70.     /**
  71.      * @var array
  72.      */
  73.     protected $conditionVariableTypes = [];
  74.     /**
  75.      * @var array|null
  76.      */
  77.     protected $data;
  78.     /**
  79.      * @return array
  80.      */
  81.     public function getConditionVariableTypes(): array
  82.     {
  83.         if (!$this->conditionVariables) {
  84.             $this->getCondition();
  85.         }
  86.         return $this->conditionVariableTypes;
  87.     }
  88.     /**
  89.      * @param array $conditionVariableTypes
  90.      */
  91.     public function setConditionVariableTypes(array $conditionVariableTypes): void
  92.     {
  93.         $this->conditionVariableTypes $conditionVariableTypes;
  94.     }
  95.     /**
  96.      * @param string $key
  97.      *
  98.      * @return bool
  99.      */
  100.     public function isValidOrderKey($key)
  101.     {
  102.         return true;
  103.     }
  104.     /**
  105.      * @return int|null
  106.      */
  107.     public function getLimit()
  108.     {
  109.         return $this->limit;
  110.     }
  111.     /**
  112.      * @return int|null
  113.      */
  114.     public function getOffset()
  115.     {
  116.         return $this->offset;
  117.     }
  118.     /**
  119.      * @return array
  120.      */
  121.     public function getOrder()
  122.     {
  123.         return $this->order;
  124.     }
  125.     /**
  126.      * @param int $limit
  127.      *
  128.      * @return $this
  129.      */
  130.     public function setLimit($limit)
  131.     {
  132.         $this->setData(null);
  133.         if ((int)$limit 0) {
  134.             $this->limit = (int)$limit;
  135.         }
  136.         return $this;
  137.     }
  138.     /**
  139.      * @param int $offset
  140.      *
  141.      * @return $this
  142.      */
  143.     public function setOffset($offset)
  144.     {
  145.         $this->setData(null);
  146.         if ((int)$offset >= 0) {
  147.             $this->offset = (int)$offset;
  148.         }
  149.         return $this;
  150.     }
  151.     /**
  152.      * @param array|string $order
  153.      *
  154.      * @return $this
  155.      */
  156.     public function setOrder($order)
  157.     {
  158.         $this->setData(null);
  159.         $this->order = [];
  160.         if (!empty($order)) {
  161.             if (is_string($order)) {
  162.                 $order strtoupper($order);
  163.                 if (in_array($order$this->validOrders)) {
  164.                     $this->order[] = $order;
  165.                 }
  166.             } elseif (is_array($order)) {
  167.                 foreach ($order as $o) {
  168.                     $o strtoupper($o);
  169.                     if (in_array($o$this->validOrders)) {
  170.                         $this->order[] = $o;
  171.                     }
  172.                 }
  173.             }
  174.         }
  175.         return $this;
  176.     }
  177.     /**
  178.      * @return array
  179.      */
  180.     public function getOrderKey()
  181.     {
  182.         return $this->orderKey;
  183.     }
  184.     /**
  185.      * @param string|array $orderKey
  186.      * @param bool $quote
  187.      *
  188.      * @return $this
  189.      */
  190.     public function setOrderKey($orderKey$quote true)
  191.     {
  192.         $this->setData(null);
  193.         $this->orderKey = [];
  194.         if (is_string($orderKey) && !empty($orderKey)) {
  195.             $orderKey = [$orderKey];
  196.         }
  197.         if (is_array($orderKey)) {
  198.             foreach ($orderKey as $o) {
  199.                 if ($quote === false) {
  200.                     $this->orderKey[] = $o;
  201.                 } elseif ($this->isValidOrderKey($o)) {
  202.                     $this->orderKey[] = $this->quoteIdentifier($o);
  203.                 }
  204.             }
  205.         }
  206.         return $this;
  207.     }
  208.     /**
  209.      * @param string $condition
  210.      * @param mixed $value
  211.      * @param string $concatenator
  212.      *
  213.      * @return $this
  214.      */
  215.     public function addConditionParam($condition$value null$concatenator 'AND')
  216.     {
  217.         $this->setData(null);
  218.         $condition '('.$condition.')';
  219.         $ignoreParameter true;
  220.         $conditionWithoutQuotedStrings preg_replace('/["\'][^"\']*?["\']/'''$condition);
  221.         if (str_contains($conditionWithoutQuotedStrings'?') || str_contains($conditionWithoutQuotedStrings':')) {
  222.             $ignoreParameter false;
  223.         }
  224.         $this->conditionParams[$condition] = [
  225.             'value' => $value,
  226.             'concatenator' => $concatenator,
  227.             'ignore-value' => $ignoreParameter// If there is not a placeholder, ignore value!
  228.         ];
  229.         return $this;
  230.     }
  231.     /**
  232.      * @return array
  233.      */
  234.     public function getConditionParams()
  235.     {
  236.         return $this->conditionParams;
  237.     }
  238.     /**
  239.      * @return $this
  240.      */
  241.     public function resetConditionParams()
  242.     {
  243.         $this->setData(null);
  244.         $this->conditionParams = [];
  245.         return $this;
  246.     }
  247.     /**
  248.      * @return string
  249.      */
  250.     public function getCondition()
  251.     {
  252.         $conditionString '';
  253.         $conditionVariableTypes = [];
  254.         $conditionParams $this->getConditionParams();
  255.         $params = [];
  256.         if (!empty($conditionParams)) {
  257.             $i 0;
  258.             foreach ($conditionParams as $key => $value) {
  259.                 if (!$this->condition && $i == 0) {
  260.                     $conditionString .= $key ' ';
  261.                 } else {
  262.                     $conditionString .= ' ' $value['concatenator'] . ' ' $key ' ';
  263.                 }
  264.                 // If there is not a placeholder, ignore value!
  265.                 if (!$value['ignore-value']) {
  266.                     if (is_array($value['value'])) {
  267.                         foreach ($value['value'] as $k => $v) {
  268.                             if (is_int($k)) {
  269.                                 $params[] = $v;
  270.                             } else {
  271.                                 $params[$k] = $v;
  272.                             }
  273.                         }
  274.                     } else {
  275.                         $params[] = $value['value'];
  276.                     }
  277.                 }
  278.                 $i++;
  279.             }
  280.         }
  281.         $params array_merge((array) $this->getConditionVariablesFromSetCondition(), $params);
  282.         $this->setConditionVariables($params);
  283.         foreach ($params as $pkey => $param) {
  284.             if (is_array($param)) {
  285.                 if (isset($param[0]) && is_string($param[0])) {
  286.                     $conditionVariableTypes[$pkey] = Connection::PARAM_STR_ARRAY;
  287.                 } else {
  288.                     $conditionVariableTypes[$pkey] = Connection::PARAM_INT_ARRAY;
  289.                 }
  290.             } else {
  291.                 if (is_bool($param)) {
  292.                     $type \PDO::PARAM_BOOL;
  293.                 } elseif (is_int($param)) {
  294.                     $type \PDO::PARAM_INT;
  295.                 } elseif (is_null($param)) {
  296.                     $type \PDO::PARAM_NULL;
  297.                 } else {
  298.                     $type \PDO::PARAM_STR;
  299.                 }
  300.                 $conditionVariableTypes[$pkey] = $type;
  301.             }
  302.         }
  303.         $this->setConditionVariableTypes($conditionVariableTypes);
  304.         return $this->condition $conditionString;
  305.     }
  306.     /**
  307.      * @param string $condition
  308.      * @param array|scalar $conditionVariables
  309.      *
  310.      * @return $this
  311.      */
  312.     public function setCondition($condition$conditionVariables null)
  313.     {
  314.         $this->setData(null);
  315.         $this->condition $condition;
  316.         // statement variables
  317.         if (is_array($conditionVariables)) {
  318.             $this->setConditionVariablesFromSetCondition($conditionVariables);
  319.         } elseif ($conditionVariables !== null) {
  320.             $this->setConditionVariablesFromSetCondition([$conditionVariables]);
  321.         }
  322.         return $this;
  323.     }
  324.     /**
  325.      * @return string|null
  326.      */
  327.     public function getGroupBy()
  328.     {
  329.         return $this->groupBy;
  330.     }
  331.     /**
  332.      * @return array
  333.      */
  334.     public function getValidOrders()
  335.     {
  336.         return $this->validOrders;
  337.     }
  338.     /**
  339.      * @param string $groupBy
  340.      * @param bool $qoute
  341.      *
  342.      * @return $this
  343.      */
  344.     public function setGroupBy($groupBy$qoute true)
  345.     {
  346.         $this->setData(null);
  347.         if ($groupBy) {
  348.             $this->groupBy $groupBy;
  349.             if ($qoute) {
  350.                 $quotedParts = [];
  351.                 $parts explode(','trim($groupBy'`'));
  352.                 foreach ($parts as $part) {
  353.                     $quotedParts[] = $this->quoteIdentifier(trim($part));
  354.                 }
  355.                 $this->groupBy implode(', '$quotedParts);
  356.             }
  357.         }
  358.         return $this;
  359.     }
  360.     /**
  361.      * @param array $validOrders
  362.      *
  363.      * @return $this
  364.      */
  365.     public function setValidOrders($validOrders)
  366.     {
  367.         $this->validOrders $validOrders;
  368.         return $this;
  369.     }
  370.     public function quoteIdentifier(string $value): string
  371.     {
  372.         $db Db::get();
  373.         return $db->quoteIdentifier($value);
  374.     }
  375.     /**
  376.      * @param mixed $value
  377.      * @param int|null $type
  378.      *
  379.      * @return string
  380.      */
  381.     public function quote($value$type null)
  382.     {
  383.         $db Db::get();
  384.         return $db->quote($value$type);
  385.     }
  386.     /**
  387.      * @param string $value
  388.      *
  389.      * @return string
  390.      */
  391.     public function escapeLike(string $value): string
  392.     {
  393.         return Helper::escapeLike($value);
  394.     }
  395.     /**
  396.      * @param array $conditionVariables
  397.      *
  398.      * @return $this
  399.      */
  400.     public function setConditionVariables($conditionVariables)
  401.     {
  402.         $this->conditionVariables $conditionVariables;
  403.         return $this;
  404.     }
  405.     /**
  406.      * @return array
  407.      */
  408.     public function getConditionVariables()
  409.     {
  410.         if (!$this->conditionVariables) {
  411.             $this->getCondition();
  412.         }
  413.         return $this->conditionVariables;
  414.     }
  415.     /**
  416.      * @param array $conditionVariables
  417.      *
  418.      * @return $this
  419.      */
  420.     public function setConditionVariablesFromSetCondition($conditionVariables)
  421.     {
  422.         $this->setData(null);
  423.         $this->conditionVariablesFromSetCondition $conditionVariables;
  424.         return $this;
  425.     }
  426.     /**
  427.      * @return array|null
  428.      */
  429.     public function getConditionVariablesFromSetCondition()
  430.     {
  431.         return $this->conditionVariablesFromSetCondition;
  432.     }
  433.     /**
  434.      * @return bool
  435.      */
  436.     public function isLoaded()
  437.     {
  438.         return $this->data !== null;
  439.     }
  440.     /**
  441.      * @return array
  442.      */
  443.     public function getData()
  444.     {
  445.         if ($this->data === null) {
  446.             $this->getDao()->load();
  447.         }
  448.         return $this->data;
  449.     }
  450.     /**
  451.      * @param array|null $data
  452.      *
  453.      * @return $this
  454.      */
  455.     public function setData(?array $data): self
  456.     {
  457.         $this->data $data;
  458.         return $this;
  459.     }
  460.     /**
  461.      * @return mixed
  462.      */
  463.     #[\ReturnTypeWillChange]
  464.     public function current()// : mixed
  465.     {
  466.         $this->getData();
  467.         return current($this->data);
  468.     }
  469.     /**
  470.      * @return int|string|null
  471.      */
  472.     #[\ReturnTypeWillChange]
  473.     public function key()// : mixed
  474.     {
  475.         $this->getData();
  476.         return key($this->data);
  477.     }
  478.     /**
  479.      * @return void
  480.      */
  481.     #[\ReturnTypeWillChange]
  482.     public function next()// : void
  483.     {
  484.         $this->getData();
  485.         next($this->data);
  486.     }
  487.     /**
  488.      * @return bool
  489.      */
  490.     #[\ReturnTypeWillChange]
  491.     public function valid()// : bool
  492.     {
  493.         $this->getData();
  494.         return $this->current() !== false;
  495.     }
  496.     /**
  497.      * @return void
  498.      */
  499.     #[\ReturnTypeWillChange]
  500.     public function rewind()// : void
  501.     {
  502.         $this->getData();
  503.         reset($this->data);
  504.     }
  505.     /**
  506.      * @return int
  507.      */
  508.     #[\ReturnTypeWillChange]
  509.     public function count()// : int
  510.     {
  511.         return $this->getDao()->getTotalCount();
  512.     }
  513. }