Update types for limit clauses, misc improvements
This commit is contained in:
parent
2620df1589
commit
c67fabd1f7
@ -34,14 +34,14 @@
|
|||||||
"require-dev": {
|
"require-dev": {
|
||||||
"consolidation/robo": "^2.0.0",
|
"consolidation/robo": "^2.0.0",
|
||||||
"monolog/monolog": "^2.0.1",
|
"monolog/monolog": "^2.0.1",
|
||||||
"phploc/phploc": "^6.0",
|
"phploc/phploc": "^5.0",
|
||||||
"phpmd/phpmd": "^2.8",
|
"phpmd/phpmd": "^2.8",
|
||||||
"phpstan/phpstan": "^0.12.2",
|
"phpstan/phpstan": "^0.12.2",
|
||||||
"phpunit/phpunit": "^9.1",
|
"phpunit/phpunit": "^8.5",
|
||||||
"sebastian/phpcpd": "^5",
|
"sebastian/phpcpd": "^4.1",
|
||||||
"simpletest/simpletest": "^1.1",
|
"simpletest/simpletest": "^1.1",
|
||||||
"squizlabs/php_codesniffer": "^3.0.0",
|
"squizlabs/php_codesniffer": "^3.0.0",
|
||||||
"theseer/phpdox": "*"
|
"theseer/phpdox": "^0.12.0"
|
||||||
},
|
},
|
||||||
"autoload": {
|
"autoload": {
|
||||||
"psr-4": {
|
"psr-4": {
|
||||||
|
@ -16,6 +16,7 @@
|
|||||||
namespace Query;
|
namespace Query;
|
||||||
|
|
||||||
use DomainException;
|
use DomainException;
|
||||||
|
use stdClass;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Connection manager class to manage connections for the
|
* Connection manager class to manage connections for the
|
||||||
@ -33,7 +34,7 @@ final class ConnectionManager {
|
|||||||
* Class instance variable
|
* Class instance variable
|
||||||
* @var ConnectionManager|null
|
* @var ConnectionManager|null
|
||||||
*/
|
*/
|
||||||
private static $instance;
|
private static ?ConnectionManager $instance = NULL;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Private constructor to prevent multiple instances
|
* Private constructor to prevent multiple instances
|
||||||
@ -119,7 +120,7 @@ final class ConnectionManager {
|
|||||||
/**
|
/**
|
||||||
* Parse the passed parameters and return a connection
|
* Parse the passed parameters and return a connection
|
||||||
*
|
*
|
||||||
* @param object|array $params
|
* @param array|object $params
|
||||||
* @throws Exception\BadDBDriverException
|
* @throws Exception\BadDBDriverException
|
||||||
* @return QueryBuilderInterface
|
* @return QueryBuilderInterface
|
||||||
*/
|
*/
|
||||||
@ -161,13 +162,13 @@ final class ConnectionManager {
|
|||||||
/**
|
/**
|
||||||
* Parses params into a dsn and option array
|
* Parses params into a dsn and option array
|
||||||
*
|
*
|
||||||
* @param object | array $params
|
* @param array|object $rawParams
|
||||||
* @return array
|
* @return array
|
||||||
* @throws Exception\BadDBDriverException
|
* @throws Exception\BadDBDriverException
|
||||||
*/
|
*/
|
||||||
public function parseParams($params): array
|
public function parseParams($rawParams): array
|
||||||
{
|
{
|
||||||
$params = (object) $params;
|
$params = (object) $rawParams;
|
||||||
$params->type = strtolower($params->type);
|
$params->type = strtolower($params->type);
|
||||||
$dbType = ($params->type === 'postgresql') ? 'pgsql' : $params->type;
|
$dbType = ($params->type === 'postgresql') ? 'pgsql' : $params->type;
|
||||||
$dbType = ucfirst($dbType);
|
$dbType = ucfirst($dbType);
|
||||||
@ -205,10 +206,10 @@ final class ConnectionManager {
|
|||||||
*
|
*
|
||||||
* @codeCoverageIgnore
|
* @codeCoverageIgnore
|
||||||
* @param string $dbType
|
* @param string $dbType
|
||||||
* @param array|object $params
|
* @param stdClass $params
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
private function createDsn(string $dbType, $params): string
|
private function createDsn(string $dbType, stdClass $params): string
|
||||||
{
|
{
|
||||||
$pairs = [];
|
$pairs = [];
|
||||||
|
|
||||||
|
@ -20,6 +20,7 @@ use function dbFilter;
|
|||||||
use InvalidArgumentException;
|
use InvalidArgumentException;
|
||||||
use PDO;
|
use PDO;
|
||||||
use PDOStatement;
|
use PDOStatement;
|
||||||
|
use function is_string;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Base Database class
|
* Base Database class
|
||||||
@ -52,7 +53,7 @@ abstract class AbstractDriver
|
|||||||
* Reference to sql class
|
* Reference to sql class
|
||||||
* @var SQLInterface
|
* @var SQLInterface
|
||||||
*/
|
*/
|
||||||
protected SQLInterface $sql;
|
protected SQLInterface $driverSQL;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Reference to util class
|
* Reference to util class
|
||||||
@ -110,7 +111,7 @@ abstract class AbstractDriver
|
|||||||
$sqlClass = __NAMESPACE__ . "\\{$driver}\\SQL";
|
$sqlClass = __NAMESPACE__ . "\\{$driver}\\SQL";
|
||||||
$utilClass = __NAMESPACE__ . "\\{$driver}\\Util";
|
$utilClass = __NAMESPACE__ . "\\{$driver}\\Util";
|
||||||
|
|
||||||
$this->sql = new $sqlClass();
|
$this->driverSQL = new $sqlClass();
|
||||||
$this->util = new $utilClass($this);
|
$this->util = new $utilClass($this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -168,7 +169,7 @@ abstract class AbstractDriver
|
|||||||
*/
|
*/
|
||||||
public function getSql(): SQLInterface
|
public function getSql(): SQLInterface
|
||||||
{
|
{
|
||||||
return $this->sql;
|
return $this->driverSQL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -494,7 +495,7 @@ abstract class AbstractDriver
|
|||||||
public function driverQuery($query, $filteredIndex=TRUE): ?array
|
public function driverQuery($query, $filteredIndex=TRUE): ?array
|
||||||
{
|
{
|
||||||
// Call the appropriate method, if it exists
|
// Call the appropriate method, if it exists
|
||||||
if (is_string($query) && method_exists($this->sql, $query))
|
if (is_string($query) && method_exists($this->driverSQL, $query))
|
||||||
{
|
{
|
||||||
$query = $this->getSql()->$query();
|
$query = $this->getSql()->$query();
|
||||||
}
|
}
|
||||||
@ -687,7 +688,7 @@ abstract class AbstractDriver
|
|||||||
// and is not already quoted before quoting
|
// and is not already quoted before quoting
|
||||||
// that value, otherwise, return the original value
|
// that value, otherwise, return the original value
|
||||||
return (
|
return (
|
||||||
\is_string($str)
|
is_string($str)
|
||||||
&& strpos($str, $this->escapeCharOpen) !== 0
|
&& strpos($str, $this->escapeCharOpen) !== 0
|
||||||
&& strrpos($str, $this->escapeCharClose) !== 0
|
&& strrpos($str, $this->escapeCharClose) !== 0
|
||||||
)
|
)
|
||||||
|
@ -25,10 +25,10 @@ abstract class AbstractSQL implements SQLInterface {
|
|||||||
*
|
*
|
||||||
* @param string $sql
|
* @param string $sql
|
||||||
* @param int $limit
|
* @param int $limit
|
||||||
* @param int|bool $offset
|
* @param int $offset
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function limit(string $sql, int $limit, $offset=FALSE): string
|
public function limit(string $sql, int $limit, ?int $offset=NULL): string
|
||||||
{
|
{
|
||||||
$sql .= "\nLIMIT {$limit}";
|
$sql .= "\nLIMIT {$limit}";
|
||||||
|
|
||||||
|
@ -17,6 +17,7 @@ namespace Query\Drivers\Mysql;
|
|||||||
|
|
||||||
use PDO;
|
use PDO;
|
||||||
use Query\Drivers\AbstractDriver;
|
use Query\Drivers\AbstractDriver;
|
||||||
|
use function defined;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* MySQL specific class
|
* MySQL specific class
|
||||||
@ -49,7 +50,7 @@ class Driver extends AbstractDriver {
|
|||||||
public function __construct(string $dsn, string $username=NULL, string $password=NULL, array $options=[])
|
public function __construct(string $dsn, string $username=NULL, string $password=NULL, array $options=[])
|
||||||
{
|
{
|
||||||
// Set the charset to UTF-8
|
// Set the charset to UTF-8
|
||||||
if (\defined('\\PDO::MYSQL_ATTR_INIT_COMMAND'))
|
if (defined('\\PDO::MYSQL_ATTR_INIT_COMMAND'))
|
||||||
{
|
{
|
||||||
$options = array_merge($options, [
|
$options = array_merge($options, [
|
||||||
PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES UTF-8 COLLATE 'UTF-8'",
|
PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES UTF-8 COLLATE 'UTF-8'",
|
||||||
|
@ -30,7 +30,7 @@ class SQL extends AbstractSQL {
|
|||||||
* @param int|boolean $offset
|
* @param int|boolean $offset
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function limit(string $sql, int $limit, $offset=FALSE): string
|
public function limit(string $sql, int $limit, ?int $offset=NULL): string
|
||||||
{
|
{
|
||||||
if ( ! is_numeric($offset))
|
if ( ! is_numeric($offset))
|
||||||
{
|
{
|
||||||
@ -166,7 +166,7 @@ SQL;
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* SQL to show infromation about columns in a table
|
* SQL to show information about columns in a table
|
||||||
*
|
*
|
||||||
* @param string $table
|
* @param string $table
|
||||||
* @return string
|
* @return string
|
||||||
@ -186,7 +186,7 @@ SQL;
|
|||||||
public function fkList(string $table): string
|
public function fkList(string $table): string
|
||||||
{
|
{
|
||||||
return <<<SQL
|
return <<<SQL
|
||||||
SELECT DISTINCT
|
SELECT DISTINCT
|
||||||
`kcu`.`COLUMN_NAME` as `child_column`,
|
`kcu`.`COLUMN_NAME` as `child_column`,
|
||||||
`kcu`.`REFERENCED_TABLE_NAME` as `parent_table`,
|
`kcu`.`REFERENCED_TABLE_NAME` as `parent_table`,
|
||||||
`kcu`.`REFERENCED_COLUMN_NAME` as `parent_column`,
|
`kcu`.`REFERENCED_COLUMN_NAME` as `parent_column`,
|
||||||
|
@ -33,7 +33,8 @@ class Util extends AbstractUtil {
|
|||||||
$string = [];
|
$string = [];
|
||||||
|
|
||||||
// Get databases
|
// Get databases
|
||||||
$dbs = $this->getDriver()->getDbs();
|
$driver = $this->getDriver();
|
||||||
|
$dbs = $driver->getDbs();
|
||||||
|
|
||||||
foreach($dbs as &$d)
|
foreach($dbs as &$d)
|
||||||
{
|
{
|
||||||
@ -46,11 +47,11 @@ class Util extends AbstractUtil {
|
|||||||
// @codeCoverageIgnoreEnd
|
// @codeCoverageIgnoreEnd
|
||||||
|
|
||||||
// Get the list of tables
|
// Get the list of tables
|
||||||
$tables = $this->getDriver()->driverQuery("SHOW TABLES FROM `{$d}`", TRUE);
|
$tables = $driver->driverQuery("SHOW TABLES FROM `{$d}`", TRUE);
|
||||||
|
|
||||||
foreach($tables as $table)
|
foreach($tables as $table)
|
||||||
{
|
{
|
||||||
$array = $this->getDriver()->driverQuery("SHOW CREATE TABLE `{$d}`.`{$table}`", FALSE);
|
$array = $driver->driverQuery("SHOW CREATE TABLE `{$d}`.`{$table}`", FALSE);
|
||||||
$row = current($array);
|
$row = current($array);
|
||||||
|
|
||||||
if ( ! isset($row['Create Table']))
|
if ( ! isset($row['Create Table']))
|
||||||
@ -72,9 +73,10 @@ class Util extends AbstractUtil {
|
|||||||
* @param array $exclude
|
* @param array $exclude
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function backupData($exclude=[]): string
|
public function backupData(array $exclude=[]): string
|
||||||
{
|
{
|
||||||
$tables = $this->getDriver()->getTables();
|
$driver = $this->getDriver();
|
||||||
|
$tables = $driver->getTables();
|
||||||
|
|
||||||
// Filter out the tables you don't want
|
// Filter out the tables you don't want
|
||||||
if( ! empty($exclude))
|
if( ! empty($exclude))
|
||||||
@ -88,7 +90,7 @@ class Util extends AbstractUtil {
|
|||||||
foreach($tables as $t)
|
foreach($tables as $t)
|
||||||
{
|
{
|
||||||
$sql = "SELECT * FROM `{$t}`";
|
$sql = "SELECT * FROM `{$t}`";
|
||||||
$res = $this->getDriver()->query($sql);
|
$res = $driver->query($sql);
|
||||||
$rows = $res->fetchAll(PDO::FETCH_ASSOC);
|
$rows = $res->fetchAll(PDO::FETCH_ASSOC);
|
||||||
|
|
||||||
// Skip empty tables
|
// Skip empty tables
|
||||||
@ -110,7 +112,7 @@ class Util extends AbstractUtil {
|
|||||||
// Workaround for Quercus
|
// Workaround for Quercus
|
||||||
foreach($row as &$r)
|
foreach($row as &$r)
|
||||||
{
|
{
|
||||||
$r = $this->getDriver()->quote($r);
|
$r = $driver->quote($r);
|
||||||
}
|
}
|
||||||
unset($r);
|
unset($r);
|
||||||
$row = array_map('trim', $row);
|
$row = array_map('trim', $row);
|
||||||
|
@ -15,6 +15,7 @@
|
|||||||
*/
|
*/
|
||||||
namespace Query\Drivers\Pgsql;
|
namespace Query\Drivers\Pgsql;
|
||||||
|
|
||||||
|
use PDO;
|
||||||
use Query\Drivers\AbstractUtil;
|
use Query\Drivers\AbstractUtil;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -56,7 +57,7 @@ class Util extends AbstractUtil {
|
|||||||
{
|
{
|
||||||
$sql = 'SELECT * FROM "'.trim($t).'"';
|
$sql = 'SELECT * FROM "'.trim($t).'"';
|
||||||
$res = $this->getDriver()->query($sql);
|
$res = $this->getDriver()->query($sql);
|
||||||
$objRes = $res->fetchAll(\PDO::FETCH_ASSOC);
|
$objRes = $res->fetchAll(PDO::FETCH_ASSOC);
|
||||||
|
|
||||||
// Don't add to the file if the table is empty
|
// Don't add to the file if the table is empty
|
||||||
if (count($objRes) < 1)
|
if (count($objRes) < 1)
|
||||||
|
@ -25,10 +25,10 @@ interface SQLInterface {
|
|||||||
*
|
*
|
||||||
* @param string $sql
|
* @param string $sql
|
||||||
* @param int $limit
|
* @param int $limit
|
||||||
* @param int|bool $offset
|
* @param int|null $offset
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function limit(string $sql, int $limit, $offset=FALSE): string;
|
public function limit(string $sql, int $limit, ?int $offset=NULL): string;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Modify the query to get the query plan
|
* Modify the query to get the query plan
|
||||||
|
@ -68,7 +68,7 @@ class Driver extends AbstractDriver {
|
|||||||
*/
|
*/
|
||||||
public function getTables(): array
|
public function getTables(): array
|
||||||
{
|
{
|
||||||
$sql = $this->sql->tableList();
|
$sql = $this->getSql()->tableList();
|
||||||
$res = $this->query($sql);
|
$res = $this->query($sql);
|
||||||
return dbFilter($res->fetchAll(PDO::FETCH_ASSOC), 'name');
|
return dbFilter($res->fetchAll(PDO::FETCH_ASSOC), 'name');
|
||||||
}
|
}
|
||||||
|
@ -57,7 +57,7 @@ class Util extends AbstractUtil {
|
|||||||
|
|
||||||
unset($res);
|
unset($res);
|
||||||
|
|
||||||
// If the row is empty, continue;
|
// If the row is empty, continue
|
||||||
if (empty($objRes))
|
if (empty($objRes))
|
||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
|
28
src/MapType.php
Normal file
28
src/MapType.php
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
<?php declare(strict_types=1);
|
||||||
|
/**
|
||||||
|
* Query
|
||||||
|
*
|
||||||
|
* SQL Query Builder / Database Abstraction Layer
|
||||||
|
*
|
||||||
|
* PHP version 7.4
|
||||||
|
*
|
||||||
|
* @package Query
|
||||||
|
* @author Timothy J. Warren <tim@timshomepage.net>
|
||||||
|
* @copyright 2012 - 2020 Timothy J. Warren
|
||||||
|
* @license http://www.opensource.org/licenses/mit-license.html MIT License
|
||||||
|
* @link https://git.timshomepage.net/aviat/Query
|
||||||
|
* @version 3.0.0
|
||||||
|
*/
|
||||||
|
namespace Query;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 'Enum' of query map types
|
||||||
|
*/
|
||||||
|
class MapType {
|
||||||
|
public const GROUP_END = 'group_end';
|
||||||
|
public const GROUP_START = 'group_start';
|
||||||
|
public const JOIN = 'join';
|
||||||
|
public const LIKE = 'like';
|
||||||
|
public const WHERE = 'where';
|
||||||
|
public const WHERE_IN = 'where_in';
|
||||||
|
}
|
File diff suppressed because it is too large
Load Diff
618
src/QueryBuilderBase.php
Normal file
618
src/QueryBuilderBase.php
Normal file
@ -0,0 +1,618 @@
|
|||||||
|
<?php declare(strict_types=1);
|
||||||
|
/**
|
||||||
|
* Query
|
||||||
|
*
|
||||||
|
* SQL Query Builder / Database Abstraction Layer
|
||||||
|
*
|
||||||
|
* PHP version 7.4
|
||||||
|
*
|
||||||
|
* @package Query
|
||||||
|
* @author Timothy J. Warren <tim@timshomepage.net>
|
||||||
|
* @copyright 2012 - 2020 Timothy J. Warren
|
||||||
|
* @license http://www.opensource.org/licenses/mit-license.html MIT License
|
||||||
|
* @link https://git.timshomepage.net/aviat/Query
|
||||||
|
* @version 3.0.0
|
||||||
|
*/
|
||||||
|
namespace Query;
|
||||||
|
|
||||||
|
use function regexInArray;
|
||||||
|
|
||||||
|
use BadMethodCallException;
|
||||||
|
use PDO;
|
||||||
|
use PDOStatement;
|
||||||
|
use Query\Drivers\DriverInterface;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @method affectedRows(): int
|
||||||
|
* @method beginTransaction(): bool
|
||||||
|
* @method commit(): bool
|
||||||
|
* @method errorCode(): string
|
||||||
|
* @method errorInfo(): array
|
||||||
|
* @method exec(string $statement): int
|
||||||
|
* @method getAttribute(int $attribute)
|
||||||
|
* @method getColumns(string $table): array | null
|
||||||
|
* @method getDbs(): array | null
|
||||||
|
* @method getFks(string $table): array | null
|
||||||
|
* @method getFunctions(): array | null
|
||||||
|
* @method getIndexes(string $table): array | null
|
||||||
|
* @method getLastQuery(): string
|
||||||
|
* @method getProcedures(): array | null
|
||||||
|
* @method getSchemas(): array | null
|
||||||
|
* @method getSequences(): array | null
|
||||||
|
* @method getSystemTables(): array | null
|
||||||
|
* @method getTables(): array
|
||||||
|
* @method getTriggers(): array | null
|
||||||
|
* @method getTypes(): array | null
|
||||||
|
* @method getUtil(): \Query\Drivers\AbstractUtil
|
||||||
|
* @method getVersion(): string
|
||||||
|
* @method getViews(): array | null
|
||||||
|
* @method inTransaction(): bool
|
||||||
|
* @method lastInsertId(string $name = NULL): string
|
||||||
|
* @method numRows(): int | null
|
||||||
|
* @method prepare(string $statement, array $driver_options = []): PDOStatement
|
||||||
|
* @method prepareExecute(string $sql, array $params): PDOStatement
|
||||||
|
* @method prepareQuery(string $sql, array $data): PDOStatement
|
||||||
|
* @method query(string $statement): PDOStatement
|
||||||
|
* @method quote(string $string, int $parameter_type = PDO::PARAM_STR): string
|
||||||
|
* @method rollback(): bool
|
||||||
|
* @method setAttribute(int $attribute, $value): bool
|
||||||
|
* @method setTablePrefix(string $prefix): void
|
||||||
|
* @method truncate(string $table): PDOStatement
|
||||||
|
*/
|
||||||
|
class QueryBuilderBase {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convenience property for connection management
|
||||||
|
* @var string
|
||||||
|
*/
|
||||||
|
public string $connName = '';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* List of queries executed
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
|
public array $queries = [
|
||||||
|
'total_time' => 0
|
||||||
|
];
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Whether to do only an explain on the query
|
||||||
|
* @var bool
|
||||||
|
*/
|
||||||
|
protected bool $explain = FALSE;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Whether to return data from a modification query
|
||||||
|
* @var bool
|
||||||
|
*/
|
||||||
|
protected bool $returning = FALSE;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The current database driver
|
||||||
|
* @var DriverInterface
|
||||||
|
*/
|
||||||
|
protected ?DriverInterface $driver;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Query parser class instance
|
||||||
|
* @var QueryParser
|
||||||
|
*/
|
||||||
|
protected QueryParser $parser;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Query Builder state
|
||||||
|
* @var State
|
||||||
|
*/
|
||||||
|
protected State $state;
|
||||||
|
|
||||||
|
// --------------------------------------------------------------------------
|
||||||
|
// ! Methods
|
||||||
|
// --------------------------------------------------------------------------
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Constructor
|
||||||
|
*
|
||||||
|
* @param DriverInterface $driver
|
||||||
|
* @param QueryParser $parser
|
||||||
|
*/
|
||||||
|
public function __construct(DriverInterface $driver, QueryParser $parser)
|
||||||
|
{
|
||||||
|
// Inject driver and parser
|
||||||
|
$this->driver = $driver;
|
||||||
|
$this->parser = $parser;
|
||||||
|
|
||||||
|
// Create new State object
|
||||||
|
$this->state = new State();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Destructor
|
||||||
|
* @codeCoverageIgnore
|
||||||
|
*/
|
||||||
|
public function __destruct()
|
||||||
|
{
|
||||||
|
$this->driver = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Calls a function further down the inheritance chain.
|
||||||
|
* 'Implements' methods on the driver object
|
||||||
|
*
|
||||||
|
* @param string $name
|
||||||
|
* @param array $params
|
||||||
|
* @return mixed
|
||||||
|
* @throws BadMethodCallException
|
||||||
|
*/
|
||||||
|
public function __call(string $name, array $params)
|
||||||
|
{
|
||||||
|
if (method_exists($this->driver, $name))
|
||||||
|
{
|
||||||
|
return $this->driver->$name(...$params);
|
||||||
|
}
|
||||||
|
|
||||||
|
throw new BadMethodCallException('Method does not exist');
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clear out the class variables, so the next query can be run
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function resetQuery(): void
|
||||||
|
{
|
||||||
|
$this->state = new State();
|
||||||
|
$this->explain = FALSE;
|
||||||
|
$this->returning = FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Method to simplify select_ methods
|
||||||
|
*
|
||||||
|
* @param string $field
|
||||||
|
* @param string|bool $as
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
protected function _select(string $field, $as = FALSE): string
|
||||||
|
{
|
||||||
|
// Escape the identifiers
|
||||||
|
$field = $this->driver->quoteIdent($field);
|
||||||
|
|
||||||
|
if ( ! \is_string($as))
|
||||||
|
{
|
||||||
|
// @codeCoverageIgnoreStart
|
||||||
|
return $field;
|
||||||
|
// @codeCoverageIgnoreEnd
|
||||||
|
}
|
||||||
|
|
||||||
|
$as = $this->driver->quoteIdent($as);
|
||||||
|
return "({$field}) AS {$as} ";
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Helper function for returning sql strings
|
||||||
|
*
|
||||||
|
* @param string $type
|
||||||
|
* @param string $table
|
||||||
|
* @param bool $reset
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
protected function _getCompile(string $type, string $table, bool $reset): string
|
||||||
|
{
|
||||||
|
$sql = $this->_compile($type, $table);
|
||||||
|
|
||||||
|
// Reset the query builder for the next query
|
||||||
|
if ($reset)
|
||||||
|
{
|
||||||
|
$this->resetQuery();
|
||||||
|
}
|
||||||
|
|
||||||
|
return $sql;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Simplify 'like' methods
|
||||||
|
*
|
||||||
|
* @param string $field
|
||||||
|
* @param mixed $val
|
||||||
|
* @param string $pos
|
||||||
|
* @param string $like
|
||||||
|
* @param string $conj
|
||||||
|
* @return self
|
||||||
|
*/
|
||||||
|
protected function _like(string $field, $val, string $pos, string $like = 'LIKE', string $conj = 'AND'): self
|
||||||
|
{
|
||||||
|
$field = $this->driver->quoteIdent($field);
|
||||||
|
|
||||||
|
// Add the like string into the order map
|
||||||
|
$like = $field . " {$like} ?";
|
||||||
|
|
||||||
|
if ($pos === 'before')
|
||||||
|
{
|
||||||
|
$val = "%{$val}";
|
||||||
|
} elseif ($pos === 'after')
|
||||||
|
{
|
||||||
|
$val = "{$val}%";
|
||||||
|
} else
|
||||||
|
{
|
||||||
|
$val = "%{$val}%";
|
||||||
|
}
|
||||||
|
|
||||||
|
$conj = empty($this->state->getQueryMap()) ? ' WHERE ' : " {$conj} ";
|
||||||
|
$this->state->appendMap($conj, $like, MapType::LIKE);
|
||||||
|
|
||||||
|
// Add to the values array
|
||||||
|
$this->state->appendWhereValues($val);
|
||||||
|
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Simplify building having clauses
|
||||||
|
*
|
||||||
|
* @param mixed $key
|
||||||
|
* @param mixed $values
|
||||||
|
* @param string $conj
|
||||||
|
* @return self
|
||||||
|
*/
|
||||||
|
protected function _having($key, $values = [], string $conj = 'AND'): self
|
||||||
|
{
|
||||||
|
$where = $this->_where($key, $values);
|
||||||
|
|
||||||
|
// Create key/value placeholders
|
||||||
|
foreach ($where as $f => $val)
|
||||||
|
{
|
||||||
|
// Split each key by spaces, in case there
|
||||||
|
// is an operator such as >, <, !=, etc.
|
||||||
|
$fArray = explode(' ', trim($f));
|
||||||
|
|
||||||
|
$item = $this->driver->quoteIdent($fArray[0]);
|
||||||
|
|
||||||
|
// Simple key value, or an operator
|
||||||
|
$item .= (count($fArray) === 1) ? '=?' : " {$fArray[1]} ?";
|
||||||
|
|
||||||
|
// Put in the having map
|
||||||
|
$this->state->appendHavingMap([
|
||||||
|
'conjunction' => empty($this->state->getHavingMap())
|
||||||
|
? ' HAVING '
|
||||||
|
: " {$conj} ",
|
||||||
|
'string' => $item
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Do all the redundant stuff for where/having type methods
|
||||||
|
*
|
||||||
|
* @param mixed $key
|
||||||
|
* @param mixed $val
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
|
protected function _where($key, $val = []): array
|
||||||
|
{
|
||||||
|
$where = [];
|
||||||
|
$pairs = [];
|
||||||
|
|
||||||
|
if (is_scalar($key))
|
||||||
|
{
|
||||||
|
$pairs[$key] = $val;
|
||||||
|
} else
|
||||||
|
{
|
||||||
|
$pairs = $key;
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach ($pairs as $k => $v)
|
||||||
|
{
|
||||||
|
$where[$k] = $v;
|
||||||
|
$this->state->appendWhereValues($v);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $where;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Simplify generating where string
|
||||||
|
*
|
||||||
|
* @param mixed $key
|
||||||
|
* @param mixed $values
|
||||||
|
* @param string $defaultConj
|
||||||
|
* @return self
|
||||||
|
*/
|
||||||
|
protected function _whereString($key, $values = [], string $defaultConj = 'AND'): self
|
||||||
|
{
|
||||||
|
// Create key/value placeholders
|
||||||
|
foreach ($this->_where($key, $values) as $f => $val)
|
||||||
|
{
|
||||||
|
$queryMap = $this->state->getQueryMap();
|
||||||
|
|
||||||
|
// Split each key by spaces, in case there
|
||||||
|
// is an operator such as >, <, !=, etc.
|
||||||
|
$fArray = explode(' ', trim($f));
|
||||||
|
|
||||||
|
$item = $this->driver->quoteIdent($fArray[0]);
|
||||||
|
|
||||||
|
// Simple key value, or an operator
|
||||||
|
$item .= (count($fArray) === 1) ? '=?' : " {$fArray[1]} ?";
|
||||||
|
$lastItem = end($queryMap);
|
||||||
|
|
||||||
|
// Determine the correct conjunction
|
||||||
|
$conjunctionList = array_column($queryMap, 'conjunction');
|
||||||
|
if (empty($queryMap) || ( ! regexInArray($conjunctionList, "/^ ?\n?WHERE/i")))
|
||||||
|
{
|
||||||
|
$conj = "\nWHERE ";
|
||||||
|
} elseif ($lastItem['type'] === 'group_start')
|
||||||
|
{
|
||||||
|
$conj = '';
|
||||||
|
} else
|
||||||
|
{
|
||||||
|
$conj = " {$defaultConj} ";
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->state->appendMap($conj, $item, MapType::WHERE);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Simplify where_in methods
|
||||||
|
*
|
||||||
|
* @param mixed $key
|
||||||
|
* @param mixed $val
|
||||||
|
* @param string $in - The (not) in fragment
|
||||||
|
* @param string $conj - The where in conjunction
|
||||||
|
* @return self
|
||||||
|
*/
|
||||||
|
protected function _whereIn($key, $val = [], string $in = 'IN', string $conj = 'AND'): self
|
||||||
|
{
|
||||||
|
$key = $this->driver->quoteIdent($key);
|
||||||
|
$params = array_fill(0, count($val), '?');
|
||||||
|
$this->state->appendWhereValues($val);
|
||||||
|
|
||||||
|
$conjunction = empty($this->state->getQueryMap()) ? ' WHERE ' : " {$conj} ";
|
||||||
|
$str = $key . " {$in} (" . implode(',', $params) . ') ';
|
||||||
|
|
||||||
|
$this->state->appendMap($conjunction, $str, MapType::WHERE_IN);
|
||||||
|
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Executes the compiled query
|
||||||
|
*
|
||||||
|
* @param string $type
|
||||||
|
* @param string $table
|
||||||
|
* @param string $sql
|
||||||
|
* @param array|null $vals
|
||||||
|
* @param boolean $reset
|
||||||
|
* @return PDOStatement
|
||||||
|
*/
|
||||||
|
protected function _run(string $type, string $table, string $sql = NULL, array $vals = NULL, bool $reset = TRUE): PDOStatement
|
||||||
|
{
|
||||||
|
if ($sql === NULL)
|
||||||
|
{
|
||||||
|
$sql = $this->_compile($type, $table);
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($vals === NULL)
|
||||||
|
{
|
||||||
|
$vals = array_merge($this->state->getValues(), $this->state->getWhereValues());
|
||||||
|
}
|
||||||
|
|
||||||
|
$startTime = microtime(TRUE);
|
||||||
|
|
||||||
|
$res = empty($vals)
|
||||||
|
? $this->driver->query($sql)
|
||||||
|
: $this->driver->prepareExecute($sql, $vals);
|
||||||
|
|
||||||
|
$endTime = microtime(TRUE);
|
||||||
|
$totalTime = number_format($endTime - $startTime, 5);
|
||||||
|
|
||||||
|
// Add this query to the list of executed queries
|
||||||
|
$this->_appendQuery($vals, $sql, (int)$totalTime);
|
||||||
|
|
||||||
|
// Reset class state for next query
|
||||||
|
if ($reset)
|
||||||
|
{
|
||||||
|
$this->resetQuery();
|
||||||
|
}
|
||||||
|
|
||||||
|
return $res;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Convert the prepared statement into readable sql
|
||||||
|
*
|
||||||
|
* @param array $values
|
||||||
|
* @param string $sql
|
||||||
|
* @param int $totalTime
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
protected function _appendQuery(array $values, string $sql, int $totalTime): void
|
||||||
|
{
|
||||||
|
$evals = is_array($values) ? $values : [];
|
||||||
|
$esql = str_replace('?', '%s', $sql);
|
||||||
|
|
||||||
|
// Quote string values
|
||||||
|
foreach ($evals as &$v)
|
||||||
|
{
|
||||||
|
$v = ( ! is_numeric($v))
|
||||||
|
? htmlentities($this->driver->quote($v), ENT_NOQUOTES, 'utf-8')
|
||||||
|
: $v;
|
||||||
|
}
|
||||||
|
unset($v);
|
||||||
|
|
||||||
|
// Add the query onto the array of values to pass
|
||||||
|
// as arguments to sprintf
|
||||||
|
array_unshift($evals, $esql);
|
||||||
|
|
||||||
|
// Add the interpreted query to the list of executed queries
|
||||||
|
$this->queries[] = [
|
||||||
|
'time' => $totalTime,
|
||||||
|
'sql' => sprintf(...$evals)
|
||||||
|
];
|
||||||
|
|
||||||
|
$this->queries['total_time'] += $totalTime;
|
||||||
|
|
||||||
|
// Set the last query to get rowcounts properly
|
||||||
|
$this->driver->setLastQuery($sql);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Sub-method for generating sql strings
|
||||||
|
*
|
||||||
|
* @codeCoverageIgnore
|
||||||
|
* @param string $type
|
||||||
|
* @param string $table
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
protected function _compileType(string $type = QueryType::SELECT, string $table = ''): string
|
||||||
|
{
|
||||||
|
$setArrayKeys = $this->state->getSetArrayKeys();
|
||||||
|
switch ($type)
|
||||||
|
{
|
||||||
|
case QueryType::INSERT:
|
||||||
|
$paramCount = count($setArrayKeys);
|
||||||
|
$params = array_fill(0, $paramCount, '?');
|
||||||
|
$sql = "INSERT INTO {$table} ("
|
||||||
|
. implode(',', $setArrayKeys)
|
||||||
|
. ")\nVALUES (" . implode(',', $params) . ')';
|
||||||
|
break;
|
||||||
|
|
||||||
|
case QueryType::UPDATE:
|
||||||
|
$setString = $this->state->getSetString();
|
||||||
|
$sql = "UPDATE {$table}\nSET {$setString}";
|
||||||
|
break;
|
||||||
|
|
||||||
|
case QueryType::DELETE:
|
||||||
|
$sql = "DELETE FROM {$table}";
|
||||||
|
break;
|
||||||
|
|
||||||
|
case QueryType::SELECT:
|
||||||
|
default:
|
||||||
|
$fromString = $this->state->getFromString();
|
||||||
|
$selectString = $this->state->getSelectString();
|
||||||
|
|
||||||
|
$sql = "SELECT * \nFROM {$fromString}";
|
||||||
|
|
||||||
|
// Set the select string
|
||||||
|
if ( ! empty($selectString))
|
||||||
|
{
|
||||||
|
// Replace the star with the selected fields
|
||||||
|
$sql = str_replace('*', $selectString, $sql);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return $sql;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* String together the sql statements for sending to the db
|
||||||
|
*
|
||||||
|
* @param string $type
|
||||||
|
* @param string $table
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
protected function _compile(string $type = '', string $table = ''): string
|
||||||
|
{
|
||||||
|
// Get the base clause for the query
|
||||||
|
$sql = $this->_compileType($type, $this->driver->quoteTable($table));
|
||||||
|
|
||||||
|
$clauses = [
|
||||||
|
'queryMap',
|
||||||
|
'groupString',
|
||||||
|
'orderString',
|
||||||
|
'havingMap',
|
||||||
|
];
|
||||||
|
|
||||||
|
// Set each type of subclause
|
||||||
|
foreach ($clauses as $clause)
|
||||||
|
{
|
||||||
|
$func = 'get' . ucFirst($clause);
|
||||||
|
$param = $this->state->$func();
|
||||||
|
if (is_array($param))
|
||||||
|
{
|
||||||
|
foreach ($param as $q)
|
||||||
|
{
|
||||||
|
$sql .= $q['conjunction'] . $q['string'];
|
||||||
|
}
|
||||||
|
} else
|
||||||
|
{
|
||||||
|
$sql .= $param;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set the limit via the class variables
|
||||||
|
$limit = $this->state->getLimit();
|
||||||
|
if (is_numeric($limit))
|
||||||
|
{
|
||||||
|
$sql = $this->driver->getSql()->limit($sql, $limit, $this->state->getOffset());
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set the returning clause, if applicable
|
||||||
|
$sql = $this->_compileReturning($sql, $type);
|
||||||
|
|
||||||
|
// See if the query plan, rather than the
|
||||||
|
// query data should be returned
|
||||||
|
if ($this->explain === TRUE)
|
||||||
|
{
|
||||||
|
$sql = $this->driver->getSql()->explain($sql);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $sql;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Generate returning clause of query
|
||||||
|
*
|
||||||
|
* @param string $sql
|
||||||
|
* @param string $type
|
||||||
|
* @return string
|
||||||
|
*/
|
||||||
|
protected function _compileReturning(string $sql, string $type): string
|
||||||
|
{
|
||||||
|
if ($this->returning === FALSE)
|
||||||
|
{
|
||||||
|
return $sql;
|
||||||
|
}
|
||||||
|
|
||||||
|
$rawSelect = $this->state->getSelectString();
|
||||||
|
$selectString = ($rawSelect === '') ? '*' : $rawSelect;
|
||||||
|
$returningSQL = $this->driver->returning($sql, $selectString);
|
||||||
|
|
||||||
|
if ($returningSQL === $sql)
|
||||||
|
{
|
||||||
|
// If the driver doesn't support the returning clause, it returns the original query.
|
||||||
|
// Fake the same result with a transaction and a select query
|
||||||
|
if ( ! $this->inTransaction())
|
||||||
|
{
|
||||||
|
$this->beginTransaction();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Generate the appropriate select query for the returning clause fallback
|
||||||
|
switch ($type)
|
||||||
|
{
|
||||||
|
case QueryType::INSERT:
|
||||||
|
// @TODO figure out a good response for insert query
|
||||||
|
break;
|
||||||
|
|
||||||
|
case QueryType::UPDATE:
|
||||||
|
// @TODO figure out a good response for update query
|
||||||
|
break;
|
||||||
|
|
||||||
|
case QueryType::INSERT_BATCH:
|
||||||
|
case QueryType::UPDATE_BATCH:
|
||||||
|
// @TODO figure out a good response for batch queries
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
// On Delete queries, what would we return?
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $returningSQL;
|
||||||
|
}
|
||||||
|
}
|
@ -107,14 +107,6 @@ interface QueryBuilderInterface {
|
|||||||
*/
|
*/
|
||||||
public function selectSum(string $field, $as=FALSE): self;
|
public function selectSum(string $field, $as=FALSE): self;
|
||||||
|
|
||||||
/**
|
|
||||||
* Add a 'returning' clause to an insert,update, or delete query
|
|
||||||
*
|
|
||||||
* @param string $fields
|
|
||||||
* @return self
|
|
||||||
*/
|
|
||||||
public function returning(string $fields = '*'): self;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds the 'distinct' keyword to a query
|
* Adds the 'distinct' keyword to a query
|
||||||
*
|
*
|
||||||
@ -308,10 +300,10 @@ interface QueryBuilderInterface {
|
|||||||
* Set a limit on the current sql statement
|
* Set a limit on the current sql statement
|
||||||
*
|
*
|
||||||
* @param int $limit
|
* @param int $limit
|
||||||
* @param int|bool $offset
|
* @param int|null $offset
|
||||||
* @return self
|
* @return self
|
||||||
*/
|
*/
|
||||||
public function limit(int $limit, $offset=FALSE): self;
|
public function limit(int $limit, ?int $offset=NULL): self;
|
||||||
|
|
||||||
// --------------------------------------------------------------------------
|
// --------------------------------------------------------------------------
|
||||||
// ! Query Grouping Methods
|
// ! Query Grouping Methods
|
||||||
@ -364,22 +356,22 @@ interface QueryBuilderInterface {
|
|||||||
* execute current compiled query
|
* execute current compiled query
|
||||||
*
|
*
|
||||||
* @param string $table
|
* @param string $table
|
||||||
* @param int|bool $limit
|
* @param int|null $limit
|
||||||
* @param int|bool $offset
|
* @param int|null $offset
|
||||||
* @return PDOStatement
|
* @return PDOStatement
|
||||||
*/
|
*/
|
||||||
public function get(string $table='', $limit=FALSE, $offset=FALSE): PDOStatement;
|
public function get(string $table='', ?int $limit=NULL, ?int $offset=NULL): PDOStatement;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Convenience method for get() with a where clause
|
* Convenience method for get() with a where clause
|
||||||
*
|
*
|
||||||
* @param string $table
|
* @param string $table
|
||||||
* @param array $where
|
* @param array $where
|
||||||
* @param int|bool $limit
|
* @param int|null $limit
|
||||||
* @param int|bool $offset
|
* @param int|null $offset
|
||||||
* @return PDOStatement
|
* @return PDOStatement
|
||||||
*/
|
*/
|
||||||
public function getWhere(string $table, $where=[], $limit=FALSE, $offset=FALSE): PDOStatement;
|
public function getWhere(string $table, $where=[], ?int $limit=NULL, ?int $offset=NULL): PDOStatement;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Retrieve the number of rows in the selected table
|
* Retrieve the number of rows in the selected table
|
||||||
@ -413,9 +405,9 @@ interface QueryBuilderInterface {
|
|||||||
*
|
*
|
||||||
* @param string $table
|
* @param string $table
|
||||||
* @param array $data
|
* @param array $data
|
||||||
* @return PDOStatement
|
* @return PDOStatement | null
|
||||||
*/
|
*/
|
||||||
public function insertBatch(string $table, $data=[]): PDOStatement;
|
public function insertBatch(string $table, $data=[]): ?PDOStatement;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates an update clause, and executes it
|
* Creates an update clause, and executes it
|
||||||
|
@ -21,6 +21,8 @@ namespace Query;
|
|||||||
class QueryType {
|
class QueryType {
|
||||||
public const SELECT = 'select';
|
public const SELECT = 'select';
|
||||||
public const INSERT = 'insert';
|
public const INSERT = 'insert';
|
||||||
|
public const INSERT_BATCH = 'insert_batch';
|
||||||
public const UPDATE = 'update';
|
public const UPDATE = 'update';
|
||||||
|
public const UPDATE_BATCH = 'update_batch';
|
||||||
public const DELETE = 'delete';
|
public const DELETE = 'delete';
|
||||||
}
|
}
|
@ -15,6 +15,8 @@
|
|||||||
*/
|
*/
|
||||||
namespace Query;
|
namespace Query;
|
||||||
|
|
||||||
|
use function is_array;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Query builder state
|
* Query builder state
|
||||||
*
|
*
|
||||||
@ -28,14 +30,20 @@ namespace Query;
|
|||||||
* @method getGroupArray(): array
|
* @method getGroupArray(): array
|
||||||
* @method getValues(): array
|
* @method getValues(): array
|
||||||
* @method getWhereValues(): array
|
* @method getWhereValues(): array
|
||||||
* @method getLimit(): int
|
* @method getLimit(): int|null
|
||||||
* @method getOffset()
|
* @method getOffset()
|
||||||
* @method getQueryMap(): array
|
* @method getQueryMap(): array
|
||||||
* @method getHavingMap(): array
|
* @method getHavingMap(): array
|
||||||
*
|
*
|
||||||
* @method setSelectString(string): self
|
* @method setSelectString(string $selectString): self
|
||||||
* @method setFromString(string): self
|
* @method setFromString(string $fromString): self
|
||||||
* @method setSetString(string): self
|
* @method setSetString(string $setString): self
|
||||||
|
* @method setOrderString(string $orderString): self
|
||||||
|
* @method setGroupString(string $groupString): self
|
||||||
|
* @method setSetArrayKeys(array $arrayKeys): self
|
||||||
|
* @method setGroupArray(array $array): self
|
||||||
|
* @method setLimit(int $limit): self
|
||||||
|
* @method setOffset(?int $offset): self
|
||||||
*/
|
*/
|
||||||
class State {
|
class State {
|
||||||
// --------------------------------------------------------------------------
|
// --------------------------------------------------------------------------
|
||||||
@ -112,15 +120,15 @@ class State {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Value for limit string
|
* Value for limit string
|
||||||
* @var integer
|
* @var int
|
||||||
*/
|
*/
|
||||||
protected int $limit;
|
protected ?int $limit = NULL;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Value for offset in limit string
|
* Value for offset in limit string
|
||||||
* @var string|false
|
* @var int
|
||||||
*/
|
*/
|
||||||
protected $offset = FALSE;
|
protected ?int $offset = NULL;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Query component order mapping
|
* Query component order mapping
|
||||||
@ -177,26 +185,6 @@ class State {
|
|||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @param string $orderString
|
|
||||||
* @return State
|
|
||||||
*/
|
|
||||||
public function setOrderString(string $orderString): self
|
|
||||||
{
|
|
||||||
$this->orderString = $orderString;
|
|
||||||
return $this;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param string $groupString
|
|
||||||
* @return State
|
|
||||||
*/
|
|
||||||
public function setGroupString(string $groupString): self
|
|
||||||
{
|
|
||||||
$this->groupString = $groupString;
|
|
||||||
return $this;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param array $setArrayKeys
|
* @param array $setArrayKeys
|
||||||
* @return State
|
* @return State
|
||||||
@ -207,16 +195,6 @@ class State {
|
|||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @param array $setArrayKeys
|
|
||||||
* @return State
|
|
||||||
*/
|
|
||||||
public function setSetArrayKeys(array $setArrayKeys): self
|
|
||||||
{
|
|
||||||
$this->setArrayKeys = $setArrayKeys;
|
|
||||||
return $this;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param string $key
|
* @param string $key
|
||||||
* @param mixed $orderArray
|
* @param mixed $orderArray
|
||||||
@ -228,16 +206,6 @@ class State {
|
|||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @param array $groupArray
|
|
||||||
* @return State
|
|
||||||
*/
|
|
||||||
public function setGroupArray(array $groupArray): self
|
|
||||||
{
|
|
||||||
$this->groupArray = $groupArray;
|
|
||||||
return $this;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param string $groupArray
|
* @param string $groupArray
|
||||||
* @return State
|
* @return State
|
||||||
@ -264,7 +232,7 @@ class State {
|
|||||||
*/
|
*/
|
||||||
public function appendWhereValues($val): self
|
public function appendWhereValues($val): self
|
||||||
{
|
{
|
||||||
if (\is_array($val))
|
if (is_array($val))
|
||||||
{
|
{
|
||||||
foreach($val as $v)
|
foreach($val as $v)
|
||||||
{
|
{
|
||||||
@ -278,26 +246,6 @@ class State {
|
|||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @param int $limit
|
|
||||||
* @return State
|
|
||||||
*/
|
|
||||||
public function setLimit(int $limit): self
|
|
||||||
{
|
|
||||||
$this->limit = $limit;
|
|
||||||
return $this;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param string|false $offset
|
|
||||||
* @return State
|
|
||||||
*/
|
|
||||||
public function setOffset($offset): self
|
|
||||||
{
|
|
||||||
$this->offset = $offset;
|
|
||||||
return $this;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add an additional set of mapping pairs to a internal map
|
* Add an additional set of mapping pairs to a internal map
|
||||||
*
|
*
|
||||||
|
@ -15,10 +15,8 @@
|
|||||||
*/
|
*/
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
use Query\{
|
use Query\ConnectionManager;
|
||||||
ConnectionManager,
|
use Query\QueryBuilderInterface;
|
||||||
QueryBuilderInterface
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Global functions that don't really fit anywhere else
|
* Global functions that don't really fit anywhere else
|
||||||
@ -139,6 +137,5 @@ namespace {
|
|||||||
// Otherwise, return a new connection
|
// Otherwise, return a new connection
|
||||||
return $manager->connect($paramsObject);
|
return $manager->connect($paramsObject);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
// End of common.php
|
// End of common.php
|
||||||
|
Loading…
Reference in New Issue
Block a user