diff options
| author | s1n <[email protected]> | 2020-03-28 10:36:41 -0700 |
|---|---|---|
| committer | s1n <[email protected]> | 2020-03-28 10:36:41 -0700 |
| commit | 25b7d2aab61ae6421398d3abae5da6ffe590333d (patch) | |
| tree | 611985ec78bb2d94099c9fd5dd687f5c9cee6f3e /includes/vendor/aura/sql/src | |
| parent | Initial commit (diff) | |
| download | crack.cf-backup-master.tar.xz crack.cf-backup-master.zip | |
Diffstat (limited to 'includes/vendor/aura/sql/src')
19 files changed, 2974 insertions, 0 deletions
diff --git a/includes/vendor/aura/sql/src/ConnectionLocator.php b/includes/vendor/aura/sql/src/ConnectionLocator.php new file mode 100644 index 0000000..5afaf51 --- /dev/null +++ b/includes/vendor/aura/sql/src/ConnectionLocator.php @@ -0,0 +1,315 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +/** + * + * Manages PDO connection objects for default, read, and write connections. + * + * @package Aura.Sql + * + */ +class ConnectionLocator implements ConnectionLocatorInterface +{ + /** + * + * A registry of PDO connection entries. + * + * @var array + * + */ + protected $registry = array( + 'default' => null, + 'read' => array(), + 'write' => array(), + ); + + /** + * + * Whether or not registry entries have been converted to objects. + * + * @var array + * + */ + protected $converted = array( + 'default' => false, + 'read' => array(), + 'write' => array(), + ); + + /** + * + * Whether or not to turn on profiling when retrieving a connection. + * + * @var bool + * + */ + protected $profiling = false; + + /** + * + * Constructor. + * + * @param callable $default A callable to create a default connection. + * + * @param array $read An array of callables to create read connections. + * + * @param array $write An array of callables to create write connections. + * + */ + public function __construct( + $default = null, + array $read = array(), + array $write = array() + ) { + if ($default) { + $this->setDefault($default); + } + foreach ($read as $name => $callable) { + $this->setRead($name, $callable); + } + foreach ($write as $name => $callable) { + $this->setWrite($name, $callable); + } + } + + /** + * + * Sets the default connection registry entry. + * + * @param callable $callable The registry entry. + * + * @return null + * + */ + public function setDefault($callable) + { + $this->registry['default'] = $callable; + $this->converted['default'] = false; + } + + /** + * + * Returns the default connection object. + * + * @return ExtendedPdoInterface + * + */ + public function getDefault() + { + if (! $this->converted['default']) { + $callable = $this->registry['default']; + $this->registry['default'] = call_user_func($callable); + $this->converted['default'] = true; + } + + $connection = $this->registry['default']; + $this->setProfiler($connection); + return $connection; + } + + /** + * + * Sets a read connection registry entry by name. + * + * @param string $name The name of the registry entry. + * + * @param callable $callable The registry entry. + * + * @return null + * + */ + public function setRead($name, $callable) + { + $this->registry['read'][$name] = $callable; + $this->converted['read'][$name] = false; + } + + /** + * + * Returns a read connection by name; if no name is given, picks a + * random connection; if no read connections are present, returns the + * default connection. + * + * @param string $name The read connection name to return. + * + * @return ExtendedPdoInterface + * + */ + public function getRead($name = null) + { + return $this->getConnection('read', $name); + } + + /** + * + * Sets a write connection registry entry by name. + * + * @param string $name The name of the registry entry. + * + * @param callable $callable The registry entry. + * + * @return null + * + */ + public function setWrite($name, $callable) + { + $this->registry['write'][$name] = $callable; + $this->converted['write'][$name] = false; + } + + /** + * + * Returns a write connection by name; if no name is given, picks a + * random connection; if no write connections are present, returns the + * default connection. + * + * @param string $name The write connection name to return. + * + * @return ExtendedPdoInterface + * + */ + public function getWrite($name = null) + { + return $this->getConnection('write', $name); + } + + /** + * + * Returns a connection by name. + * + * @param string $type The connection type ('read' or 'write'). + * + * @param string $name The name of the connection. + * + * @return ExtendedPdoInterface + * + * @throws Exception\ConnectionNotFound + */ + protected function getConnection($type, $name) + { + if (! $this->registry[$type]) { + return $this->getDefault(); + } + + if (! $name) { + $name = array_rand($this->registry[$type]); + } + + if (! isset($this->registry[$type][$name])) { + throw new Exception\ConnectionNotFound("{$type}:{$name}"); + } + + if (! $this->converted[$type][$name]) { + $callable = $this->registry[$type][$name]; + $this->registry[$type][$name] = call_user_func($callable); + $this->converted[$type][$name] = true; + } + + $connection = $this->registry[$type][$name]; + $this->setProfiler($connection); + return $connection; + } + + /** + * + * Given a connection, enable or disable profiling on it. If a profiler has + * not been set into the connection, this will instantiate and set one. + * + * @param ExtendedPdo $connection The connection. + * + * @return null + * + */ + protected function setProfiler(ExtendedPdo $connection) + { + $profiler = $connection->getProfiler(); + + if (! $this->profiling && ! $profiler) { + return; + } + + if (! $profiler) { + $profiler = new Profiler(); + $connection->setProfiler($profiler); + } + + $profiler->setActive($this->profiling); + } + + /** + * + * Set profiling on all connections at retrieval time? + * + * @param bool $profiling True to enable, or false to disable, profiling on + * each connection as it is retrieved. + * + * @return null + * + */ + public function setProfiling($profiling = true) + { + $this->profiling = (bool) $profiling; + } + + /** + * + * Gets the profiles from all connections. + * + * @return array + * + */ + public function getProfiles() + { + $profiles = array(); + + if ($this->converted['default']) { + $connection = $this->registry['default']; + $this->addProfiles('default', $connection, $profiles); + } + + foreach (array('read', 'write') as $type) { + foreach ($this->registry[$type] as $name) { + if ($this->converted[$type][$name]) { + $connection = $this->registry[$type][$name]; + $this->addProfiles("{$type}:{$name}", $connection, $profiles); + } + } + } + + ksort($profiles); + return $profiles; + } + + /** + * + * Adds profiles from a connection, with a label for the connection name. + * + * @param string $label The connection label. + * + * @param ExtendedPdo $connection The connection. + * + * @param array &$profiles Add the connection profiles to this array, in + * place. + * + * @return null + */ + protected function addProfiles($label, ExtendedPdo $connection, &$profiles) + { + $profiler = $connection->getProfiler(); + if (! $profiler) { + return; + } + + foreach ($profiler->getProfiles() as $key => $profile) { + $profile = array('connection' => $label) + $profile; + $profiles[$key] = $profile; + } + } +} diff --git a/includes/vendor/aura/sql/src/ConnectionLocatorInterface.php b/includes/vendor/aura/sql/src/ConnectionLocatorInterface.php new file mode 100644 index 0000000..558a953 --- /dev/null +++ b/includes/vendor/aura/sql/src/ConnectionLocatorInterface.php @@ -0,0 +1,91 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +/** + * + * Locates PDO connections for default, read, and write databases. + * + * @package Aura.Sql + * + */ +interface ConnectionLocatorInterface +{ + /** + * + * Sets the default connection registry entry. + * + * @param callable $callable The registry entry. + * + * @return null + * + */ + public function setDefault($callable); + + /** + * + * Returns the default connection object. + * + * @return ExtendedPdoInterface + * + */ + public function getDefault(); + + /** + * + * Sets a read connection registry entry by name. + * + * @param string $name The name of the registry entry. + * + * @param callable $callable The registry entry. + * + * @return null + * + */ + public function setRead($name, $callable); + + /** + * + * Returns a read connection by name; if no name is given, picks a + * random connection; if no read connections are present, returns the + * default connection. + * + * @param string $name The read connection name to return. + * + * @return ExtendedPdoInterface + * + */ + public function getRead($name = null); + + /** + * + * Sets a write connection registry entry by name. + * + * @param string $name The name of the registry entry. + * + * @param callable $callable The registry entry. + * + * @return null + * + */ + public function setWrite($name, $callable); + + /** + * + * Returns a write connection by name; if no name is given, picks a + * random connection; if no write connections are present, returns the + * default connection. + * + * @param string $name The write connection name to return. + * + * @return ExtendedPdoInterface + * + */ + public function getWrite($name = null); +} diff --git a/includes/vendor/aura/sql/src/Exception.php b/includes/vendor/aura/sql/src/Exception.php new file mode 100644 index 0000000..4430df2 --- /dev/null +++ b/includes/vendor/aura/sql/src/Exception.php @@ -0,0 +1,20 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +/** + * + * Base Exception class for Aura Sql + * + * @package Aura.Sql + * + */ +class Exception extends \Exception +{ +} diff --git a/includes/vendor/aura/sql/src/Exception/CannotBindValue.php b/includes/vendor/aura/sql/src/Exception/CannotBindValue.php new file mode 100644 index 0000000..336ddd2 --- /dev/null +++ b/includes/vendor/aura/sql/src/Exception/CannotBindValue.php @@ -0,0 +1,23 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Exception; + +use Aura\Sql\Exception; + +/** + * + * Could not bind a value to a placeholder in a statement, generally because + * the value is an array, object, or resource. + * + * @package Aura.Sql + * + */ +class CannotBindValue extends Exception +{ +} diff --git a/includes/vendor/aura/sql/src/Exception/CannotDisconnect.php b/includes/vendor/aura/sql/src/Exception/CannotDisconnect.php new file mode 100644 index 0000000..3f1cf2d --- /dev/null +++ b/includes/vendor/aura/sql/src/Exception/CannotDisconnect.php @@ -0,0 +1,23 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Exception; + +use Aura\Sql\Exception; + +/** + * + * ExtendedPdo could not disconnect; e.g., because its PDO connection was + * created externally and then injected. + * + * @package Aura.Sql + * + */ +class CannotDisconnect extends Exception +{ +} diff --git a/includes/vendor/aura/sql/src/Exception/ConnectionNotFound.php b/includes/vendor/aura/sql/src/Exception/ConnectionNotFound.php new file mode 100644 index 0000000..b6a15a4 --- /dev/null +++ b/includes/vendor/aura/sql/src/Exception/ConnectionNotFound.php @@ -0,0 +1,22 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Exception; + +use Aura\Sql\Exception; + +/** + * + * Locator could not find a named connection. + * + * @package Aura.Sql + * + */ +class ConnectionNotFound extends Exception +{ +} diff --git a/includes/vendor/aura/sql/src/Exception/MissingParameter.php b/includes/vendor/aura/sql/src/Exception/MissingParameter.php new file mode 100644 index 0000000..2a16c9a --- /dev/null +++ b/includes/vendor/aura/sql/src/Exception/MissingParameter.php @@ -0,0 +1,22 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Exception; + +use Aura\Sql\Exception; + +/** + * + * Missing a parameter in the values bound to a statement + * + * @package Aura.Sql + * + */ +class MissingParameter extends Exception +{ +} diff --git a/includes/vendor/aura/sql/src/ExtendedPdo.php b/includes/vendor/aura/sql/src/ExtendedPdo.php new file mode 100644 index 0000000..d3668ac --- /dev/null +++ b/includes/vendor/aura/sql/src/ExtendedPdo.php @@ -0,0 +1,1138 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +use Aura\Sql\Exception; +use PDO; +use PDOStatement; + +/** + * + * This extended decorator for PDO provides lazy connection, array quoting, a + * new `perform()` method, and new `fetch*()` methods. + * + * @package Aura.Sql + * + */ +class ExtendedPdo extends PDO implements ExtendedPdoInterface +{ + /** + * + * The PDO connection itself. + * + * @var PDO + * + */ + protected $pdo; + + /** + * + * The attributes for a lazy connection. + * + * @var array + * + */ + protected $attributes = array( + self::ATTR_ERRMODE => self::ERRMODE_EXCEPTION, + ); + + /** + * + * Was the PDO connection injected at construction time? + * + * @var PDO + * + */ + protected $injected = false; + + /** + * + * The DSN for a lazy connection. + * + * @var string + * + */ + protected $dsn; + + /** + * + * PDO options for a lazy connection. + * + * @var array + * + */ + protected $options = array(); + + /** + * + * The password for a lazy connection. + * + * @var string + * + */ + protected $password; + + /** + * + * The current profile information. + * + * @var array + * + */ + protected $profile = array(); + + /** + * + * A query profiler. + * + * @var ProfilerInterface + * + */ + protected $profiler; + + /** + * + * The username for a lazy connection. + * + * @var string + * + */ + protected $username; + + /** + * + * A specialized statement preparer. + * + * @var Rebuilder + * + */ + protected $rebuilder; + + /** + * + * This constructor is pseudo-polymorphic. You may pass a normal set of PDO + * constructor parameters, and ExtendedPdo will use them for a lazy + * connection. Alternatively, if the `$dsn` parameter is an existing PDO + * instance, that instance will be decorated by ExtendedPdo; the remaining + * parameters will be ignored. + * + * @param PDO|string $dsn The data source name for a lazy PDO connection, + * or an existing instance of PDO. If the latter, the remaining params are + * ignored. + * + * @param string $username The username for a lazy connection. + * + * @param string $password The password for a lazy connection. + * + * @param array $options Driver-specific options for a lazy connection. + * + * @param array $attributes Attributes to set after a lazy connection. + * + * @see http://php.net/manual/en/pdo.construct.php + * + */ + public function __construct( + $dsn, + $username = null, + $password = null, + array $options = array(), + array $attributes = array() + ) { + if ($dsn instanceof PDO) { + $this->pdo = $dsn; + $this->injected = true; + } else { + $this->dsn = $dsn; + $this->username = $username; + $this->password = $password; + $this->options = $options; + $this->attributes = array_replace($this->attributes, $attributes); + } + } + + /** + * + * Begins a transaction and turns off autocommit mode. + * + * @return bool True on success, false on failure. + * + * @see http://php.net/manual/en/pdo.begintransaction.php + * + */ + public function beginTransaction() + { + $this->connect(); + $this->beginProfile(__FUNCTION__); + $result = $this->pdo->beginTransaction(); + $this->endProfile(); + return $result; + } + + /** + * + * Commits the existing transaction and restores autocommit mode. + * + * @return bool True on success, false on failure. + * + * @see http://php.net/manual/en/pdo.commit.php + * + */ + public function commit() + { + $this->connect(); + $this->beginProfile(__FUNCTION__); + $result = $this->pdo->commit(); + $this->endProfile(); + return $result; + } + + /** + * + * Connects to the database and sets PDO attributes. + * + * @return null + * + * @throws \PDOException if the connection fails. + * + */ + public function connect() + { + // don't connect twice + if ($this->pdo) { + return; + } + + // connect to the database + $this->beginProfile(__FUNCTION__); + $this->pdo = new PDO( + $this->dsn, + $this->username, + $this->password, + $this->options + ); + $this->endProfile(); + + // set attributes + foreach ($this->attributes as $attribute => $value) { + $this->setAttribute($attribute, $value); + } + } + + /** + * + * Explicitly disconnect by unsetting the PDO instance; does not prevent + * later reconnection, whether implicit or explicit. + * + * @return null + * + * @throws Exception\CannotDisconnect when the PDO instance was injected + * for decoration; manage the lifecycle of that PDO instance elsewhere. + * + */ + public function disconnect() + { + if ($this->injected) { + $message = "Cannot disconnect an injected PDO instance."; + throw new Exception\CannotDisconnect($message); + } + $this->pdo = null; + } + + /** + * + * Gets the most recent error code. + * + * @return mixed + * + */ + public function errorCode() + { + $this->connect(); + return $this->pdo->errorCode(); + } + + /** + * + * Gets the most recent error info. + * + * @return array + * + */ + public function errorInfo() + { + $this->connect(); + return $this->pdo->errorInfo(); + } + + /** + * + * Executes an SQL statement and returns the number of affected rows. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @return int The number of affected rows. + * + * @see http://php.net/manual/en/pdo.exec.php + * + */ + public function exec($statement) + { + $this->connect(); + $this->beginProfile(__FUNCTION__); + $affected_rows = $this->pdo->exec($statement); + $this->endProfile($statement); + return $affected_rows; + } + + /** + * + * Performs a statement and returns the number of affected rows. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return int + * + */ + public function fetchAffected($statement, array $values = array()) + { + $sth = $this->perform($statement, $values); + return $sth->rowCount(); + } + + /** + * + * Fetches a sequential array of rows from the database; the rows + * are returned as associative arrays. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + public function fetchAll( + $statement, + array $values = array(), + $callable = null + ) { + return $this->fetchAllWithCallable( + self::FETCH_ASSOC, + $statement, + $values, + $callable + ); + } + + /** + * + * Support for fetchAll() and fetchCol(). + * + * @param string $fetch_type A PDO FETCH_* constant. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + protected function fetchAllWithCallable( + $fetch_type, + $statement, + array $values = array(), + $callable = null + ) { + $sth = $this->perform($statement, $values); + if ($fetch_type == self::FETCH_COLUMN) { + $data = $sth->fetchAll($fetch_type, 0); + } else { + $data = $sth->fetchAll($fetch_type); + } + return $this->applyCallableToFetchAll($callable, $data); + } + + /** + * + * Applies a callable to a data set. + * + * @param callable|null $callable The callable to apply, if any. + * + * @param array $data The data set. + * + * @return array + * + */ + protected function applyCallableToFetchAll($callable, $data) + { + if ($callable) { + foreach ($data as $key => $row) { + $data[$key] = call_user_func($callable, $row); + } + } + return $data; + } + + /** + * + * Fetches an associative array of rows from the database; the rows + * are returned as associative arrays, and the array of rows is keyed + * on the first column of each row. + * + * N.b.: If multiple rows have the same first column value, the last + * row with that value will override earlier rows. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + public function fetchAssoc( + $statement, + array $values = array(), + $callable = null + ) { + $sth = $this->perform($statement, $values); + + if (! $callable) { + $callable = function ($row) { return $row; }; + } + + $data = array(); + while ($row = $sth->fetch(self::FETCH_ASSOC)) { + $key = current($row); + $data[$key] = call_user_func($callable, $row); + } + + return $data; + } + + /** + * + * Fetches the first column of rows as a sequential array. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + public function fetchCol( + $statement, + array $values = array(), + $callable = null + ) { + return $this->fetchAllWithCallable( + self::FETCH_COLUMN, + $statement, + $values, + $callable + ); + } + + /** + * + * Fetches one row from the database as an object where the column values + * are mapped to object properties. + * + * Warning: PDO "injects property-values BEFORE invoking the constructor - + * in other words, if your class initializes property-values to defaults + * in the constructor, you will be overwriting the values injected by + * fetchObject() !" + * <http://www.php.net/manual/en/pdostatement.fetchobject.php#111744> + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param string $class_name The name of the class to create. + * + * @param array $ctor_args Arguments to pass to the object constructor. + * + * @return object|false + * + */ + public function fetchObject( + $statement, + array $values = array(), + $class_name = 'StdClass', + array $ctor_args = array() + ) { + $sth = $this->perform($statement, $values); + + if ($ctor_args) { + return $sth->fetchObject($class_name, $ctor_args); + } + + return $sth->fetchObject($class_name); + } + + /** + * + * Fetches a sequential array of rows from the database; the rows + * are returned as objects where the column values are mapped to + * object properties. + * + * Warning: PDO "injects property-values BEFORE invoking the constructor - + * in other words, if your class initializes property-values to defaults + * in the constructor, you will be overwriting the values injected by + * fetchObject() !" + * <http://www.php.net/manual/en/pdostatement.fetchobject.php#111744> + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param string $class_name The name of the class to create from each + * row. + * + * @param array $ctor_args Arguments to pass to each object constructor. + * + * @return array + * + */ + public function fetchObjects( + $statement, + array $values = array(), + $class_name = 'StdClass', + array $ctor_args = array() + ) { + $sth = $this->perform($statement, $values); + + if ($ctor_args) { + return $sth->fetchAll(self::FETCH_CLASS, $class_name, $ctor_args); + } + + return $sth->fetchAll(self::FETCH_CLASS, $class_name); + } + + /** + * + * Fetches one row from the database as an associative array. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return array|false + * + */ + public function fetchOne($statement, array $values = array()) + { + $sth = $this->perform($statement, $values); + return $sth->fetch(self::FETCH_ASSOC); + } + + /** + * + * Fetches an associative array of rows as key-value pairs (first + * column is the key, second column is the value). + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + public function fetchPairs( + $statement, + array $values = array(), + $callable = null + ) { + $sth = $this->perform($statement, $values); + if ($callable) { + $data = array(); + while ($row = $sth->fetch(self::FETCH_NUM)) { + // apply the callback first so the key can be modified + $row = call_user_func($callable, $row); + // now retain the data + $data[$row[0]] = $row[1]; + } + } else { + $data = $sth->fetchAll(self::FETCH_KEY_PAIR); + } + return $data; + } + + /** + * + * Fetches the very first value (i.e., first column of the first row). + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return mixed + * + */ + public function fetchValue($statement, array $values = array()) + { + $sth = $this->perform($statement, $values); + return $sth->fetchColumn(0); + } + + /** + * + * Fetches multiple from the database as an associative array. + * The first column will be the index + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param int $style a fetch style defaults to PDO::FETCH_COLUMN for single + * values, use PDO::FETCH_NAMED when fetching a multiple columns + * + * @return array + * + */ + public function fetchGroup( + $statement, + array $values = array(), + $style = self::FETCH_COLUMN + ) { + $sth = $this->perform($statement, $values); + return $sth->fetchAll(self::FETCH_GROUP | $style); + } + + /** + * + * Gets a PDO attribute value. + * + * @param mixed $attribute The PDO::ATTR_* constant. + * + * @return mixed The value for the attribute. + * + */ + public function getAttribute($attribute) + { + $this->connect(); + return $this->pdo->getAttribute($attribute); + } + + /** + * + * Returns the DSN for a lazy connection; if the underlying PDO instance + * was injected at construction time, this will be null. + * + * @return string|null + * + */ + public function getDsn() + { + return $this->dsn; + } + + /** + * + * Returns the underlying PDO connection object. + * + * @return PDO + * + */ + public function getPdo() + { + $this->connect(); + return $this->pdo; + } + + /** + * + * Returns the profiler object. + * + * @return ProfilerInterface + * + */ + public function getProfiler() + { + return $this->profiler; + } + + /** + * + * Is a transaction currently active? + * + * @return bool + * + * @see http://php.net/manual/en/pdo.intransaction.php + * + */ + public function inTransaction() + { + $this->connect(); + $this->beginProfile(__FUNCTION__); + $result = $this->pdo->inTransaction(); + $this->endProfile(); + return $result; + } + + /** + * + * Is this instance connected to a database? + * + * @return bool + * + */ + public function isConnected() + { + return isset($this->pdo); + } + + /** + * + * Returns the last inserted autoincrement sequence value. + * + * @param string $name The name of the sequence to check; typically needed + * only for PostgreSQL, where it takes the form of `<table>_<column>_seq`. + * + * @return int + * + * @see http://php.net/manual/en/pdo.lastinsertid.php + * + */ + public function lastInsertId($name = null) + { + $this->connect(); + $this->beginProfile(__FUNCTION__); + $result = $this->pdo->lastInsertId($name); + $this->endProfile(); + return $result; + } + + /** + * + * Performs a query with bound values and returns the resulting + * PDOStatement; array values will be passed through `quote()` and their + * respective placeholders will be replaced in the query string. + * + * @param string $statement The SQL statement to perform. + * + * @param array $values Values to bind to the query + * + * @return PDOStatement + * + * @see quote() + * + */ + public function perform($statement, array $values = array()) + { + $sth = $this->prepareWithValues($statement, $values); + $this->beginProfile(__FUNCTION__); + $sth->execute(); + $this->endProfile($statement, $values); + return $sth; + } + + /** + * + * Prepares an SQL statement for execution. + * + * @param string $statement The SQL statement to prepare for execution. + * + * @param array $options Set these attributes on the returned + * PDOStatement. + * + * @return PDOStatement + * + * @see http://php.net/manual/en/pdo.prepare.php + * + */ + public function prepare($statement, $options = array()) + { + $this->connect(); + $this->beginProfile(__FUNCTION__); + $sth = $this->pdo->prepare($statement, $options); + $this->endProfile($statement, $options); + return $sth; + } + + /** + * + * Queries the database and returns a PDOStatement. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param int $fetch_mode The `PDO::FETCH_*` type to set on the returned + * `PDOStatement::setFetchMode()`. + * + * @param mixed $fetch_arg1 The first additional argument to send to + * `PDOStatement::setFetchMode()`. + * + * @param mixed $fetch_arg2 The second additional argument to send to + * `PDOStatement::setFetchMode()`. + * + * @return PDOStatement + * + * @see http://php.net/manual/en/pdo.query.php + * + */ + public function query($statement) + { + $this->connect(); + $this->beginProfile(__FUNCTION__); + + // remove empty constructor params list if it exists + $args = func_get_args(); + if (count($args) === 4 && $args[3] === array()) { + unset($args[3]); + } + + $sth = call_user_func_array(array($this->pdo, 'query'), $args); + + $this->endProfile($sth->queryString); + return $sth; + } + + /** + * + * Quotes a value for use in an SQL statement. + * + * This differs from `PDO::quote()` in that it will convert an array into + * a string of comma-separated quoted values. + * + * @param mixed $value The value to quote. + * + * @param int $parameter_type A data type hint for the database driver. + * + * @return mixed The quoted value. + * + * @see http://php.net/manual/en/pdo.quote.php + * + */ + public function quote($value, $parameter_type = self::PARAM_STR) + { + $this->connect(); + + // non-array quoting + if (! is_array($value)) { + return $this->pdo->quote($value, $parameter_type); + } + + // quote array values, not keys, then combine with commas + foreach ($value as $k => $v) { + $value[$k] = $this->pdo->quote($v, $parameter_type); + } + return implode(', ', $value); + } + + /** + * + * Rolls back the current transaction, and restores autocommit mode. + * + * @return bool True on success, false on failure. + * + * @see http://php.net/manual/en/pdo.rollback.php + * + */ + public function rollBack() + { + $this->connect(); + $this->beginProfile(__FUNCTION__); + $result = $this->pdo->rollBack(); + $this->endProfile(); + + return $result; + } + + /** + * + * Sets a PDO attribute value. + * + * @param mixed $attribute The PDO::ATTR_* constant. + * + * @param mixed $value The value for the attribute. + * + * @return bool True on success, false on failure. Note that if PDO has not + * not connected, all calls will be treated as successful. + * + */ + public function setAttribute($attribute, $value) + { + if ($this->pdo) { + return $this->pdo->setAttribute($attribute, $value); + } + + $this->attributes[$attribute] = $value; + return true; + } + + /** + * + * Sets the profiler object. + * + * @param ProfilerInterface $profiler + * + * @return null + * + */ + public function setProfiler(ProfilerInterface $profiler) + { + $this->profiler = $profiler; + } + + /** + * + * Begins a profile entry. + * + * @param string $function The function starting the profile entry. + * + * @return null + * + */ + protected function beginProfile($function) + { + // if there's no profiler, can't profile + if (! $this->profiler) { + return; + } + + // retain starting profile info + $this->profile['time'] = microtime(true); + $this->profile['function'] = $function; + } + + /** + * + * Ends and records a profile entry. + * + * @param string $statement The statement being profiled, if any. + * + * @param array $values The values bound to the statement, if any. + * + * @return null + * + */ + protected function endProfile($statement = null, array $values = array()) + { + // is there a profiler in place? + if ($this->profiler) { + // add an entry to the profiler + $this->profiler->addProfile( + microtime(true) - $this->profile['time'], + $this->profile['function'], + $statement, + $values + ); + } + + // clear the starting profile info + $this->profile = array(); + } + + /** + * + * Prepares an SQL statement with bound values. + * + * This method only binds values that have placeholders in the + * statement, thereby avoiding errors from PDO regarding too many bound + * values. It also binds all sequential (question-mark) placeholders. + * + * If a placeholder value is an array, the array is converted to a string + * of comma-separated quoted values; e.g., for an `IN (...)` condition. + * The quoted string is replaced directly into the statement instead of + * using `PDOStatement::bindValue()` proper. + * + * @param string $statement The SQL statement to prepare for execution. + * + * @param array $values The values to bind to the statement, if any. + * + * @return PDOStatement + * + * @see http://php.net/manual/en/pdo.prepare.php + * + */ + public function prepareWithValues($statement, array $values = array()) + { + // if there are no values to bind ... + if (! $values) { + // ... use the normal preparation + return $this->prepare($statement); + } + + // rebuild the statement and values + $rebuilder = new Rebuilder($this); + list($statement, $values) = $rebuilder->__invoke($statement, $values); + + // prepare the statement + $sth = $this->prepare($statement); + + // for the placeholders we found, bind the corresponding data values + foreach ($values as $key => $val) { + $this->bindValue($sth, $key, $val); + } + + // done + return $sth; + } + + /** + * + * Yields rows from the database. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return Iterator\AllIterator + * + */ + public function yieldAll($statement, array $values = array()) + { + $sth = $this->perform($statement, $values); + return new Iterator\AllIterator($sth); + } + + /** + * + * Yields rows from the database keyed on the first column of each row. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return Iterator\AssocIterator + * + */ + public function yieldAssoc($statement, array $values = array()) + { + $sth = $this->perform($statement, $values); + return new Iterator\AssocIterator($sth); + } + + /** + * + * Yields the first column of each row. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return Iterator\ColIterator + * + */ + public function yieldCol($statement, array $values = array()) + { + $sth = $this->perform($statement, $values); + return new Iterator\ColIterator($sth); + } + + /** + * + * Yields objects where the column values are mapped to object properties. + * + * Warning: PDO "injects property-values BEFORE invoking the constructor - + * in other words, if your class initializes property-values to defaults + * in the constructor, you will be overwriting the values injected by + * fetchObject() !" + * <http://www.php.net/manual/en/pdostatement.fetchobject.php#111744> + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param string $class_name The name of the class to create from each + * row. + * + * @param array $ctor_args Arguments to pass to each object constructor. + * + * @return Iterator\ObjectsIterator + * + */ + public function yieldObjects( + $statement, + array $values = array(), + $class_name = 'stdClass', + array $ctor_args = array() + ) { + $sth = $this->perform($statement, $values); + return new Iterator\ObjectsIterator($sth, $class_name, $ctor_args); + } + + /** + * + * Yields key-value pairs (first column is the key, second column is the + * value). + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return Iterator\PairsIterator + * + */ + public function yieldPairs($statement, array $values = array()) + { + $sth = $this->perform($statement, $values); + return new Iterator\PairsIterator($sth); + } + + /** + * + * Bind a value using the proper PDO::PARAM_* type. + * + * @param PDOStatement $sth The statement to bind to. + * + * @param mixed $key The placeholder key. + * + * @param mixed $val The value to bind to the statement. + * + * @return null + * + * @throws Exception\CannotBindValue when the value to be bound is not + * bindable (e.g., array, object, or resource). + * + */ + protected function bindValue(PDOStatement $sth, $key, $val) + { + if (is_int($val)) { + return $sth->bindValue($key, $val, self::PARAM_INT); + } + + if (is_bool($val)) { + // bind booleans as string '1' or string '0'. + // cf. https://bugs.php.net/bug.php?id=49255 + $val = $val ? '1' : '0'; + return $sth->bindValue($key, $val, self::PARAM_BOOL); + } + + if (is_null($val)) { + return $sth->bindValue($key, $val, self::PARAM_NULL); + } + + if (! is_scalar($val)) { + $type = gettype($val); + throw new Exception\CannotBindValue( + "Cannot bind value of type '{$type}' to placeholder '{$key}'" + ); + } + + $sth->bindValue($key, $val); + } +} diff --git a/includes/vendor/aura/sql/src/ExtendedPdoInterface.php b/includes/vendor/aura/sql/src/ExtendedPdoInterface.php new file mode 100644 index 0000000..77e49b1 --- /dev/null +++ b/includes/vendor/aura/sql/src/ExtendedPdoInterface.php @@ -0,0 +1,267 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +/** + * + * An interface to the Aura.Sql extended PDO object. + * + * @package Aura.Sql + * + * @method Iterator\AllIterator yieldAll(string $statment, array $values = array()) Yields rows from the database keyed on the first column of each row. + * @method Iterator\AssocIterator yieldAssoc(string $statment, array $values = array()) Yields rows from the database keyed on the first column of each row. + * @method Iterator\ColIterator yieldCol(string $statment, array $values = array()) Yields the first column of each row. + * @method Iterator\ObjectsIterator yieldObjects(string $statment, array $values = array(), $class_name = 'stdClass', array $ctor_args = array()) Yields objects where the column values are mapped to object properties. + * @method Iterator\PairsIterator yieldPairs(string $statment, array $values = array()) Yields key-value pairs (first column is the key, second column is the value). + */ +interface ExtendedPdoInterface extends PdoInterface +{ + /** + * + * Connects to the database and sets PDO attributes. + * + * @return null + * + * @throws \PDOException if the connection fails. + * + */ + public function connect(); + + /** + * + * Performs a statement and returns the number of affected rows. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return array + * + */ + public function fetchAffected($statement, array $values = array()); + + /** + * + * Fetches a sequential array of rows from the database; the rows + * are represented as associative arrays. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + public function fetchAll($statement, array $values = array(), $callable = null); + + /** + * + * Fetches an associative array of rows from the database; the rows + * are represented as associative arrays. The array of rows is keyed + * on the first column of each row. + * + * N.b.: if multiple rows have the same first column value, the last + * row with that value will override earlier rows. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + public function fetchAssoc($statement, array $values = array(), $callable = null); + + /** + * + * Fetches the first column of rows as a sequential array. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + public function fetchCol($statement, array $values = array(), $callable = null); + + /** + * + * Fetches one row from the database as an object, mapping column values + * to object properties. + * + * Warning: PDO "injects property-values BEFORE invoking the constructor - + * in other words, if your class initializes property-values to defaults + * in the constructor, you will be overwriting the values injected by + * fetchObject() !" + * <http://www.php.net/manual/en/pdostatement.fetchobject.php#111744> + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param string $class_name The name of the class to create. + * + * @param array $ctor_args Arguments to pass to the object constructor. + * + * @return object|false + * + */ + public function fetchObject( + $statement, + array $values = array(), + $class_name = 'StdClass', + array $ctor_args = array() + ); + + /** + * + * Fetches a sequential array of rows from the database; the rows + * are represented as objects, where the column values are mapped to + * object properties. + * + * Warning: PDO "injects property-values BEFORE invoking the constructor - + * in other words, if your class initializes property-values to defaults + * in the constructor, you will be overwriting the values injected by + * fetchObject() !" + * <http://www.php.net/manual/en/pdostatement.fetchobject.php#111744> + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param string $class_name The name of the class to create from each + * row. + * + * @param array $ctor_args Arguments to pass to each object constructor. + * + * @return array + * + */ + public function fetchObjects( + $statement, + array $values = array(), + $class_name = 'StdClass', + array $ctor_args = array() + ); + + /** + * + * Fetches one row from the database as an associative array. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return array|false + * + */ + public function fetchOne($statement, array $values = array()); + + /** + * + * Fetches an associative array of rows as key-value pairs (first + * column is the key, second column is the value). + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @param callable $callable A callable to be applied to each of the rows + * to be returned. + * + * @return array + * + */ + public function fetchPairs($statement, array $values = array(), $callable = null); + + /** + * + * Fetches the very first value (i.e., first column of the first row). + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return mixed + * + */ + public function fetchValue($statement, array $values = array()); + + /** + * + * Returns the DSN for a lazy connection; if the underlying PDO instance + * was injected at construction time, this will be null. + * + * @return string|null + * + */ + public function getDsn(); + + /** + * + * Returns the underlying PDO connection object. + * + * @return PDO or Null if connection was manually disconnected + * + */ + public function getPdo(); + + /** + * + * Returns the profiler object. + * + * @return ProfilerInterface + * + */ + public function getProfiler(); + + /** + * + * Is the instance connected to a database? + * + * @return bool + * + */ + public function isConnected(); + + /** + * + * Performs a query after preparing the statement with bound values, then + * returns the result as a PDOStatement. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param array $values Values to bind to the query. + * + * @return \PDOStatement + * + */ + public function perform($statement, array $values = array()); + + /** + * + * Sets the profiler object. + * + * @param ProfilerInterface $profiler + * + * @return null + * + */ + public function setProfiler(ProfilerInterface $profiler); +} diff --git a/includes/vendor/aura/sql/src/Iterator/AbstractIterator.php b/includes/vendor/aura/sql/src/Iterator/AbstractIterator.php new file mode 100644 index 0000000..895fd4e --- /dev/null +++ b/includes/vendor/aura/sql/src/Iterator/AbstractIterator.php @@ -0,0 +1,114 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Iterator; + +use Iterator; +use PDOStatement; + +/** + * + * A base class for iterators. + * + * @package Aura.Sql + * + */ +abstract class AbstractIterator implements Iterator +{ + /** + * + * PDO statement. + * + * @var PDOStatement + * + */ + protected $statement; + + /** + * + * Current row value. + * + * @var mixed + * + */ + protected $row; + + /** + * + * Current key. + * + * @var mixed + * + */ + protected $key = -1; + + /** + * + * Frees memory when object is destroyed. + * + */ + public function __destruct() + { + $this->statement->closeCursor(); + unset($this->statement); + } + + /** + * + * Moves row set pointer to first element. + * + */ + public function rewind() + { + $this->key = -1; + $this->next(); + } + + /** + * + * Returns value at current position. + * + * @return mixed + * + */ + public function current() + { + return $this->row; + } + + /** + * + * Returns key at current position. + * + * @return mixed + * + */ + public function key() + { + return $this->key; + } + + /** + * + * Fetches next row from statement. + * + */ + abstract public function next(); + + /** + * + * Detects if iterator state is valid. + * + * @return bool + * + */ + public function valid() + { + return $this->row !== false; + } +} diff --git a/includes/vendor/aura/sql/src/Iterator/AllIterator.php b/includes/vendor/aura/sql/src/Iterator/AllIterator.php new file mode 100644 index 0000000..9d56a24 --- /dev/null +++ b/includes/vendor/aura/sql/src/Iterator/AllIterator.php @@ -0,0 +1,46 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Iterator; + +use PDO; +use PDOStatement; + +/** + * + * The iterator equivalent of `fetchAll()`. + * + * @package Aura.Sql + * + */ +class AllIterator extends AbstractIterator +{ + /** + * + * Constructor. + * + * @param PDOStatement $statement PDO statement. + * + */ + public function __construct(PDOStatement $statement) + { + $this->statement = $statement; + $this->statement->setFetchMode(PDO::FETCH_ASSOC); + } + + /** + * + * Fetches next row from statement. + * + */ + public function next() + { + $this->row = $this->statement->fetch(); + $this->key ++; + } +} diff --git a/includes/vendor/aura/sql/src/Iterator/AssocIterator.php b/includes/vendor/aura/sql/src/Iterator/AssocIterator.php new file mode 100644 index 0000000..ea77a7a --- /dev/null +++ b/includes/vendor/aura/sql/src/Iterator/AssocIterator.php @@ -0,0 +1,49 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Iterator; + +use PDO; +use PDOStatement; + +/** + * + * The iterator equivalent of `fetchAssoc()`. + * + * @package Aura.Sql + * + */ +class AssocIterator extends AbstractIterator +{ + /** + * + * Constructor. + * + * @param PDOStatement $statement PDO statement. + * + */ + public function __construct(PDOStatement $statement) + { + $this->statement = $statement; + $this->statement->setFetchMode(PDO::FETCH_ASSOC); + } + + /** + * + * Fetches next row from statement. + * + */ + public function next() + { + $this->row = $this->statement->fetch(); + $this->key = false; + if ($this->row !== false) { + $this->key = current($this->row); + } + } +} diff --git a/includes/vendor/aura/sql/src/Iterator/ColIterator.php b/includes/vendor/aura/sql/src/Iterator/ColIterator.php new file mode 100644 index 0000000..7be66e8 --- /dev/null +++ b/includes/vendor/aura/sql/src/Iterator/ColIterator.php @@ -0,0 +1,49 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Iterator; + +use PDO; +use PDOStatement; + +/** + * + * The iterator equivalent of `fetchCol()`. + * + * @package Aura.Sql + * + */ +class ColIterator extends AbstractIterator +{ + /** + * + * Constructor. + * + * @param PDOStatement $statement PDO statement. + * + */ + public function __construct(PDOStatement $statement) + { + $this->statement = $statement; + $this->statement->setFetchMode(PDO::FETCH_NUM); + } + + /** + * + * Fetches next row from statement. + * + */ + public function next() + { + $this->row = $this->statement->fetch(); + if ($this->row !== false) { + $this->row = $this->row[0]; + } + $this->key ++; + } +} diff --git a/includes/vendor/aura/sql/src/Iterator/ObjectsIterator.php b/includes/vendor/aura/sql/src/Iterator/ObjectsIterator.php new file mode 100644 index 0000000..bbd08fc --- /dev/null +++ b/includes/vendor/aura/sql/src/Iterator/ObjectsIterator.php @@ -0,0 +1,60 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Iterator; + +use PDO; +use PDOStatement; + +/** + * + * The iterator equivalent of `fetchObjects()`. + * + * @package Aura.Sql + * + */ +class ObjectsIterator extends AbstractIterator +{ + /** + * + * Constructor. + * + * @param PDOStatement $statement PDO statement. + * + * @param string $class_name The name of the class to create. + * + * @param array $ctor_args Arguments to pass to the object constructor. + * + */ + public function __construct( + PDOStatement $statement, + $class_name = 'StdClass', + array $ctor_args = array() + ) { + $this->statement = $statement; + $this->statement->setFetchMode(PDO::FETCH_CLASS, $class_name); + if ($ctor_args) { + $this->statement->setFetchMode( + PDO::FETCH_CLASS, + $class_name, + $ctor_args + ); + } + } + + /** + * + * Fetches next row from statement. + * + */ + public function next() + { + $this->row = $this->statement->fetch(); + $this->key ++; + } +} diff --git a/includes/vendor/aura/sql/src/Iterator/PairsIterator.php b/includes/vendor/aura/sql/src/Iterator/PairsIterator.php new file mode 100644 index 0000000..20c1a13 --- /dev/null +++ b/includes/vendor/aura/sql/src/Iterator/PairsIterator.php @@ -0,0 +1,50 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql\Iterator; + +use PDO; +use PDOStatement; + +/** + * + * The iterator equivalent of `fetchPairs()`. + * + * @package Aura.Sql + * + */ +class PairsIterator extends AbstractIterator +{ + /** + * + * Constructor. + * + * @param PDOStatement $statement PDO statement. + * + */ + public function __construct(PDOStatement $statement) + { + $this->statement = $statement; + $this->statement->setFetchMode(PDO::FETCH_NUM); + } + + /** + * + * Fetches next row from statement. + * + */ + public function next() + { + $this->key = false; + $this->row = $this->statement->fetch(); + if ($this->row !== false) { + $this->key = $this->row[0]; + $this->row = $this->row[1]; + } + } +} diff --git a/includes/vendor/aura/sql/src/PdoInterface.php b/includes/vendor/aura/sql/src/PdoInterface.php new file mode 100644 index 0000000..5987ee4 --- /dev/null +++ b/includes/vendor/aura/sql/src/PdoInterface.php @@ -0,0 +1,196 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +use PDO; + +/** + * + * An interface to the native PDO object. + * + * @package Aura.Sql + * + */ +interface PdoInterface +{ + /** + * + * Begins a transaction and turns off autocommit mode. + * + * @return bool True on success, false on failure. + * + * @see http://php.net/manual/en/pdo.begintransaction.php + * + */ + public function beginTransaction(); + + /** + * + * Commits the existing transaction and restores autocommit mode. + * + * @return bool True on success, false on failure. + * + * @see http://php.net/manual/en/pdo.commit.php + * + */ + public function commit(); + + /** + * + * Gets the most recent error code. + * + * @return mixed + * + */ + public function errorCode(); + + /** + * + * Gets the most recent error info. + * + * @return array + * + */ + public function errorInfo(); + + /** + * + * Executes an SQL statement and returns the number of affected rows. + * + * @param string $statement The SQL statement to execute. + * + * @return int The number of rows affected. + * + * @see http://php.net/manual/en/pdo.exec.php + * + */ + public function exec($statement); + + /** + * + * Gets a PDO attribute value. + * + * @param mixed $attribute The PDO::ATTR_* constant. + * + * @return mixed The value for the attribute. + * + */ + public function getAttribute($attribute); + + /** + * + * Is a transaction currently active? + * + * @return bool + * + * @see http://php.net/manual/en/pdo.intransaction.php + * + */ + public function inTransaction(); + + /** + * + * Returns the last inserted autoincrement sequence value. + * + * @param string $name The name of the sequence to check; typically needed + * only for PostgreSQL, where it takes the form of `<table>_<column>_seq`. + * + * @return int + * + * @see http://php.net/manual/en/pdo.lastinsertid.php + * + */ + public function lastInsertId($name = null); + + /** + * + * Prepares an SQL statement for execution. + * + * @param string $statement The SQL statement to prepare for execution. + * + * @param array $options Set these attributes on the returned + * PDOStatement. + * + * @return \PDOStatement + * + * @see http://php.net/manual/en/pdo.prepare.php + * + */ + public function prepare($statement, $options = null); + + /** + * + * Queries the database and returns a PDOStatement. + * + * @param string $statement The SQL statement to prepare and execute. + * + * @param int $fetch_mode The `PDO::FETCH_*` type to set on the returned + * `PDOStatement::setFetchMode()`. + * + * @param mixed $fetch_arg1 The first additional argument to send to + * `PDOStatement::setFetchMode()`. + * + * @param mixed $fetch_arg2 The second additional argument to send to + * `PDOStatement::setFetchMode()`. + * + * @return \PDOStatement + * + * @see http://php.net/manual/en/pdo.query.php + * + */ + public function query($statement); + + /** + * + * Quotes a value for use in an SQL statement. + * + * @param mixed $value The value to quote. + * + * @param int $parameter_type A data type hint for the database driver. + * + * @return mixed The quoted value. + * + * @see http://php.net/manual/en/pdo.quote.php + * + */ + public function quote($value, $parameter_type = PDO::PARAM_STR); + + /** + * + * Rolls back the current transaction and restores autocommit mode. + * + * @return bool True on success, false on failure. + * + * @see http://php.net/manual/en/pdo.rollback.php + * + */ + public function rollBack(); + + /** + * + * Sets a PDO attribute value. + * + * @param mixed $attribute The PDO::ATTR_* constant. + * + * @param mixed $value The value for the attribute. + * + * @return bool + * + */ + public function setAttribute($attribute, $value); + + /** + * + * Returns all currently available PDO drivers. + * + * @return array + * + */ + public static function getAvailableDrivers(); +} diff --git a/includes/vendor/aura/sql/src/Profiler.php b/includes/vendor/aura/sql/src/Profiler.php new file mode 100644 index 0000000..93a1c9e --- /dev/null +++ b/includes/vendor/aura/sql/src/Profiler.php @@ -0,0 +1,129 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +/** + * + * Retains query profiles. + * + * @package Aura.Sql + * + */ +class Profiler implements ProfilerInterface +{ + /** + * + * Is the profiler active? + * + * @var bool + * + */ + protected $active = false; + + /** + * + * Retained profiles. + * + * @var array + * + */ + protected $profiles = array(); + + protected static $count = 0; + + /** + * + * Turns the profiler on and off. + * + * @param bool $active True to turn on, false to turn off. + * + * @return null + * + */ + public function setActive($active) + { + $this->active = (bool) $active; + } + + /** + * + * Is the profiler active? + * + * @return bool + * + */ + public function isActive() + { + return (bool) $this->active; + } + + /** + * + * Adds a profile entry. + * + * @param float $duration The query duration. + * + * @param string $function The PDO method that made the entry. + * + * @param string $statement The SQL query statement. + * + * @param array $bind_values The values bound to the statement. + * + * @return null + * + */ + public function addProfile( + $duration, + $function, + $statement, + array $bind_values = array() + ) { + if (! $this->isActive()) { + return; + } + + $e = new \Exception; + + // this allows for multiple profilers getting inter-sorted later + $k = self::$count ++; + + $this->profiles[$k] = array( + 'duration' => $duration, + 'function' => $function, + 'statement' => $statement, + 'bind_values' => $bind_values, + 'trace' => $e->getTraceAsString(), + ); + } + + /** + * + * Returns all the profile entries. + * + * @return array + * + */ + public function getProfiles() + { + return $this->profiles; + } + + /** + * + * Reset all the profiles + * + * @return null + * + */ + public function resetProfiles() + { + $this->profiles = array(); + self::$count = 0; + } +} diff --git a/includes/vendor/aura/sql/src/ProfilerInterface.php b/includes/vendor/aura/sql/src/ProfilerInterface.php new file mode 100644 index 0000000..f3ae0d8 --- /dev/null +++ b/includes/vendor/aura/sql/src/ProfilerInterface.php @@ -0,0 +1,80 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +/** + * + * Interface for query profilers. + * + * @package Aura.Sql + * + */ +interface ProfilerInterface +{ + /** + * + * Turns the profiler on and off. + * + * @param bool $active True to turn on, false to turn off. + * + * @return null + * + */ + public function setActive($active); + + /** + * + * Is the profiler active? + * + * @return bool + * + */ + public function isActive(); + + /** + * + * Adds a profile entry. + * + * @param float $duration The query duration. + * + * @param string $function The PDO method that made the entry. + * + * @param string $statement The SQL query statement. + * + * @param array $bind_values The values bound to the statement. + * + * @return null + * + */ + public function addProfile( + $duration, + $function, + $statement, + array $bind_values + ); + + /** + * + * Returns all the profiles. + * + * @return array + * + */ + public function getProfiles(); + + + /** + * + * Reset all the profiles + * + * @return null + * + */ + public function resetProfiles(); +} diff --git a/includes/vendor/aura/sql/src/Rebuilder.php b/includes/vendor/aura/sql/src/Rebuilder.php new file mode 100644 index 0000000..997beff --- /dev/null +++ b/includes/vendor/aura/sql/src/Rebuilder.php @@ -0,0 +1,280 @@ +<?php +/** + * + * This file is part of Aura for PHP. + * + * @license http://opensource.org/licenses/bsd-license.php BSD + * + */ +namespace Aura\Sql; + +use Aura\Sql\Exception\MissingParameter; + +/** + * + * This support class for ExtendedPdo rebuilds an SQL statement for automatic + * binding of values. + * + * @package Aura.Sql + * + */ +class Rebuilder +{ + /** + * + * The calling ExtendedPdo object. + * + * @var ExtendedPdo + * + */ + protected $xpdo; + + /** + * + * How many numbered placeholders in the original statement. + * + * @var int + * + */ + protected $num = 0; + + /** + * + * How many numbered placeholders to actually be bound; this may + * differ from 'num' in that some numbered placeholders may get + * replaced with quoted CSV strings + * + * @var int + * + */ + protected $count = 0; + + /** + * + * The initial values to be bound. + * + * @var array + * + */ + protected $values = array(); + + /** + * + * Named and numbered placeholders to bind at the end. + * + * @var array + * + */ + protected $final_values = array(); + + /** + * + * Constructor. + * + * @param ExtendedPdo $xpdo The calling ExtendedPdo object. + * + */ + public function __construct(ExtendedPdo $xpdo) + { + $this->xpdo = $xpdo; + } + + /** + * + * Rebuilds a statement with array values replaced into placeholders. + * + * @param string $statement The statement to rebuild. + * + * @param array $values The values to bind and/or replace into a statement. + * + * @return array An array where element 0 is the rebuilt statement and + * element 1 is the rebuilt array of values. + * + */ + public function __invoke($statement, $values) + { + // match standard PDO execute() behavior of zero-indexed arrays + if (array_key_exists(0, $values)) { + array_unshift($values, null); + } + + $this->values = $values; + $statement = $this->rebuildStatement($statement); + return array($statement, $this->final_values); + } + + /** + * + * Given a statement, rebuilds it with array values embedded. + * + * @param string $statement The SQL statement. + * + * @return string The rebuilt statement. + * + */ + protected function rebuildStatement($statement) + { + // find all parts not inside quotes or backslashed-quotes + $apos = "'"; + $quot = '"'; + $parts = preg_split( + "/(($apos+|$quot+|\\$apos+|\\$quot+).*?)\\2/m", + $statement, + -1, + PREG_SPLIT_DELIM_CAPTURE + ); + return $this->rebuildParts($parts); + } + + /** + * + * Given an array of statement parts, rebuilds each part. + * + * @param array $parts The statement parts. + * + * @return string The rebuilt statement. + * + */ + protected function rebuildParts($parts) + { + // loop through the non-quoted parts (0, 3, 6, 9, etc.) + $k = count($parts); + for ($i = 0; $i <= $k; $i += 3) { + $parts[$i] = $this->rebuildPart($parts[$i]); + } + return implode('', $parts); + } + + /** + * + * Rebuilds a single statement part. + * + * @param string $part The statement part. + * + * @return string The rebuilt statement. + * + */ + protected function rebuildPart($part) + { + // split into subparts by ":name" and "?" + $subs = preg_split( + "/(:[a-zA-Z_][a-zA-Z0-9_]*)|(\?)/m", + $part, + -1, + PREG_SPLIT_DELIM_CAPTURE + ); + + // check subparts to convert bound arrays to quoted CSV strings + $subs = $this->prepareValuePlaceholders($subs); + + // reassemble + return implode('', $subs); + } + + /** + * + * Prepares the sub-parts of a query with placeholders. + * + * @param array $subs The query subparts. + * + * @return array The prepared subparts. + * + */ + protected function prepareValuePlaceholders(array $subs) + { + foreach ($subs as $i => $sub) { + + // is the subpart a ?-mark? + if ($sub == '?') { + // prepare as numbered placeholder + $subs[$i] = $this->prepareNumberedPlaceholder($sub); + } + + // is the subpart only a colon? + if ($sub == ':') { + // ignore it + continue; + } + + // does the subpart begin with a colon? + $char = substr($sub, 0, 1); + if ($char != ':') { + // no, so cannot be named placeholder + continue; + } + + // does previous subpart (if there is one) end in a colon? + if ($i > 0 && substr($subs[$i - 1], -1) == ':') { + // prev ended in ':', and current begins with ':', making it a + // double-colon, so ignore it + continue; + } + + // begins with colon, previous did not end with colon, so prepare + // as a named placeholder + $subs[$i] = $this->prepareNamedPlaceholder($sub); + } + + return $subs; + } + + /** + * + * Bind or quote a numbered placeholder in a query subpart. + * + * @param string $sub The query subpart. + * + * @return string The prepared query subpart. + * + * @throws MissingParameter + */ + protected function prepareNumberedPlaceholder($sub) + { + // what numbered placeholder is this in the original statement? + $this->num ++; + + // is the corresponding data element an array? + $bind_array = isset($this->values[$this->num]) + && is_array($this->values[$this->num]); + if ($bind_array) { + // PDO won't bind an array; quote and replace directly + $sub = $this->xpdo->quote($this->values[$this->num]); + } else { + // increase the count of numbered placeholders to be bound + $this->count ++; + if (array_key_exists($this->num, $this->values) === false) { + throw new MissingParameter('Parameter ' . $this->num . ' is missing from the bound values'); + } + $this->final_values[$this->count] = $this->values[$this->num]; + } + + return $sub; + } + + /** + * + * Bind or quote a named placeholder in a query subpart. + * + * @param string $sub The query subpart. + * + * @return string The prepared query subpart. + * + */ + protected function prepareNamedPlaceholder($sub) + { + $name = substr($sub, 1); + + // is the corresponding data element an array? + $bind_array = isset($this->values[$name]) + && is_array($this->values[$name]); + if ($bind_array) { + // PDO won't bind an array; quote and replace directly + $sub = $this->xpdo->quote($this->values[$name]); + } else { + // not an array, retain the placeholder for later + $this->final_values[$name] = $this->values[$name]; + } + + return $sub; + } +}
\ No newline at end of file |