From 7133757c0ab0831328fd2b084915ad9f5f769eef Mon Sep 17 00:00:00 2001 From: Robert Sesek Date: Sun, 19 May 2013 14:41:02 -0400 Subject: [PATCH] Remove the database abstraction layer and write a new PDO backend. PDO is the future and what Hoplite requires. This hacks in a new DB_Abstract-like backend that uses PDO instead of the mysql_* family of functions. (cherry picked from commit 101c9dc4f6c1189fdb38c464d50773f56b5e7bb9) --- framework/db_mysql.php | 261 ------------------------ framework/{db.php => db_mysql_pdo.php} | 225 +++++--------------- framework/db_mysqli.php | 167 --------------- framework/db_postgresql.php | 271 ------------------------- includes/init.php | 3 +- 5 files changed, 49 insertions(+), 878 deletions(-) delete mode 100755 framework/db_mysql.php rename framework/{db.php => db_mysql_pdo.php} (64%) delete mode 100755 framework/db_mysqli.php delete mode 100755 framework/db_postgresql.php diff --git a/framework/db_mysql.php b/framework/db_mysql.php deleted file mode 100755 index 04a96d7..0000000 --- a/framework/db_mysql.php +++ /dev/null @@ -1,261 +0,0 @@ -load('db', null); - -/** -* MySQL Database Abstraction Layer -* -* This framework is a function wrapper for MySQL functions so we can have -* better error reporting and query reporting. -* -* @author Blue Static -* @copyright Copyright (c)2002 - [#]year[#], Blue Static -* @version $Revision$ -* @package ISSO -* -*/ -class DB_MySQL extends DB_Abstract -{ - /** - * Command mapping list - * @var array - * @access private - */ - var $commands = array( - 'pconnect' => '$this->command_mysql_pconnect', - 'connect' => '$this->command_mysql_connect', - 'query' => '$this->command_mysql_query', - 'error_num' => 'mysql_errno', - 'error_str' => 'mysql_error', - 'escape_string' => '$this->command_mysql_escape_string', - 'escape_binary' => '$this->escape_binary', - 'fetch_assoc' => 'mysql_fetch_assoc', - 'fetch_row' => 'mysql_fetch_row', - 'fetch_object' => 'mysql_fetch_object', - 'free_result' => 'mysql_free_result', - 'insert_id' => 'mysql_insert_id', - 'num_rows' => 'mysql_num_rows', - 'affected_rows' => 'mysql_affected_rows' - ); - - // ################################################################### - /** - * Constructor - */ - function __construct(&$registry) - { - parent::__construct($registry); - } - - // ################################################################### - /** - * (PHP 4) Constructor - */ - function DB_MySQL(&$registry) - { - $this->__construct($registry); - } - - // ################################################################### - /** - * Wrapper: mysql_pconnect - * - * @access protected - * - * @param string Server name - * @param string User name - * @param string Password - * @param string Database - * - * @return integer DB-Link - */ - function command_mysql_pconnect($server, $user, $password, $database) - { - $link = mysql_pconnect($server, $user, $password); - $this->select_db($database, $link); - - return $link; - } - - // ################################################################### - /** - * Wrapper: mysql_connect - * - * @access protected - * - * @param string Server name - * @param string User name - * @param string Password - * @param string Database - * - * @return integer DB-Link - */ - function command_mysql_connect($server, $user, $password, $database) - { - $link = mysql_connect($server, $user, $password, true); - $this->select_db($database, $link); - - return $link; - } - - // ################################################################### - /** - * Wrapper: mysql_select_db - * - * @access protected - * - * @param string Database name - * @param integer DB-Link - */ - function select_db($database, $link) - { - if (!mysql_select_db($database, $link)) - { - $this->error('Cannot use the database \'' . $database . '\''); - } - } - - // ################################################################### - /** - * Wrapper: mysql_query - * - * @access protected - * - * @param integer DB-Link - * @param string Query string - * - * @return integer Result - */ - function command_mysql_query($link, $string) - { - return mysql_query($string, $link); - } - - // ################################################################### - /** - * Escapes a binary string for insertion into the database - * - * @access public - * - * @param string Unescaped data - * - * @return string Escaped binary data - */ - function escape_binary($binary) - { - return mysql_escape_string($binary); - } - - // ################################################################### - /** - * Wrapper: mysql(_real)_escape_string - * - * @access protected - * - * @param integer DB-Link - * @param string Unescaped text - * - * @return string Escaped text - */ - function command_mysql_escape_string($link, $string) - { - if (function_exists('mysql_real_escape_string')) - { - return @mysql_real_escape_string($string, $link); - } - else - { - return @mysql_escape_string($string); - } - } - - // ################################################################### - /** - * Not supported: unescape binary string - * - * @access protected - * - * @param string Escaped data - * - * @return string Same data - */ - function command_unescape_binary($string) - { - return $string; - } - - // ################################################################### - /** - * Starts a database transaction - * - * @access public - */ - function transaction_start() - { - $this->query("BEGIN WORK"); - } - - // ################################################################### - /** - * Saves current transaction steps as a savepoint - * - * @access public - * - * @param string Named savepoint - */ - function transaction_savepoint($name) - { - $this->query("SAVEPOINT $name"); - } - - // ################################################################### - /** - * Reverts a transaction back to a given savepoint - * - * @access public - * - * @param string Named savepoint - */ - function transaction_rollback($name = null) - { - $this->query("ROLLBACK" . ($name != null ? " TO SAVEPOINT $name" : "")); - } - - // ################################################################### - /** - * Commits a database transaction - * - * @access public - */ - function transaction_commit() - { - $this->query("COMMIT"); - } -} - diff --git a/framework/db.php b/framework/db_mysql_pdo.php similarity index 64% rename from framework/db.php rename to framework/db_mysql_pdo.php index e79d8df..dbbba6d 100755 --- a/framework/db.php +++ b/framework/db_mysql_pdo.php @@ -27,23 +27,20 @@ */ /** -* Abstract Database Layer +* PDO MySQL Driver * -* This class provides an abstract template for all RDBMS layers. All -* ISSO abstraction layers should inherit this class. It provides error -* reporting, SQL analysis, and general connection functionality. +* This class wraps PDO-MySQL in the old DB_Abstract ISSO API. * * Constants: -* [required] ISSO_DB_LAYER - The name of the DB layer module used in the application * ISSO_SHOW_QUERIES_LIVE - Show queries in page output as they are sent * * @author Blue Static * @copyright Copyright (c)2002 - [#]year[#], Blue Static * @version $Revision$ * @package ISSO -* +* */ -class DB_Abstract +class DB_MySQL_PDO { /** * Framework registry object @@ -51,79 +48,56 @@ class DB_Abstract * @access protected */ var $registry = null; - + /** * Determines whether or not errors should be shown * @var bool * @access public */ var $showerrors = true; - + /** * Current error number * @var integer * @access protected */ var $errnum = 0; - + /** * Description of current error * @var string * @access protected */ var $errstr = ''; - + /** * Currend open MySQL connexion * @var resource * @access protected */ var $dblink = null; - + /** * Current query ID * @var integer * @access protected */ var $result = null; - + /** * Current query string * @var string * @access protected */ var $querystr = ''; - + /** * History of all executed queryies * @var array * @access protected */ var $history = array(); - - /** - * Command mapping list - * @var array - * @access protected - */ - var $commands = array( - 'pconnect' => '%server %user %password %database', - 'connect' => '%server %user %password %database', - 'query' => '%link %query', - 'error_num' => '%link', - 'error_str' => '%link', - 'escape_string' => '%link %string', - 'escape_binary' => '%string', - 'unescape_binary' => '%string', - 'fetch_assoc' => '%result', - 'fetch_row' => '%result', - 'fetch_object' => '%result', - 'free_result' => '%result', - 'insert_id' => '%link', - 'num_rows' => '%result', - 'affected_rows' => '%result' - ); - + // ################################################################### /** * Constructor @@ -131,45 +105,8 @@ class DB_Abstract function __construct(&$registry) { $this->registry =& $registry; - - // because ivars and call_user_func() are conspiring against us... - foreach ($this->commands AS $key => $string) - { - if (strpos($string, '$this->') !== false) - { - $this->commands["$key"] = array($this, str_replace('$this->', '', $string)); - } - } } - - // ################################################################### - /** - * (PHP 4) Constructor - */ - function DB_Abstract(&$registry) - { - $this->__construct($registry); - } - - // ################################################################### - /** - * Initializes the class and all subclasses under a common package name - * - * @access protected - * - * @return string The package name - */ - function init_as_package() - { - if (!defined('ISSO_DB_LAYER')) - { - define('ISSO_DB_LAYER', get_class($this)); - trigger_error('ISSO_DB_LAYER was defined automatically by DB::init_as_package(). Define the constant yourself to remove this warning', E_USER_WARNING); - } - - return 'db'; - } - + // ################################################################### /** * Connect to a the specified database @@ -186,20 +123,19 @@ class DB_Abstract */ function connect($server, $user, $password, $database, $pconnect) { + define('ISSO_DB_LAYER', 'db_mysql_pdo'); if ($this->dblink == false) { - $this->dblink = call_user_func(($pconnect ? $this->commands['pconnect'] : $this->commands['connect']), $server, $user, $password, $database); - + $this->dblink = new PDO("mysql:dbname=$database;host=$server", $user, $password); if ($this->dblink == false) { $this->error('DB-Link == false, cannot connect'); return false; } - return true; } } - + // ################################################################### /** * Send a query to the open database link @@ -213,17 +149,17 @@ class DB_Abstract function query($string) { $time = microtime(); - + $this->querystr = $string; - $this->result = @call_user_func($this->commands['query'], $this->dblink, $string); - + $this->result = $this->dblink->query($string); + if (!$this->result) { $this->error('Invalid SQL query'); } - + $this->history[] = $history = array('query' => $string, 'time' => ($this->registry->is_loaded('functions') ? $this->registry->modules['functions']->fetch_microtime_diff($time) : 0), 'trace' => $this->registry->format_debug_trace(debug_backtrace())); - + if (defined('ISSO_SHOW_QUERIES_LIVE')) { if (constant('ISSO_SHOW_QUERIES_LIVE')) @@ -231,10 +167,10 @@ class DB_Abstract print($this->construct_query_debug($history)); } } - + return $this->result; } - + // ################################################################### /** * Escape a string (depending on character set, if supported) @@ -247,9 +183,9 @@ class DB_Abstract */ function escape_string($string) { - return call_user_func($this->commands['escape_string'], $this->dblink, $string); + return $this->dblink->quote($string); } - + // ################################################################### /** * Escapes a binary string for insertion into the database @@ -264,22 +200,7 @@ class DB_Abstract { return call_user_func($this->commands['escape_binary'], $binary); } - - // ################################################################### - /** - * Unescapes a binary string that was fetched from the database - * - * @access public - * - * @param string Escaped data - * - * @return string Unescaped binary data - */ - function unescape_binary($binary) - { - return call_user_func($this->commands['unescape_binary'], $binary); - } - + // ################################################################### /** * Fetch the query result as an array @@ -293,9 +214,10 @@ class DB_Abstract */ function fetch_array($result, $assoc = true) { - return call_user_func($this->commands[ ($assoc ? 'fetch_assoc' : 'fetch_row') ], $result); + $style = $assoc ? PDO::FETCH_ASSOC : PDO::FETCH_NUM; + return $result->fetch($style); } - + // ################################################################### /** * Fetch the query result as an object @@ -308,9 +230,9 @@ class DB_Abstract */ function fetch_object($result) { - return call_user_func($this->commands['fetch_object'], $result); + return $result->fetch(PDO::FETCH_OBJ); } - + // ################################################################### /** * Send a query and return the first row of the results @@ -336,7 +258,7 @@ class DB_Abstract return false; } } - + // ################################################################### /** * Free the current query result @@ -347,11 +269,11 @@ class DB_Abstract */ function free_result($result) { - call_user_func($this->commands['free_result'], $result); + $result->closeCursor(); $this->result = null; $this->querystr = ''; } - + // ################################################################### /** * Fetch the unique ID of the record just inserted @@ -362,9 +284,9 @@ class DB_Abstract */ function insert_id() { - return call_user_func($this->commands['insert_id'], $this->dblink); + return $this->dblink->lastInsertId(); } - + // ################################################################### /** * Fetch the number of rows in the result @@ -377,9 +299,9 @@ class DB_Abstract */ function num_rows($result) { - return call_user_func($this->commands['num_rows'], $result); + return $result->rowCount(); } - + // ################################################################### /** * Fetch the number of rows affected by the query @@ -392,61 +314,9 @@ class DB_Abstract */ function affected_rows($result) { - return call_user_func($this->commands['affected_rows'], $result); - } - - // ################################################################### - /** - * Sends the command to start a transaction. This command should never - * be reached as it's always overridden - * - * @access public - */ - function transaction_start() - { - trigger_error('DB_Abstract::transaction_start() needs to be overridden when subclassed', E_USER_ERROR); + return $result->rowCount(); } - - // ################################################################### - /** - * Sends the command to set this as a savepoint. This command should never - * be reached as it's always overridden - * - * @access public - * - * @param string Named savepoint - */ - function transaction_savepoint($name) - { - trigger_error('DB_Abstract::transaction_savepoint() needs to be overridden when subclassed', E_USER_ERROR); - } - - // ################################################################### - /** - * Sends the command to rollback to a given savepoint. This command - * should never be reached as it's always overridden - * - * @access public - * - * @param string Named savepoint - */ - function transaction_rollback($name) - { - trigger_error('DB_Abstract::transaction_rollback() needs to be overridden when subclassed', E_USER_ERROR); - } - - // ################################################################### - /** - * Sends the command to commit the entire transaction. This command - * should never be reached as it's always overridden - * - * @access public - */ - function transaction_commit($name) - { - trigger_error('DB_Abstract::transaction_commit() needs to be overridden when subclassed', E_USER_ERROR); - } - + // ################################################################### /** * Constructs a table of query information output that is used in some @@ -465,10 +335,10 @@ class DB_Abstract $block .= "\n\t\n\t\t"; $block .= "Time: $query[time]
\n\t\t
\n\t\t"; $block .= "Backtrace:\n\t\t
" . implode("
\n", $query['trace']) . "
\n\t\n"; - + return $this->registry->message('Query Debug', $block, 1, true, false, 0); } - + // ################################################################### /** * Error wrapper for ISSO->message() @@ -483,12 +353,13 @@ class DB_Abstract { if ($this->dblink) { - $this->errnum = call_user_func($this->commands['error_num'], $this->dblink); - $this->errstr = call_user_func($this->commands['error_str'], $this->dblink); + $err = $this->dblink->errorInfo(); + $this->errnum = $err[0]; + $this->errstr = $err[1] . ': ' . $err[2]; } - + $style['code'] = 'font-family: \'Courier New\', Courier, mono; font-size: 11px;'; - + $message_prepped = "
\n

"; $message_prepped .= "\n\t» Query:\n

" . htmlspecialchars($this->querystr) ."
\n
"; $message_prepped .= "\n\t» Error Number: " . $this->errnum . "\n
"; @@ -496,7 +367,7 @@ class DB_Abstract $message_prepped .= "\n\t» Additional Notes: " . $message . "\n
"; $message_prepped .= "\n\t» File: " . $_SERVER['PHP_SELF'] . "\n"; $message_prepped .= "\n

\n
"; - + $this->registry->message('Database Error in `' . $this->registry->application . '`', $message_prepped, 3); exit; } diff --git a/framework/db_mysqli.php b/framework/db_mysqli.php deleted file mode 100755 index 5527c08..0000000 --- a/framework/db_mysqli.php +++ /dev/null @@ -1,167 +0,0 @@ -load('db', null); - -/** -* MySQLi Database Abstraction Layer -* -* This framework is a function wrapper for MySQLi functions so we can have -* better error reporting and query reporting. -* -* @author Blue Static -* @copyright Copyright (c)2002 - [#]year[#], Blue Static -* @version $Revision$ -* @package ISSO -* -*/ -class DB_MySQLi extends DB_Abstract -{ - /** - * Command mapping list - * @var array - * @access private - */ - var $commands = array( - 'pconnect' => '$this->command_mysqli_connect', - 'connect' => '$this->command_mysqli_connect', - 'query' => 'mysqli_query', - 'error_num' => 'mysqli_errno', - 'error_str' => 'mysqli_error', - 'escape_string' => 'mysqli_real_escape_string', - 'escape_binary' => 'mysqli_real_escape_string', - 'unescape_binary' => '$this->command_unescape_binary', - 'fetch_assoc' => 'mysqli_fetch_assoc', - 'fetch_row' => 'mysqli_fetch_row', - 'fetch_object' => 'mysqli_fetch_object', - 'free_result' => 'mysqli_free_result', - 'insert_id' => 'mysqli_insert_id', - 'num_rows' => 'mysqli_num_rows', - 'affected_rows' => 'mysqli_affected_rows' - ); - - // ################################################################### - /** - * Constructor - */ - function __construct(&$registry) - { - parent::__construct($registry); - } - - // ################################################################### - /** - * (PHP 4) Constructor - */ - function DB_MySQLi(&$registry) - { - $this->__construct($registry); - } - - // ################################################################### - /** - * Wrapper: mysqli_connect - * - * @access protected - * - * @param string Server name - * @param string User name - * @param string Password - * @param string Database - * - * @return integer DB-Link - */ - function command_mysqli_connect($server, $user, $password, $database) - { - return mysqli_connect($server, $user, $password, $database); - } - - // ################################################################### - /** - * Not supported: unescape binary string - * - * @access protected - * - * @param string Escaped data - * - * @return string Same data - */ - function command_unescape_binary($string) - { - return $string; - } - - // ################################################################### - /** - * Starts a database transaction - * - * @access public - */ - function transaction_start() - { - $this->query("START TRANSACTION"); - } - - // ################################################################### - /** - * Saves current transaction steps as a savepoint - * - * @access public - * - * @param string Named savepoint - */ - function transaction_savepoint($name) - { - $this->query("SAVEPOINT $name"); - } - - // ################################################################### - /** - * Reverts a transaction back to a given savepoint - * - * @access public - * - * @param string Named savepoint - */ - function transaction_rollback($name = null) - { - $this->query("ROLLBACK" . ($name != null ? " TO SAVEPOINT $name" : "")); - } - - // ################################################################### - /** - * Commits a database transaction - * - * @access public - */ - function transaction_commit() - { - $this->query("COMMIT"); - } -} - diff --git a/framework/db_postgresql.php b/framework/db_postgresql.php deleted file mode 100755 index 00529ff..0000000 --- a/framework/db_postgresql.php +++ /dev/null @@ -1,271 +0,0 @@ -load('db', null); - -/** -* PostgreSQL Database Abstraction Layer -* -* This framework is a function wrapper for PostgresQL functions so we can have -* better error reporting and query reporting. -* -* @author Blue Static -* @copyright Copyright (c)2002 - [#]year[#], Blue Static -* @version $Revision$ -* @package ISSO -* -*/ -class DB_PostgreSQL extends DB_Abstract -{ - /** - * Command mapping list - * @var array - * @access private - */ - var $commands = array( - 'pconnect' => '$this->command_pg_pconnect', - 'connect' => '$this->command_pg_connect', - 'query' => 'pg_query', - 'error_num' => '$this->command_error_num', - 'error_str' => '$this->command_error_str', - 'escape_string' => '$this->command_pg_escape_string', - 'escape_binary' => 'pg_escape_bytea', - 'unescape_binary' => 'pg_unescape_bytea', - 'fetch_assoc' => 'pg_fetch_assoc', - 'fetch_row' => 'pg_fetch_row', - 'fetch_object' => 'pg_fetch_object', - 'free_result' => 'pg_free_result', - 'insert_id' => '%link', // how do we support this...? - 'num_rows' => 'pg_num_rows', - 'affected_rows' => 'pg_affected_rows' - ); - - /** - * Port number to connect to - * @var integer - * @access private - */ - var $port = 5432; - - // ################################################################### - /** - * Constructor - */ - function __construct(&$registry) - { - parent::__construct($registry); - } - - // ################################################################### - /** - * (PHP 4) Constructor - */ - function DB_PostgreSQL(&$registry) - { - $this->__construct($registry); - } - - // ################################################################### - /** - * Sets the PGSQL port number - * - * @access public - * - * @param integer The port number - */ - function setPort($port) - { - $this->port = $port; - } - - // ################################################################### - /** - * Gets the currently-set port number - * - * @access public - * - * @return integer The port number - */ - function getPort() - { - return $this->port; - } - - // ################################################################### - /** - * Wrapper: pg_connect - * - * @access protected - * - * @param string Server name - * @param string User name - * @param string Password - * @param string Database - * - * @return integer DB-Link - */ - function command_pg_connect($server, $user, $password, $database) - { - return pg_connect("host='$server' port={$this->port} user='$user' password='$password' dbname='$database'"); - } - - // ################################################################### - /** - * Wrapper: pg_pconnect - * - * @access protected - * - * @param string Server name - * @param string User name - * @param string Password - * @param string Database - * - * @return integer DB-Link - */ - function command_pg_pconnect($server, $user, $password, $database) - { - return pg_pconnect("host='$server' port={$this->port} user='$user' password='$password' dbname='$database'"); - } - - // ################################################################### - /** - * Wrapper: pg_escape_string - * - * @access protected - * - * @param integer DB-Link (unused) - * @param string Raw string - * - * @return string Escaped string - */ - function command_pg_escape_string($link, $string) - { - return pg_escape_string($string); - } - - // ################################################################### - /** - * Wrapper/no support: error string - * - * @access protected - * - * @param integer DB-Link - * - * @return string Error string - */ - function command_error_str($link) - { - if ($this->result) - { - return pg_result_error($this->result); - } - - return pg_last_error($link); - } - - // ################################################################### - /** - * Not supported: error numbers - * - * @access protected - * - * @param integer DB-Link - * - * @return integer Returns -1 always - */ - function command_error_num($link) - { - return -1; - } - - // ################################################################### - /** - * Overload: insert_id - * - * @access public - * - * @param string Table name - * @param string Auto-up field - * - * @return integer Insert ID - */ - function insert_id($table, $field) - { - $temp = $this->query_first("SELECT last_value FROM {$table}_{$field}_seq"); - return $temp['last_value']; - } - - // ################################################################### - /** - * Starts a database transaction - * - * @access public - */ - function transaction_start() - { - $this->query("BEGIN"); - } - - // ################################################################### - /** - * Saves current transaction steps as a savepoint - * - * @access public - * - * @param string Named savepoint - */ - function transaction_savepoint($name) - { - $this->query("SAVEPOINT $name"); - } - - // ################################################################### - /** - * Reverts a transaction back to a given savepoint - * - * @access public - * - * @param string Named savepoint - */ - function transaction_rollback($name = null) - { - $this->query("ROLLBACK" . ($name != null ? " TO $name" : "")); - } - - // ################################################################### - /** - * Commits a database transaction - * - * @access public - */ - function transaction_commit() - { - $this->query("COMMIT"); - } -} - diff --git a/includes/init.php b/includes/init.php index aa83f68..d1d0ba4 100755 --- a/includes/init.php +++ b/includes/init.php @@ -46,8 +46,7 @@ require_once('./includes/config.php'); $bugsys->setDebug($debug); -define('ISSO_DB_LAYER', 'db_mysql'); -$bugsys->load('db_mysql', 'db', true); +$bugsys->load('db_mysql_pdo', 'db', true); $db->connect($servername, $username, $password, $database, $usepconnect); if ($utf8) { -- 2.43.5