Spade
Mini Shell
| Directory:~$ /home/lmsyaran/public_html/joomla4/ |
| [Home] [System Details] [Kill Me] |
element.php000064400000005204151156424730006717 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Query Element Class.
*
* @property-read string $name The name of the element.
* @property-read array $elements An array of elements.
* @property-read string $glue Glue piece.
*
* @since 1.7.0
*/
class JDatabaseQueryElement
{
/**
* @var string The name of the element.
* @since 1.7.0
*/
protected $name = null;
/**
* @var array An array of elements.
* @since 1.7.0
*/
protected $elements = null;
/**
* @var string Glue piece.
* @since 1.7.0
*/
protected $glue = null;
/**
* Constructor.
*
* @param string $name The name of the element.
* @param mixed $elements String or array.
* @param string $glue The glue for elements.
*
* @since 1.7.0
*/
public function __construct($name, $elements, $glue = ',')
{
$this->elements = array();
$this->name = $name;
$this->glue = $glue;
$this->append($elements);
}
/**
* Magic function to convert the query element to a string.
*
* @return string
*
* @since 1.7.0
*/
public function __toString()
{
if (substr($this->name, -2) == '()')
{
return PHP_EOL . substr($this->name, 0, -2) . '(' .
implode($this->glue, $this->elements) . ')';
}
else
{
return PHP_EOL . $this->name . ' ' .
implode($this->glue, $this->elements);
}
}
/**
* Appends element parts to the internal list.
*
* @param mixed $elements String or array.
*
* @return void
*
* @since 1.7.0
*/
public function append($elements)
{
if (is_array($elements))
{
$this->elements = array_merge($this->elements, $elements);
}
else
{
$this->elements[] = $elements;
}
}
/**
* Gets the elements of this element.
*
* @return array
*
* @since 1.7.0
*/
public function getElements()
{
return $this->elements;
}
/**
* Sets the name of this element.
*
* @param string $name Name of the element.
*
* @return JDatabaseQueryElement Returns this object to allow chaining.
*
* @since 3.6
*/
public function setName($name)
{
$this->name = $name;
return $this;
}
/**
* Method to provide deep copy support to nested objects and arrays
* when cloning.
*
* @return void
*
* @since 1.7.3
*/
public function __clone()
{
foreach ($this as $k => $v)
{
if (is_object($v) || is_array($v))
{
$this->{$k} = unserialize(serialize($v));
}
}
}
}
limitable.php000064400000003236151156424730007233 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Joomla Database Query Limitable Interface.
* Adds bind/unbind methods as well as a getBounded() method
* to retrieve the stored bounded variables on demand prior to
* query execution.
*
* @since 3.0.0
*/
interface JDatabaseQueryLimitable
{
/**
* Method to modify a query already in string format with the needed
* additions to make the query limited to a particular number of
* results, or start at a particular offset. This method is used
* automatically by the __toString() method if it detects that the
* query implements the JDatabaseQueryLimitable interface.
*
* @param string $query The query in string format
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return string
*
* @since 3.0.0
*/
public function processLimit($query, $limit, $offset = 0);
/**
* Sets the offset and limit for the result set, if the database driver
supports it.
*
* Usage:
* $query->setLimit(100, 0); (retrieve 100 rows, starting at first
record)
* $query->setLimit(50, 50); (retrieve 50 rows, starting at 50th
record)
*
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return JDatabaseQuery Returns this object to allow chaining.
*
* @since 3.0.0
*/
public function setLimit($limit = 0, $offset = 0);
}
mysql.php000064400000000674151156424730006441 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Query Building Class.
*
* @since 1.7.0
* @deprecated 4.0 Use MySQLi or PDO MySQL instead
*/
class JDatabaseQueryMysql extends JDatabaseQueryMysqli
{
}
mysqli.php000064400000012315151156424730006605 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Query Building Class.
*
* @since 1.7.0
*/
class JDatabaseQueryMysqli extends JDatabaseQuery implements
JDatabaseQueryLimitable
{
/**
* @var integer The offset for the result set.
* @since 3.0.0
*/
protected $offset;
/**
* @var integer The limit for the result set.
* @since 3.0.0
*/
protected $limit;
/**
* Magic function to convert the query to a string.
*
* @return string The completed query.
*
* @since 1.7.0
*/
public function __toString()
{
switch ($this->type)
{
case 'select':
if ($this->selectRowNumber)
{
$orderBy = $this->selectRowNumber['orderBy'];
$tmpOffset = $this->offset;
$tmpLimit = $this->limit;
$this->offset = 0;
$this->limit = 0;
$tmpOrder = $this->order;
$this->order = null;
$query = parent::__toString();
$this->order = $tmpOrder;
$this->offset = $tmpOffset;
$this->limit = $tmpLimit;
// Add support for second order by, offset and limit
$query = PHP_EOL . 'SELECT * FROM (' . $query . PHP_EOL .
"ORDER BY $orderBy" . PHP_EOL . ') w';
if ($this->order)
{
$query .= (string) $this->order;
}
return $this->processLimit($query, $this->limit,
$this->offset);
}
}
return parent::__toString();
}
/**
* Method to modify a query already in string format with the needed
* additions to make the query limited to a particular number of
* results, or start at a particular offset.
*
* @param string $query The query in string format
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return string
*
* @since 3.0.0
*/
public function processLimit($query, $limit, $offset = 0)
{
if ($limit > 0 && $offset > 0)
{
$query .= ' LIMIT ' . $offset . ', ' . $limit;
}
elseif ($limit > 0)
{
$query .= ' LIMIT ' . $limit;
}
return $query;
}
/**
* Concatenates an array of column names or values.
*
* @param array $values An array of values to concatenate.
* @param string $separator As separator to place between each value.
*
* @return string The concatenated values.
*
* @since 1.7.0
*/
public function concatenate($values, $separator = null)
{
if ($separator)
{
$concat_string = 'CONCAT_WS(' . $this->quote($separator);
foreach ($values as $value)
{
$concat_string .= ', ' . $value;
}
return $concat_string . ')';
}
else
{
return 'CONCAT(' . implode(',', $values) .
')';
}
}
/**
* Sets the offset and limit for the result set, if the database driver
supports it.
*
* Usage:
* $query->setLimit(100, 0); (retrieve 100 rows, starting at first
record)
* $query->setLimit(50, 50); (retrieve 50 rows, starting at 50th
record)
*
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return JDatabaseQuery Returns this object to allow chaining.
*
* @since 3.0.0
*/
public function setLimit($limit = 0, $offset = 0)
{
$this->limit = (int) $limit;
$this->offset = (int) $offset;
return $this;
}
/**
* Return correct regexp operator for mysqli.
*
* Ensure that the regexp operator is mysqli compatible.
*
* Usage:
* $query->where('field ' . $query->regexp($search));
*
* @param string $value The regex pattern.
*
* @return string Returns the regex operator.
*
* @since 1.7.3
*/
public function regexp($value)
{
return ' REGEXP ' . $value;
}
/**
* Return correct rand() function for Mysql.
*
* Ensure that the rand() function is Mysql compatible.
*
* Usage:
* $query->Rand();
*
* @return string The correct rand function.
*
* @since 3.5
*/
public function Rand()
{
return ' RAND() ';
}
/**
* Return the number of the current row.
*
* @param string $orderBy An expression of ordering for
window function.
* @param string $orderColumnAlias An alias for new ordering column.
*
* @return JDatabaseQuery Returns this object to allow chaining.
*
* @since 3.7.0
* @throws RuntimeException
*/
public function selectRowNumber($orderBy, $orderColumnAlias)
{
$this->validateRowNumber($orderBy, $orderColumnAlias);
$this->select("(SELECT @rownum := @rownum + 1 FROM (SELECT
@rownum := 0) AS r) AS $orderColumnAlias");
return $this;
}
/**
* Casts a value to a char.
*
* Ensure that the value is properly quoted before passing to the method.
*
* Usage:
* $query->select($query->castAsChar('a'));
* $query->select($query->castAsChar('a', 40));
*
* @param string $value The value to cast as a char.
*
* @param string $len The length of the char.
*
* @return string Returns the cast value.
*
* @since 3.7.0
*/
public function castAsChar($value, $len = null)
{
if (!$len)
{
return $value;
}
else
{
return ' CAST(' . $value . ' AS CHAR(' . $len .
'))';
}
}
}
oracle.php000064400000012367151156424730006543 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Oracle Query Building Class.
*
* @since 3.0.0
*/
class JDatabaseQueryOracle extends JDatabaseQueryPdo implements
JDatabaseQueryPreparable, JDatabaseQueryLimitable
{
/**
* @var integer The offset for the result set.
* @since 3.0.0
*/
protected $offset;
/**
* @var integer The limit for the result set.
* @since 3.0.0
*/
protected $limit;
/**
* @var array Bounded object array
* @since 3.0.0
*/
protected $bounded = array();
/**
* Method to add a variable to an internal array that will be bound to a
prepared SQL statement before query execution. Also
* removes a variable that has been bounded from the internal bounded
array when the passed in value is null.
*
* @param string|integer $key The key that will be used in
your SQL query to reference the value. Usually of
* the form ':key', but
can also be an integer.
* @param mixed &$value The value that will be
bound. The value is passed by reference to support output
* parameters such as those
possible with stored procedures.
* @param integer $dataType Constant corresponding to a
SQL datatype.
* @param integer $length The length of the variable.
Usually required for OUTPUT parameters.
* @param array $driverOptions Optional driver options to be
used.
*
* @return JDatabaseQueryOracle
*
* @since 3.0.0
*/
public function bind($key = null, &$value = null, $dataType =
PDO::PARAM_STR, $length = 0, $driverOptions = array())
{
// Case 1: Empty Key (reset $bounded array)
if (empty($key))
{
$this->bounded = array();
return $this;
}
// Case 2: Key Provided, null value (unset key from $bounded array)
if (is_null($value))
{
if (isset($this->bounded[$key]))
{
unset($this->bounded[$key]);
}
return $this;
}
$obj = new stdClass;
$obj->value = &$value;
$obj->dataType = $dataType;
$obj->length = $length;
$obj->driverOptions = $driverOptions;
// Case 3: Simply add the Key/Value into the bounded array
$this->bounded[$key] = $obj;
return $this;
}
/**
* Retrieves the bound parameters array when key is null and returns it by
reference. If a key is provided then that item is
* returned.
*
* @param mixed $key The bounded variable key to retrieve.
*
* @return mixed
*
* @since 3.0.0
*/
public function &getBounded($key = null)
{
if (empty($key))
{
return $this->bounded;
}
else
{
if (isset($this->bounded[$key]))
{
return $this->bounded[$key];
}
}
}
/**
* Clear data from the query or a specific clause of the query.
*
* @param string $clause Optionally, the name of the clause to clear,
or nothing to clear the whole query.
*
* @return JDatabaseQueryOracle Returns this object to allow chaining.
*
* @since 3.0.0
*/
public function clear($clause = null)
{
switch ($clause)
{
case null:
$this->bounded = array();
break;
}
parent::clear($clause);
return $this;
}
/**
* Method to modify a query already in string format with the needed
* additions to make the query limited to a particular number of
* results, or start at a particular offset. This method is used
* automatically by the __toString() method if it detects that the
* query implements the JDatabaseQueryLimitable interface.
*
* @param string $query The query in string format
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return string
*
* @since 3.0.0
*/
public function processLimit($query, $limit, $offset = 0)
{
// Check if we need to mangle the query.
if ($limit || $offset)
{
$query = 'SELECT joomla2.*
FROM (
SELECT joomla1.*, ROWNUM AS joomla_db_rownum
FROM (
' . $query . '
) joomla1
) joomla2';
// Check if the limit value is greater than zero.
if ($limit > 0)
{
$query .= ' WHERE joomla2.joomla_db_rownum BETWEEN ' .
($offset + 1) . ' AND ' . ($offset + $limit);
}
else
{
// Check if there is an offset and then use this.
if ($offset)
{
$query .= ' WHERE joomla2.joomla_db_rownum > ' . ($offset
+ 1);
}
}
}
return $query;
}
/**
* Sets the offset and limit for the result set, if the database driver
supports it.
*
* Usage:
* $query->setLimit(100, 0); (retrieve 100 rows, starting at first
record)
* $query->setLimit(50, 50); (retrieve 50 rows, starting at 50th
record)
*
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return JDatabaseQueryOracle Returns this object to allow chaining.
*
* @since 3.0.0
*/
public function setLimit($limit = 0, $offset = 0)
{
$this->limit = (int) $limit;
$this->offset = (int) $offset;
return $this;
}
}
pdo.php000064400000001706151156424730006053 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* PDO Query Building Class.
*
* @since 3.0.0
*/
class JDatabaseQueryPdo extends JDatabaseQuery
{
/**
* Casts a value to a char.
*
* Ensure that the value is properly quoted before passing to the method.
*
* Usage:
* $query->select($query->castAsChar('a'));
* $query->select($query->castAsChar('a', 40));
*
* @param string $value The value to cast as a char.
*
* @param string $len The length of the char.
*
* @return string Returns the cast value.
*
* @since 1.7.0
*/
public function castAsChar($value, $len = null)
{
if (!$len)
{
return $value;
}
else
{
return ' CAST(' . $value . ' AS CHAR(' . $len .
'))';
}
}
}
pdomysql.php000064400000000701151156424730007133 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Query Building Class.
*
* @package Joomla.Platform
* @subpackage Database
* @since 3.4
*/
class JDatabaseQueryPdomysql extends JDatabaseQueryMysqli
{
}
pgsql.php000064400000006175151156424730006424 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* PDO PostgreSQL Query Building Class.
*
* @since 3.9.0
*/
class JDatabaseQueryPgsql extends JDatabaseQueryPostgresql implements
JDatabaseQueryPreparable
{
/**
* Holds key / value pair of bound objects.
*
* @var mixed
* @since 3.9.0
*/
protected $bounded = array();
/**
* Method to add a variable to an internal array that will be bound to a
prepared SQL statement before query execution. Also
* removes a variable that has been bounded from the internal bounded
array when the passed in value is null.
*
* @param string|integer $key The key that will be used in
your SQL query to reference the value. Usually of
* the form ':key', but
can also be an integer.
* @param mixed &$value The value that will be
bound. The value is passed by reference to support output
* parameters such as those
possible with stored procedures.
* @param integer $dataType Constant corresponding to a
SQL datatype.
* @param integer $length The length of the variable.
Usually required for OUTPUT parameters.
* @param array $driverOptions Optional driver options to be
used.
*
* @return JDatabaseQueryPgsql
*
* @since 3.9.0
*/
public function bind($key = null, &$value = null, $dataType =
PDO::PARAM_STR, $length = 0, $driverOptions = array())
{
// Case 1: Empty Key (reset $bounded array)
if (empty($key))
{
$this->bounded = array();
return $this;
}
// Case 2: Key Provided, null value (unset key from $bounded array)
if (is_null($value))
{
if (isset($this->bounded[$key]))
{
unset($this->bounded[$key]);
}
return $this;
}
$obj = new stdClass;
$obj->value = &$value;
$obj->dataType = $dataType;
$obj->length = $length;
$obj->driverOptions = $driverOptions;
// Case 3: Simply add the Key/Value into the bounded array
$this->bounded[$key] = $obj;
return $this;
}
/**
* Retrieves the bound parameters array when key is null and returns it by
reference. If a key is provided then that item is
* returned.
*
* @param mixed $key The bounded variable key to retrieve.
*
* @return mixed
*
* @since 3.9.0
*/
public function &getBounded($key = null)
{
if (empty($key))
{
return $this->bounded;
}
if (isset($this->bounded[$key]))
{
return $this->bounded[$key];
}
}
/**
* Clear data from the query or a specific clause of the query.
*
* @param string $clause Optionally, the name of the clause to clear,
or nothing to clear the whole query.
*
* @return JDatabaseQueryPgsql Returns this object to allow chaining.
*
* @since 3.9.0
*/
public function clear($clause = null)
{
switch ($clause)
{
case null:
$this->bounded = array();
break;
}
return parent::clear($clause);
}
}
postgresql.php000064400000041030151156424730007466 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Query Building Class.
*
* @since 1.7.3
* @deprecated 4.0 Use PDO PostgreSQL instead
*/
class JDatabaseQueryPostgresql extends JDatabaseQuery implements
JDatabaseQueryLimitable
{
/**
* @var object The FOR UPDATE element used in "FOR UPDATE"
lock
* @since 1.7.3
*/
protected $forUpdate = null;
/**
* @var object The FOR SHARE element used in "FOR SHARE"
lock
* @since 1.7.3
*/
protected $forShare = null;
/**
* @var object The NOWAIT element used in "FOR SHARE" and
"FOR UPDATE" lock
* @since 1.7.3
*/
protected $noWait = null;
/**
* @var object The LIMIT element
* @since 1.7.3
*/
protected $limit = null;
/**
* @var object The OFFSET element
* @since 1.7.3
*/
protected $offset = null;
/**
* @var object The RETURNING element of INSERT INTO
* @since 1.7.3
*/
protected $returning = null;
/**
* Magic function to convert the query to a string, only for postgresql
specific query
*
* @return string The completed query.
*
* @since 1.7.3
*/
public function __toString()
{
$query = '';
switch ($this->type)
{
case 'select':
if ($this->selectRowNumber &&
$this->selectRowNumber['native'] === false)
{
// Workaround for postgresql version less than 8.4.0
try
{
$this->db->setQuery('CREATE TEMP SEQUENCE
ROW_NUMBER');
$this->db->execute();
}
catch (JDatabaseExceptionExecuting $e)
{
// Do nothing, sequence exists
}
$orderBy = $this->selectRowNumber['orderBy'];
$orderColumnAlias =
$this->selectRowNumber['orderColumnAlias'];
$columns = "nextval('ROW_NUMBER') - 1 AS
$orderColumnAlias";
if ($this->select === null)
{
$query = PHP_EOL . "SELECT 1"
. (string) $this->from
. (string) $this->where;
}
else
{
$tmpOffset = $this->offset;
$tmpLimit = $this->limit;
$this->offset = 0;
$this->limit = 0;
$tmpOrder = $this->order;
$this->order = null;
$query = parent::__toString();
$columns = "w.*, $columns";
$this->order = $tmpOrder;
$this->offset = $tmpOffset;
$this->limit = $tmpLimit;
}
// Add support for second order by, offset and limit
$query = PHP_EOL . "SELECT $columns FROM (" . $query .
PHP_EOL . "ORDER BY $orderBy"
. PHP_EOL . ") w,(SELECT setval('ROW_NUMBER', 1)) AS
r";
if ($this->order)
{
$query .= (string) $this->order;
}
break;
}
$query .= (string) $this->select;
$query .= (string) $this->from;
if ($this->join)
{
// Special case for joins
foreach ($this->join as $join)
{
$query .= (string) $join;
}
}
if ($this->where)
{
$query .= (string) $this->where;
}
if ($this->selectRowNumber)
{
if ($this->order)
{
$query .= (string) $this->order;
}
break;
}
if ($this->group)
{
$query .= (string) $this->group;
}
if ($this->having)
{
$query .= (string) $this->having;
}
if ($this->order)
{
$query .= (string) $this->order;
}
if ($this->forUpdate)
{
$query .= (string) $this->forUpdate;
}
else
{
if ($this->forShare)
{
$query .= (string) $this->forShare;
}
}
if ($this->noWait)
{
$query .= (string) $this->noWait;
}
break;
case 'update':
$query .= (string) $this->update;
$query .= (string) $this->set;
if ($this->join)
{
$tmpFrom = $this->from;
$tmpWhere = $this->where ? clone $this->where : null;
$this->from = null;
// Workaround for special case of JOIN with UPDATE
foreach ($this->join as $join)
{
$joinElem = $join->getElements();
$joinArray = preg_split('/\sON\s/i', $joinElem[0]);
if (count($joinArray) > 2)
{
$condition = array_pop($joinArray);
$joinArray = array(implode(' ON ', $joinArray),
$condition);
}
$this->from($joinArray[0]);
if (isset($joinArray[1]))
{
$this->where($joinArray[1]);
}
}
$query .= (string) $this->from;
if ($this->where)
{
$query .= (string) $this->where;
}
$this->from = $tmpFrom;
$this->where = $tmpWhere;
}
elseif ($this->where)
{
$query .= (string) $this->where;
}
break;
case 'insert':
$query .= (string) $this->insert;
if ($this->values)
{
if ($this->columns)
{
$query .= (string) $this->columns;
}
$elements = $this->values->getElements();
if (!($elements[0] instanceof $this))
{
$query .= ' VALUES ';
}
$query .= (string) $this->values;
if ($this->returning)
{
$query .= (string) $this->returning;
}
}
break;
default:
$query = parent::__toString();
break;
}
if ($this instanceof JDatabaseQueryLimitable)
{
$query = $this->processLimit($query, $this->limit,
$this->offset);
}
return $query;
}
/**
* Clear data from the query or a specific clause of the query.
*
* @param string $clause Optionally, the name of the clause to clear,
or nothing to clear the whole query.
*
* @return JDatabaseQueryPostgresql Returns this object to allow
chaining.
*
* @since 1.7.3
*/
public function clear($clause = null)
{
switch ($clause)
{
case 'limit':
$this->limit = null;
break;
case 'offset':
$this->offset = null;
break;
case 'forUpdate':
$this->forUpdate = null;
break;
case 'forShare':
$this->forShare = null;
break;
case 'noWait':
$this->noWait = null;
break;
case 'returning':
$this->returning = null;
break;
case 'select':
case 'update':
case 'delete':
case 'insert':
case 'from':
case 'join':
case 'set':
case 'where':
case 'group':
case 'having':
case 'order':
case 'columns':
case 'values':
parent::clear($clause);
break;
default:
$this->type = null;
$this->limit = null;
$this->offset = null;
$this->forUpdate = null;
$this->forShare = null;
$this->noWait = null;
$this->returning = null;
parent::clear($clause);
break;
}
return $this;
}
/**
* Casts a value to a char.
*
* Ensure that the value is properly quoted before passing to the method.
*
* Usage:
* $query->select($query->castAsChar('a'));
* $query->select($query->castAsChar('a', 40));
*
* @param string $value The value to cast as a char.
*
* @param string $len The length of the char.
*
* @return string Returns the cast value.
*
* @since 1.7.3
*/
public function castAsChar($value, $len = null)
{
if (!$len)
{
return $value . '::text';
}
else
{
return ' CAST(' . $value . ' AS CHAR(' . $len .
'))';
}
}
/**
* Concatenates an array of column names or values.
*
* Usage:
* $query->select($query->concatenate(array('a',
'b')));
*
* @param array $values An array of values to concatenate.
* @param string $separator As separator to place between each value.
*
* @return string The concatenated values.
*
* @since 1.7.3
*/
public function concatenate($values, $separator = null)
{
if ($separator)
{
return implode(' || ' . $this->quote($separator) . '
|| ', $values);
}
else
{
return implode(' || ', $values);
}
}
/**
* Gets the current date and time.
*
* @return string Return string used in query to obtain
*
* @since 1.7.3
*/
public function currentTimestamp()
{
return 'NOW()';
}
/**
* Sets the FOR UPDATE lock on select's output row
*
* @param string $tableName The table to lock
* @param string $glue The glue by which to join the conditions.
Defaults to ',' .
*
* @return JDatabaseQueryPostgresql FOR UPDATE query element
*
* @since 1.7.3
*/
public function forUpdate($tableName, $glue = ',')
{
$this->type = 'forUpdate';
if (is_null($this->forUpdate))
{
$glue = strtoupper($glue);
$this->forUpdate = new JDatabaseQueryElement('FOR UPDATE',
'OF ' . $tableName, "$glue ");
}
else
{
$this->forUpdate->append($tableName);
}
return $this;
}
/**
* Sets the FOR SHARE lock on select's output row
*
* @param string $tableName The table to lock
* @param string $glue The glue by which to join the conditions.
Defaults to ',' .
*
* @return JDatabaseQueryPostgresql FOR SHARE query element
*
* @since 1.7.3
*/
public function forShare($tableName, $glue = ',')
{
$this->type = 'forShare';
if (is_null($this->forShare))
{
$glue = strtoupper($glue);
$this->forShare = new JDatabaseQueryElement('FOR SHARE',
'OF ' . $tableName, "$glue ");
}
else
{
$this->forShare->append($tableName);
}
return $this;
}
/**
* Used to get a string to extract year from date column.
*
* Usage:
*
$query->select($query->year($query->quoteName('dateColumn')));
*
* @param string $date Date column containing year to be extracted.
*
* @return string Returns string to extract year from a date.
*
* @since 3.0.0
*/
public function year($date)
{
return 'EXTRACT (YEAR FROM ' . $date . ')';
}
/**
* Used to get a string to extract month from date column.
*
* Usage:
*
$query->select($query->month($query->quoteName('dateColumn')));
*
* @param string $date Date column containing month to be extracted.
*
* @return string Returns string to extract month from a date.
*
* @since 3.0.0
*/
public function month($date)
{
return 'EXTRACT (MONTH FROM ' . $date . ')';
}
/**
* Used to get a string to extract day from date column.
*
* Usage:
*
$query->select($query->day($query->quoteName('dateColumn')));
*
* @param string $date Date column containing day to be extracted.
*
* @return string Returns string to extract day from a date.
*
* @since 3.0.0
*/
public function day($date)
{
return 'EXTRACT (DAY FROM ' . $date . ')';
}
/**
* Used to get a string to extract hour from date column.
*
* Usage:
*
$query->select($query->hour($query->quoteName('dateColumn')));
*
* @param string $date Date column containing hour to be extracted.
*
* @return string Returns string to extract hour from a date.
*
* @since 3.0.0
*/
public function hour($date)
{
return 'EXTRACT (HOUR FROM ' . $date . ')';
}
/**
* Used to get a string to extract minute from date column.
*
* Usage:
*
$query->select($query->minute($query->quoteName('dateColumn')));
*
* @param string $date Date column containing minute to be extracted.
*
* @return string Returns string to extract minute from a date.
*
* @since 3.0.0
*/
public function minute($date)
{
return 'EXTRACT (MINUTE FROM ' . $date . ')';
}
/**
* Used to get a string to extract seconds from date column.
*
* Usage:
*
$query->select($query->second($query->quoteName('dateColumn')));
*
* @param string $date Date column containing second to be extracted.
*
* @return string Returns string to extract second from a date.
*
* @since 3.0.0
*/
public function second($date)
{
return 'EXTRACT (SECOND FROM ' . $date . ')';
}
/**
* Sets the NOWAIT lock on select's output row
*
* @return JDatabaseQueryPostgresql NO WAIT query element
*
* @since 1.7.3
*/
public function noWait ()
{
$this->type = 'noWait';
if (is_null($this->noWait))
{
$this->noWait = new JDatabaseQueryElement('NOWAIT', null);
}
return $this;
}
/**
* Set the LIMIT clause to the query
*
* @param integer $limit An int of how many row will be returned
*
* @return JDatabaseQueryPostgresql Returns this object to allow
chaining.
*
* @since 1.7.3
*/
public function limit($limit = 0)
{
if (is_null($this->limit))
{
$this->limit = new JDatabaseQueryElement('LIMIT', (int)
$limit);
}
return $this;
}
/**
* Set the OFFSET clause to the query
*
* @param integer $offset An int for skipping row
*
* @return JDatabaseQueryPostgresql Returns this object to allow
chaining.
*
* @since 1.7.3
*/
public function offset($offset = 0)
{
if (is_null($this->offset))
{
$this->offset = new JDatabaseQueryElement('OFFSET', (int)
$offset);
}
return $this;
}
/**
* Add the RETURNING element to INSERT INTO statement.
*
* @param mixed $pkCol The name of the primary key column.
*
* @return JDatabaseQueryPostgresql Returns this object to allow
chaining.
*
* @since 1.7.3
*/
public function returning($pkCol)
{
if (is_null($this->returning))
{
$this->returning = new JDatabaseQueryElement('RETURNING',
$pkCol);
}
return $this;
}
/**
* Sets the offset and limit for the result set, if the database driver
supports it.
*
* Usage:
* $query->setLimit(100, 0); (retrieve 100 rows, starting at first
record)
* $query->setLimit(50, 50); (retrieve 50 rows, starting at 50th
record)
*
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return JDatabaseQueryPostgresql Returns this object to allow
chaining.
*
* @since 3.0.0
*/
public function setLimit($limit = 0, $offset = 0)
{
$this->limit = (int) $limit;
$this->offset = (int) $offset;
return $this;
}
/**
* Method to modify a query already in string format with the needed
* additions to make the query limited to a particular number of
* results, or start at a particular offset.
*
* @param string $query The query in string format
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return string
*
* @since 3.0.0
*/
public function processLimit($query, $limit, $offset = 0)
{
if ($limit > 0)
{
$query .= ' LIMIT ' . $limit;
}
if ($offset > 0)
{
$query .= ' OFFSET ' . $offset;
}
return $query;
}
/**
* Add to the current date and time in Postgresql.
* Usage:
* $query->select($query->dateAdd());
* Prefixing the interval with a - (negative sign) will cause subtraction
to be used.
*
* @param string $date The db quoted string representation of the
date to add to
* @param string $interval The string representation of the
appropriate number of units
* @param string $datePart The part of the date to perform the
addition on
*
* @return string The string with the appropriate sql for addition of
dates
*
* @since 3.2.0
* @note Not all drivers support all units. Check appropriate
references
* @link
http://www.postgresql.org/docs/9.0/static/functions-datetime.html.
*/
public function dateAdd($date, $interval, $datePart)
{
if (substr($interval, 0, 1) != '-')
{
return "timestamp " . $date . " + interval '" .
$interval . " " . $datePart . "'";
}
else
{
return "timestamp " . $date . " - interval '" .
ltrim($interval, '-') . " " . $datePart .
"'";
}
}
/**
* Return correct regexp operator for Postgresql.
*
* Ensure that the regexp operator is Postgresql compatible.
*
* Usage:
* $query->where('field ' . $query->regexp($search));
*
* @param string $value The regex pattern.
*
* @return string Returns the regex operator.
*
* @since 1.7.3
*/
public function regexp($value)
{
return ' ~* ' . $value;
}
/**
* Return correct rand() function for Postgresql.
*
* Ensure that the rand() function is Postgresql compatible.
*
* Usage:
* $query->Rand();
*
* @return string The correct rand function.
*
* @since 3.5
*/
public function Rand()
{
return ' RANDOM() ';
}
/**
* Return the number of the current row.
*
* @param string $orderBy An expression of ordering for
window function.
* @param string $orderColumnAlias An alias for new ordering column.
*
* @return JDatabaseQuery Returns this object to allow chaining.
*
* @since 3.7.0
* @throws RuntimeException
*/
public function selectRowNumber($orderBy, $orderColumnAlias)
{
$this->validateRowNumber($orderBy, $orderColumnAlias);
if (version_compare($this->db->getVersion(), '8.4.0')
>= 0)
{
$this->selectRowNumber['native'] = true;
$this->select("ROW_NUMBER() OVER (ORDER BY $orderBy) AS
$orderColumnAlias");
}
else
{
$this->selectRowNumber['native'] = false;
}
return $this;
}
}
preparable.php000064400000003705151156424730007407 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Joomla Database Query Preparable Interface.
* Adds bind/unbind methods as well as a getBounded() method
* to retrieve the stored bounded variables on demand prior to
* query execution.
*
* @since 3.0.0
*/
interface JDatabaseQueryPreparable
{
/**
* Method to add a variable to an internal array that will be bound to a
prepared SQL statement before query execution. Also
* removes a variable that has been bounded from the internal bounded
array when the passed in value is null.
*
* @param string|integer $key The key that will be used in
your SQL query to reference the value. Usually of
* the form ':key', but
can also be an integer.
* @param mixed &$value The value that will be
bound. The value is passed by reference to support output
* parameters such as those
possible with stored procedures.
* @param integer $dataType Constant corresponding to a
SQL datatype.
* @param integer $length The length of the variable.
Usually required for OUTPUT parameters.
* @param array $driverOptions Optional driver options to be
used.
*
* @return JDatabaseQuery
*
* @since 3.0.0
*/
public function bind($key = null, &$value = null, $dataType =
PDO::PARAM_STR, $length = 0, $driverOptions = array());
/**
* Retrieves the bound parameters array when key is null and returns it by
reference. If a key is provided then that item is
* returned.
*
* @param mixed $key The bounded variable key to retrieve.
*
* @return mixed
*
* @since 3.0.0
*/
public function &getBounded($key = null);
}
sqlazure.php000064400000001470151156424730007135 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Query Building Class.
*
* @since 1.7.0
*/
class JDatabaseQuerySqlazure extends JDatabaseQuerySqlsrv
{
/**
* The character(s) used to quote SQL statement names such as table names
or field names,
* etc. The child classes should define this as necessary. If a single
character string the
* same character is used for both sides of the quoted name, else the
first character will be
* used for the opening quote and the second for the closing quote.
*
* @var string
*
* @since 1.7.0
*/
protected $name_quotes = '';
}
sqlite.php000064400000024343151156424730006574 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* SQLite Query Building Class.
*
* @since 3.0.0
*/
class JDatabaseQuerySqlite extends JDatabaseQueryPdo implements
JDatabaseQueryPreparable, JDatabaseQueryLimitable
{
/**
* @var integer The offset for the result set.
* @since 3.0.0
*/
protected $offset;
/**
* @var integer The limit for the result set.
* @since 3.0.0
*/
protected $limit;
/**
* @var array Bounded object array
* @since 3.0.0
*/
protected $bounded = array();
/**
* Method to add a variable to an internal array that will be bound to a
prepared SQL statement before query execution. Also
* removes a variable that has been bounded from the internal bounded
array when the passed in value is null.
*
* @param string|integer $key The key that will be used in
your SQL query to reference the value. Usually of
* the form ':key', but
can also be an integer.
* @param mixed &$value The value that will be
bound. The value is passed by reference to support output
* parameters such as those
possible with stored procedures.
* @param integer $dataType Constant corresponding to a
SQL datatype.
* @param integer $length The length of the variable.
Usually required for OUTPUT parameters.
* @param array $driverOptions Optional driver options to be
used.
*
* @return JDatabaseQuerySqlite
*
* @since 3.0.0
*/
public function bind($key = null, &$value = null, $dataType =
PDO::PARAM_STR, $length = 0, $driverOptions = array())
{
// Case 1: Empty Key (reset $bounded array)
if (empty($key))
{
$this->bounded = array();
return $this;
}
// Case 2: Key Provided, null value (unset key from $bounded array)
if (is_null($value))
{
if (isset($this->bounded[$key]))
{
unset($this->bounded[$key]);
}
return $this;
}
$obj = new stdClass;
$obj->value = &$value;
$obj->dataType = $dataType;
$obj->length = $length;
$obj->driverOptions = $driverOptions;
// Case 3: Simply add the Key/Value into the bounded array
$this->bounded[$key] = $obj;
return $this;
}
/**
* Retrieves the bound parameters array when key is null and returns it by
reference. If a key is provided then that item is
* returned.
*
* @param mixed $key The bounded variable key to retrieve.
*
* @return mixed
*
* @since 3.0.0
*/
public function &getBounded($key = null)
{
if (empty($key))
{
return $this->bounded;
}
else
{
if (isset($this->bounded[$key]))
{
return $this->bounded[$key];
}
}
}
/**
* Gets the number of characters in a string.
*
* Note, use 'length' to find the number of bytes in a string.
*
* Usage:
* $query->select($query->charLength('a'));
*
* @param string $field A value.
* @param string $operator Comparison operator between charLength
integer value and $condition
* @param string $condition Integer value to compare charLength with.
*
* @return string The required char length call.
*
* @since 3.2.0
*/
public function charLength($field, $operator = null, $condition = null)
{
return 'length(' . $field . ')' . (isset($operator)
&& isset($condition) ? ' ' . $operator . ' ' .
$condition : '');
}
/**
* Clear data from the query or a specific clause of the query.
*
* @param string $clause Optionally, the name of the clause to clear,
or nothing to clear the whole query.
*
* @return JDatabaseQuerySqlite Returns this object to allow chaining.
*
* @since 3.0.0
*/
public function clear($clause = null)
{
switch ($clause)
{
case null:
$this->bounded = array();
break;
}
parent::clear($clause);
return $this;
}
/**
* Concatenates an array of column names or values.
*
* Usage:
* $query->select($query->concatenate(array('a',
'b')));
*
* @param array $values An array of values to concatenate.
* @param string $separator As separator to place between each value.
*
* @return string The concatenated values.
*
* @since 1.7.0
*/
public function concatenate($values, $separator = null)
{
if ($separator)
{
return implode(' || ' . $this->quote($separator) . '
|| ', $values);
}
else
{
return implode(' || ', $values);
}
}
/**
* Method to modify a query already in string format with the needed
* additions to make the query limited to a particular number of
* results, or start at a particular offset. This method is used
* automatically by the __toString() method if it detects that the
* query implements the JDatabaseQueryLimitable interface.
*
* @param string $query The query in string format
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return string
*
* @since 3.0.0
*/
public function processLimit($query, $limit, $offset = 0)
{
if ($limit > 0 || $offset > 0)
{
$query .= ' LIMIT ' . $offset . ', ' . $limit;
}
return $query;
}
/**
* Sets the offset and limit for the result set, if the database driver
supports it.
*
* Usage:
* $query->setLimit(100, 0); (retrieve 100 rows, starting at first
record)
* $query->setLimit(50, 50); (retrieve 50 rows, starting at 50th
record)
*
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return JDatabaseQuerySqlite Returns this object to allow chaining.
*
* @since 3.0.0
*/
public function setLimit($limit = 0, $offset = 0)
{
$this->limit = (int) $limit;
$this->offset = (int) $offset;
return $this;
}
/**
* Add to the current date and time.
* Usage:
* $query->select($query->dateAdd());
* Prefixing the interval with a - (negative sign) will cause subtraction
to be used.
*
* @param datetime $date The date or datetime to add to
* @param string $interval The string representation of the
appropriate number of units
* @param string $datePart The part of the date to perform the
addition on
*
* @return string The string with the appropriate sql for addition of
dates
*
* @since 3.2.0
* @link http://www.sqlite.org/lang_datefunc.html
*/
public function dateAdd($date, $interval, $datePart)
{
// SQLite does not support microseconds as a separate unit. Convert the
interval to seconds
if (strcasecmp($datePart, 'microseconds') == 0)
{
// Force the dot as a decimal point
$interval = str_replace(',', '.', .001 * $interval);
$datePart = 'seconds';
}
if (substr($interval, 0, 1) != '-')
{
return "datetime('" . $date . "', '+"
. $interval . " " . $datePart . "')";
}
else
{
return "datetime('" . $date . "', '"
. $interval . " " . $datePart . "')";
}
}
/**
* Gets the current date and time.
*
* Usage:
* $query->where('published_up <
'.$query->currentTimestamp());
*
* @return string
*
* @since 3.4
*/
public function currentTimestamp()
{
return 'CURRENT_TIMESTAMP';
}
/**
* Magic function to convert the query to a string.
*
* @return string The completed query.
*
* @since 1.7.0
*/
public function __toString()
{
switch ($this->type)
{
case 'select':
if ($this->selectRowNumber)
{
$orderBy = $this->selectRowNumber['orderBy'];
$orderColumnAlias =
$this->selectRowNumber['orderColumnAlias'];
$column = "ROW_NUMBER() AS $orderColumnAlias";
if ($this->select === null)
{
$query = PHP_EOL . "SELECT 1"
. (string) $this->from
. (string) $this->where;
}
else
{
$tmpOffset = $this->offset;
$tmpLimit = $this->limit;
$this->offset = 0;
$this->limit = 0;
$tmpOrder = $this->order;
$this->order = null;
$query = parent::__toString();
$column = "w.*, $column";
$this->order = $tmpOrder;
$this->offset = $tmpOffset;
$this->limit = $tmpLimit;
}
// Special sqlite query to count ROW_NUMBER
$query = PHP_EOL . "SELECT $column"
. PHP_EOL . "FROM ($query" . PHP_EOL . "ORDER BY
$orderBy"
. PHP_EOL . ") AS w,(SELECT ROW_NUMBER(0)) AS r"
// Forbid to flatten subqueries.
. ((string) $this->order ?: PHP_EOL . 'ORDER BY NULL');
return $this->processLimit($query, $this->limit,
$this->offset);
}
break;
case 'update':
if ($this->join)
{
$table = $this->update->getElements();
$table = $table[0];
$tableName = explode(' ', $table);
$tableName = $tableName[0];
if ($this->columns === null)
{
$fields = $this->db->getTableColumns($tableName);
foreach ($fields as $key => $value)
{
$fields[$key] = $key;
}
$this->columns = new JDatabaseQueryElement('()',
$fields);
}
$fields = $this->columns->getElements();
$elements = $this->set->getElements();
foreach ($elements as $nameValue)
{
$setArray = explode(' = ', $nameValue, 2);
if ($setArray[0][0] === '`')
{
// Unquote column name
$setArray[0] = substr($setArray[0], 1, -1);
}
$fields[$setArray[0]] = $setArray[1];
}
$select = new JDatabaseQuerySqlite($this->db);
$select->select(array_values($fields))
->from($table);
$select->join = $this->join;
$select->where = $this->where;
return 'INSERT OR REPLACE INTO ' . $tableName
. ' (' . implode(',', array_keys($fields)) .
')'
. (string) $select;
}
}
return parent::__toString();
}
/**
* Return the number of the current row.
*
* @param string $orderBy An expression of ordering for
window function.
* @param string $orderColumnAlias An alias for new ordering column.
*
* @return JDatabaseQuery Returns this object to allow chaining.
*
* @since 3.7.0
* @throws RuntimeException
*/
public function selectRowNumber($orderBy, $orderColumnAlias)
{
$this->validateRowNumber($orderBy, $orderColumnAlias);
return $this;
}
}
sqlsrv.php000064400000056775151156424730006643 0ustar00<?php
/**
* @package Joomla.Platform
* @subpackage Database
*
* @copyright Copyright (C) 2005 - 2020 Open Source Matters, Inc. All
rights reserved.
* @license GNU General Public License version 2 or later; see LICENSE
*/
defined('JPATH_PLATFORM') or die;
/**
* Query Building Class.
*
* @since 1.7.0
*/
class JDatabaseQuerySqlsrv extends JDatabaseQuery implements
JDatabaseQueryLimitable
{
/**
* The character(s) used to quote SQL statement names such as table names
or field names,
* etc. The child classes should define this as necessary. If a single
character string the
* same character is used for both sides of the quoted name, else the
first character will be
* used for the opening quote and the second for the closing quote.
*
* @var string
* @since 1.7.0
*/
protected $name_quotes = '`';
/**
* The null or zero representation of a timestamp for the database driver.
This should be
* defined in child classes to hold the appropriate value for the engine.
*
* @var string
* @since 1.7.0
*/
protected $null_date = '1900-01-01 00:00:00';
/**
* @var integer The affected row limit for the current SQL statement.
* @since 3.2
*/
protected $limit = 0;
/**
* @var integer The affected row offset to apply for the current SQL
statement.
* @since 3.2
*/
protected $offset = 0;
/**
* Magic function to convert the query to a string.
*
* @return string The completed query.
*
* @since 1.7.0
*/
public function __toString()
{
$query = '';
switch ($this->type)
{
case 'select':
// Add required aliases for offset or fixGroupColumns method
$columns = $this->fixSelectAliases();
$query = (string) $this->select;
if ($this->group)
{
$this->fixGroupColumns($columns);
}
$query .= (string) $this->from;
if ($this->join)
{
// Special case for joins
foreach ($this->join as $join)
{
$query .= (string) $join;
}
}
if ($this->where)
{
$query .= (string) $this->where;
}
if ($this->selectRowNumber === null)
{
if ($this->group)
{
$query .= (string) $this->group;
}
if ($this->having)
{
$query .= (string) $this->having;
}
}
if ($this->order)
{
$query .= (string) $this->order;
}
if ($this instanceof JDatabaseQueryLimitable &&
($this->limit > 0 || $this->offset > 0))
{
$query = $this->processLimit($query, $this->limit,
$this->offset);
}
break;
case 'insert':
$query .= (string) $this->insert;
// Set method
if ($this->set)
{
$query .= (string) $this->set;
}
// Columns-Values method
elseif ($this->values)
{
if ($this->columns)
{
$query .= (string) $this->columns;
}
$elements = $this->insert->getElements();
$tableName = array_shift($elements);
$query .= 'VALUES ';
$query .= (string) $this->values;
if ($this->autoIncrementField)
{
$query = 'SET IDENTITY_INSERT ' . $tableName . '
ON;' . $query . 'SET IDENTITY_INSERT ' . $tableName . '
OFF;';
}
if ($this->where)
{
$query .= (string) $this->where;
}
}
break;
case 'delete':
$query .= (string) $this->delete;
$query .= (string) $this->from;
if ($this->join)
{
// Special case for joins
foreach ($this->join as $join)
{
$query .= (string) $join;
}
}
if ($this->where)
{
$query .= (string) $this->where;
}
if ($this->order)
{
$query .= (string) $this->order;
}
break;
case 'update':
if ($this->join)
{
$tmpUpdate = $this->update;
$tmpFrom = $this->from;
$this->update = null;
$this->from = null;
$updateElem = $tmpUpdate->getElements();
$updateArray = explode(' ', $updateElem[0]);
// Use table alias if exists
$this->update(end($updateArray));
$this->from($updateElem[0]);
$query .= (string) $this->update;
$query .= (string) $this->set;
$query .= (string) $this->from;
$this->update = $tmpUpdate;
$this->from = $tmpFrom;
// Special case for joins
foreach ($this->join as $join)
{
$query .= (string) $join;
}
}
else
{
$query .= (string) $this->update;
$query .= (string) $this->set;
}
if ($this->where)
{
$query .= (string) $this->where;
}
if ($this->order)
{
$query .= (string) $this->order;
}
break;
default:
$query = parent::__toString();
break;
}
return $query;
}
/**
* Casts a value to a char.
*
* Ensure that the value is properly quoted before passing to the method.
*
* @param string $value The value to cast as a char.
*
* @param string $len The length of the char.
*
* @return string Returns the cast value.
*
* @since 1.7.0
*/
public function castAsChar($value, $len = null)
{
if (!$len)
{
return 'CAST(' . $value . ' as NVARCHAR(30))';
}
else
{
return 'CAST(' . $value . ' as NVARCHAR(' . $len .
'))';
}
}
/**
* Gets the function to determine the length of a character string.
*
* @param string $field A value.
* @param string $operator Comparison operator between charLength
integer value and $condition
* @param string $condition Integer value to compare charLength with.
*
* @return string The required char length call.
*
* @since 1.7.0
*/
public function charLength($field, $operator = null, $condition = null)
{
return 'DATALENGTH(' . $field . ')' .
(isset($operator) && isset($condition) ? ' ' . $operator
. ' ' . $condition : '');
}
/**
* Concatenates an array of column names or values.
*
* @param array $values An array of values to concatenate.
* @param string $separator As separator to place between each value.
*
* @return string The concatenated values.
*
* @since 1.7.0
*/
public function concatenate($values, $separator = null)
{
if ($separator)
{
return '(' . implode('+' .
$this->quote($separator) . '+', $values) . ')';
}
else
{
return '(' . implode('+', $values) . ')';
}
}
/**
* Gets the current date and time.
*
* @return string
*
* @since 1.7.0
*/
public function currentTimestamp()
{
return 'GETDATE()';
}
/**
* Get the length of a string in bytes.
*
* @param string $value The string to measure.
*
* @return integer
*
* @since 1.7.0
*/
public function length($value)
{
return 'LEN(' . $value . ')';
}
/**
* Add to the current date and time.
* Usage:
* $query->select($query->dateAdd());
* Prefixing the interval with a - (negative sign) will cause subtraction
to be used.
*
* @param datetime $date The date to add to; type may be time or
datetime.
* @param string $interval The string representation of the
appropriate number of units
* @param string $datePart The part of the date to perform the
addition on
*
* @return string The string with the appropriate sql for addition of
dates
*
* @since 3.2.0
* @note Not all drivers support all units.
* @link http://msdn.microsoft.com/en-us/library/ms186819.aspx for more
information
*/
public function dateAdd($date, $interval, $datePart)
{
return 'DATEADD(' . $datePart . ', ' . $interval .
', ' . $date . ')';
}
/**
* Method to modify a query already in string format with the needed
* additions to make the query limited to a particular number of
* results, or start at a particular offset.
*
* @param string $query The query in string format
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return string
*
* @since 3.0.0
*/
public function processLimit($query, $limit, $offset = 0)
{
if ($limit)
{
$total = $offset + $limit;
$position = stripos($query, 'SELECT');
$distinct = stripos($query, 'SELECT DISTINCT');
if ($position === $distinct)
{
$query = substr_replace($query, 'SELECT DISTINCT TOP ' .
(int) $total, $position, 15);
}
else
{
$query = substr_replace($query, 'SELECT TOP ' . (int) $total,
$position, 6);
}
}
if (!$offset)
{
return $query;
}
return PHP_EOL
. 'SELECT * FROM (SELECT *, ROW_NUMBER() OVER (ORDER BY (SELECT 0))
AS RowNumber FROM ('
. $query
. PHP_EOL . ') AS A) AS A WHERE RowNumber > ' . (int)
$offset;
}
/**
* Sets the offset and limit for the result set, if the database driver
supports it.
*
* Usage:
* $query->setLimit(100, 0); (retrieve 100 rows, starting at first
record)
* $query->setLimit(50, 50); (retrieve 50 rows, starting at 50th
record)
*
* @param integer $limit The limit for the result set
* @param integer $offset The offset for the result set
*
* @return JDatabaseQuery Returns this object to allow chaining.
*
* @since 3.0.0
*/
public function setLimit($limit = 0, $offset = 0)
{
$this->limit = (int) $limit;
$this->offset = (int) $offset;
return $this;
}
/**
* Split a string of sql expression into an array of individual columns.
* Single line or line end comments and multi line comments are stripped
off.
* Always return at least one column.
*
* @param string $string Input string of sql expression like select
expression.
*
* @return array[] The columns from the input string separated into an
array.
*
* @since 3.7.0
*/
protected function splitSqlExpression($string)
{
// Append whitespace as equivalent to the last comma
$string .= ' ';
$colIdx = 0;
$start = 0;
$open = false;
$openC = 0;
$comment = false;
$endString = '';
$length = strlen($string);
$columns = array();
$column = array();
$current = '';
$previous = null;
$operators = array(
'+' => '',
'-' => '',
'*' => '',
'/' => '',
'%' => '',
'&' => '',
'|' => '',
'~' => '',
'^' => '',
);
$addBlock = function ($block) use (&$column, &$colIdx)
{
if (isset($column[$colIdx]))
{
$column[$colIdx] .= $block;
}
else
{
$column[$colIdx] = $block;
}
};
for ($i = 0; $i < $length; $i++)
{
$current = substr($string, $i, 1);
$current2 = substr($string, $i, 2);
$current3 = substr($string, $i, 3);
$lenEndString = strlen($endString);
$testEnd = substr($string, $i, $lenEndString);
if ($current == '[' || $current == '"' ||
$current == "'" || $current2 == '--'
|| ($current2 == '/*') || ($current == '#'
&& $current3 != '#__')
|| ($lenEndString && $testEnd == $endString))
{
if ($open)
{
if ($testEnd === $endString)
{
if ($comment)
{
if ($lenEndString > 1)
{
$i += ($lenEndString - 1);
}
// Move cursor after close tag of comment
$start = $i + 1;
$comment = false;
}
elseif ($current == "'" || $current == ']'
|| $current == '"')
{
// Check for escaped quote like '', ]] or ""
$n = 1;
while ($i + $n < $length && $string[$i + $n] == $current)
{
$n++;
}
// Jump to the last quote
$i += $n - 1;
if ($n % 2 === 0)
{
// There is only escaped quote
continue;
}
elseif ($n > 2)
{
// The last right close quote is not escaped
$current = $string[$i];
}
}
$open = false;
$endString = '';
}
}
else
{
$open = true;
if ($current == '#' || $current2 == '--')
{
$endString = "\n";
$comment = true;
}
elseif ($current2 == '/*')
{
$endString = '*/';
$comment = true;
}
elseif ($current == '[')
{
$endString = ']';
}
else
{
$endString = $current;
}
if ($comment && $start < $i)
{
// Add string exists before comment
$addBlock(substr($string, $start, $i - $start));
$previous = $string[$i - 1];
$start = $i;
}
}
}
elseif (!$open)
{
if ($current == '(')
{
$openC++;
$previous = $current;
}
elseif ($current == ')')
{
$openC--;
$previous = $current;
}
elseif ($current == '.')
{
if ($i === $start && $colIdx > 0 &&
!isset($column[$colIdx]))
{
// Remove whitepace placed before dot
$colIdx--;
}
$previous = $current;
}
elseif ($openC === 0)
{
if (ctype_space($current))
{
// Normalize whitepace
$string[$i] = ' ';
if ($start < $i)
{
// Add text placed before whitespace
$addBlock(substr($string, $start, $i - $start));
$colIdx++;
$previous = $string[$i - 1];
}
elseif (isset($column[$colIdx]))
{
if ($colIdx > 1 || !isset($operators[$previous]))
{
// There was whitespace after comment
$colIdx++;
}
}
// Move cursor forward
$start = $i + 1;
}
elseif (isset($operators[$current]) && ($current !==
'*' || $previous !== '.'))
{
if ($start < $i)
{
// Add text before operator
$addBlock(substr($string, $start, $i - $start));
$colIdx++;
}
elseif (!isset($column[$colIdx]) &&
isset($operators[$previous]))
{
// Do not create whitespace between operators
$colIdx--;
}
// Add operator
$addBlock($current);
$previous = $current;
$colIdx++;
// Move cursor forward
$start = $i + 1;
}
else
{
$previous = $current;
}
}
}
if (($current == ',' && !$open && $openC == 0)
|| $i == $length - 1)
{
if ($start < $i && !$comment)
{
// Save remaining text
$addBlock(substr($string, $start, $i - $start));
}
$columns[] = $column;
// Reset values
$column = array();
$colIdx = 0;
$previous = null;
// Column saved, move cursor forward after comma
$start = $i + 1;
}
}
return $columns;
}
/**
* Add required aliases to columns for select statement in subquery.
*
* @return array[] Array of columns with added missing aliases.
*
* @since 3.7.0
*/
protected function fixSelectAliases()
{
$operators = array(
'+' => '',
'-' => '',
'*' => '',
'/' => '',
'%' => '',
'&' => '',
'|' => '',
'~' => '',
'^' => '',
);
// Split into array and remove comments
$columns = $this->splitSqlExpression(implode(',',
$this->select->getElements()));
foreach ($columns as $i => $column)
{
$size = count($column);
if ($size == 0)
{
continue;
}
if ($size > 2 && strcasecmp($column[$size - 2],
'AS') === 0)
{
// Alias exists, replace it to uppercase
$columns[$i][$size - 2] = 'AS';
continue;
}
if ($i == 0 && stripos(' DISTINCT ALL ', "
$column[0] ") !== false)
{
// This words are reserved, they are not column names
array_shift($column);
$size--;
}
$lastWord = strtoupper($column[$size - 1]);
$length = strlen($lastWord);
$lastChar = $lastWord[$length - 1];
if ($lastChar == '*')
{
// Skip on wildcard
continue;
}
if ($lastChar == ')'
|| ($size == 1 && $lastChar == "'")
|| $lastWord[0] == '@'
|| $lastWord == 'NULL'
|| $lastWord == 'END'
|| is_numeric($lastWord))
{
/* Ends with:
* - SQL function
* - single static value like 'only '+'string'
* - @@var
* - NULL
* - CASE ... END
* - Numeric
*/
$columns[$i][] = 'AS';
$columns[$i][] = $this->quoteName('columnAlias' . $i);
continue;
}
if ($size == 1)
{
continue;
}
$lastChar2 = substr($column[$size - 2], -1);
// Check if column ends with '- a.x' or '- a. x'
if (isset($operators[$lastChar2])
|| ($size > 2 && $lastChar2 === '.' &&
isset($operators[substr($column[$size - 3], -1)])))
{
// Ignore plus signs if column start with them
if ($size != 2 || ltrim($column[0], '+') !== '' ||
$column[1][0] === "'")
{
// If operator exists before last word then alias is required for
subquery
$columns[$i][] = 'AS';
$columns[$i][] = $this->quoteName('columnAlias' . $i);
continue;
}
}
elseif ($column[$size - 1][0] !== '.' && $lastChar2
!== '.')
{
// If columns is like name name2 then second word is alias.
// Add missing AS before the alias, exception for 'a. x' and
'a .x'
array_splice($columns[$i], -1, 0, 'AS');
}
}
$selectColumns = array();
foreach ($columns as $i => $column)
{
$selectColumns[$i] = implode(' ', $column);
}
$this->select = new JDatabaseQueryElement('SELECT',
$selectColumns);
return $columns;
}
/**
* Add missing columns names to GROUP BY clause.
*
* @param array[] $selectColumns Array of columns from
splitSqlExpression method.
*
* @return JDatabaseQuery Returns this object to allow chaining.
*
* @since 3.7.0
*/
protected function fixGroupColumns($selectColumns)
{
// Cache tables columns
static $cacheCols = array();
// Known columns of all included tables
$knownColumnsByAlias = array();
$iquotes = array('"' => '', '['
=> '', "'" => '');
$nquotes = array('"', '[', ']');
// Aggregate functions
$aFuncs = array(
'AVG(',
'CHECKSUM_AGG(',
'COUNT(',
'COUNT_BIG(',
'GROUPING(',
'GROUPING_ID(',
'MIN(',
'MAX(',
'SUM(',
'STDEV(',
'STDEVP(',
'VAR(',
'VARP(',
);
// Aggregated columns
$filteredColumns = array();
// Aliases found in SELECT statement
$knownAliases = array();
$wildcardTables = array();
foreach ($selectColumns as $i => $column)
{
$size = count($column);
if ($size === 0)
{
continue;
}
if ($i == 0 && stripos(' DISTINCT ALL ', "
$column[0] ") !== false)
{
// These words are reserved, they are not column names
array_shift($selectColumns[0]);
array_shift($column);
$size--;
}
if ($size > 2 && $column[$size - 2] === 'AS')
{
// Save and remove AS alias
$alias = $column[$size - 1];
if (isset($iquotes[$alias[0]]))
{
$alias = substr($alias, 1, -1);
}
// Remove alias
$selectColumns[$i] = $column = array_slice($column, 0, -2);
if ($size === 3 || ($size === 4 &&
strpos('+-*/%&|~^', $column[0][0]) !== false))
{
$lastWord = $column[$size - 3];
if ($lastWord[0] === "'" || $lastWord ===
'NULL' || is_numeric($lastWord))
{
unset($selectColumns[$i]);
continue;
}
}
// Remember pair alias => column expression
$knownAliases[$alias] = implode(' ', $column);
}
$aggregated = false;
foreach ($column as $j => $block)
{
if (substr($block, -2) === '.*')
{
// Found column ends with .*
if (isset($iquotes[$block[0]]))
{
// Quoted table
$wildcardTables[] = substr($block, 1, -3);
}
else
{
$wildcardTables[] = substr($block, 0, -2);
}
}
elseif (str_ireplace($aFuncs, '', $block) != $block)
{
$aggregated = true;
}
if ($block[0] === "'")
{
// Shrink static strings which could contain column name
$column[$j] = "''";
}
}
if (!$aggregated)
{
// Without aggregated columns and aliases
$filteredColumns[] = implode(' ', $selectColumns[$i]);
}
// Without aliases and static strings
$selectColumns[$i] = implode(' ', $column);
}
// If select statement use table.* expression
if ($wildcardTables)
{
// Split FROM statement into list of tables
$tables = $this->splitSqlExpression(implode(',',
$this->from->getElements()));
foreach ($tables as $i => $table)
{
$table = implode(' ', $table);
// Exclude subquery from the FROM clause
if (strpos($table, '(') === false)
{
// Unquote
$table = str_replace($nquotes, '', $table);
$table = str_replace('#__', $this->db->getPrefix(),
$table);
$table = explode(' ', $table);
$alias = end($table);
$table = $table[0];
// Chek if exists a wildcard with current alias table?
if (in_array($alias, $wildcardTables, true))
{
if (!isset($cacheCols[$table]))
{
$cacheCols[$table] = $this->db->getTableColumns($table);
}
if ($this->join || $table != $alias)
{
foreach ($cacheCols[$table] as $name => $type)
{
$knownColumnsByAlias[$alias][] = $alias . '.' . $name;
}
}
else
{
foreach ($cacheCols[$table] as $name => $type)
{
$knownColumnsByAlias[$alias][] = $name;
}
}
}
}
}
// Now we need to get all tables from any joins
// Go through all joins and add them to the tables array
if ($this->join)
{
foreach ($this->join as $join)
{
// Unquote and replace prefix
$joinTbl = str_replace($nquotes, '', (string) $join);
$joinTbl = str_replace("#__", $this->db->getPrefix(),
$joinTbl);
// Exclude subquery
if (preg_match('/JOIN\s+(\w+)(?:\s+AS)?(?:\s+(\w+))?/i',
$joinTbl, $matches))
{
$table = $matches[1];
$alias = isset($matches[2]) ? $matches[2] : $table;
// Chek if exists a wildcard with current alias table?
if (in_array($alias, $wildcardTables, true))
{
if (!isset($cacheCols[$table]))
{
$cacheCols[$table] = $this->db->getTableColumns($table);
}
foreach ($cacheCols[$table] as $name => $type)
{
$knownColumnsByAlias[$alias][] = $alias . '.' . $name;
}
}
}
}
}
}
$selectExpression = implode(',', $selectColumns);
// Split into the right columns
$groupColumns = $this->splitSqlExpression(implode(',',
$this->group->getElements()));
// Remove column aliases from GROUP statement - SQLSRV does not support
it
foreach ($groupColumns as $i => $column)
{
$groupColumns[$i] = implode(' ', $column);
$column = str_replace($nquotes, '', $groupColumns[$i]);
if (isset($knownAliases[$column]))
{
// Be sure that this is not a valid column name
if (!preg_match('/\b' . preg_quote($column, '/') .
'\b/', $selectExpression))
{
// Replace column alias by column expression
$groupColumns[$i] = $knownAliases[$column];
}
}
}
// Find all alias.* and fill with proper table column names
foreach ($filteredColumns as $i => $column)
{
if (substr($column, -2) === '.*')
{
unset($filteredColumns[$i]);
// Extract alias.* columns into GROUP BY statement
$groupColumns = array_merge($groupColumns,
$knownColumnsByAlias[substr($column, 0, -2)]);
}
}
$groupColumns = array_merge($groupColumns, $filteredColumns);
if ($this->order)
{
// Remove direction suffixes
$dir = array(" DESC\v", " ASC\v");
$orderColumns = $this->splitSqlExpression(implode(',',
$this->order->getElements()));
foreach ($orderColumns as $i => $column)
{
$column = implode(' ', $column);
$orderColumns[$i] = $column = trim(str_ireplace($dir, '',
"$column\v"), "\v");
if (isset($knownAliases[str_replace($nquotes, '', $column)]))
{
unset($orderColumns[$i]);
}
if (str_ireplace($aFuncs, '', $column) != $column)
{
// Do not add aggregate expression
unset($orderColumns[$i]);
}
}
$groupColumns = array_merge($groupColumns, $orderColumns);
}
// Get a unique string of all column names that need to be included in
the group statement
$this->group = new JDatabaseQueryElement('GROUP BY',
array_unique($groupColumns));
return $this;
}
/**
* Return correct rand() function for MSSQL.
*
* Ensure that the rand() function is MSSQL compatible.
*
* Usage:
* $query->Rand();
*
* @return string The correct rand function.
*
* @since 3.5
*/
public function Rand()
{
return ' NEWID() ';
}
}
abstract.php000064400000001761151160642700007067 0ustar00<?php
/**
* @package FrameworkOnFramework
* @subpackage query
* @copyright Copyright (C) 2010-2016 Nicholas K. Dionysopoulos / Akeeba
Ltd. All rights reserved.
* @license GNU General Public License version 2 or later; see
LICENSE.txt
*/
// Protect from unauthorized access
defined('FOF_INCLUDED') or die;
/**
* FrameworkOnFramework query base class; for compatibility purposes
*
* @package FrameworkOnFramework
* @since 2.1
* @deprecated 2.1
*/
abstract class FOFQueryAbstract
{
/**
* Returns a new database query class
*
* @param FOFDatabaseDriver $db The DB driver which will provide us
with a query object
*
* @return FOFQueryAbstract
*/
public static function &getNew($db = null)
{
FOFPlatform::getInstance()->logDeprecated('FOFQueryAbstract is
deprecated. Use FOFDatabaseQuery instead.');
if (is_null($db))
{
$ret = FOFPlatform::getInstance()->getDbo()->getQuery(true);
}
else
{
$ret = $db->getQuery(true);
}
return $ret;
}
}