2010-04-21 12:01:32 +00:00
< ? php
$possible_drivers [] = " SQLite " ;
$possible_drivers [] = " SQLite3 " ;
$possible_drivers [] = " PDO_SQLite " ;
if ( extension_loaded ( " sqlite3 " ) || extension_loaded ( " pdo_sqlite " )) {
$drivers [ " sqlite " ] = " SQLite 3 " ;
}
if ( extension_loaded ( " sqlite " ) || extension_loaded ( " pdo_sqlite " )) {
$drivers [ " sqlite2 " ] = " SQLite 2 " ;
}
if ( isset ( $_GET [ " sqlite " ]) || isset ( $_GET [ " sqlite2 " ])) {
define ( " DRIVER " , ( isset ( $_GET [ " sqlite " ]) ? " sqlite " : " sqlite2 " ));
if ( extension_loaded ( isset ( $_GET [ " sqlite2 " ]) ? " sqlite " : " sqlite3 " )) {
if ( isset ( $_GET [ " sqlite2 " ])) {
class Min_SQLite {
var $extension = " SQLite " , $server_info , $affected_rows , $error , $_connection ;
function __construct () {
$this -> server_info = sqlite_libversion ();
}
function open ( $filename ) {
$this -> _connection = new SQLiteDatabase ( $filename );
}
function query ( $query , $unbuffered = false ) {
$method = ( $unbuffered ? " unbufferedQuery " : " query " );
$result = @ $this -> _connection -> $method ( $query , SQLITE_BOTH , $error );
if ( ! $result ) {
$this -> error = $error ;
return false ;
} elseif ( $result === true ) {
$this -> affected_rows = $this -> changes ();
return true ;
}
return new Min_Result ( $result );
}
function quote ( $string ) {
return " ' " . sqlite_escape_string ( $string ) . " ' " ;
}
function result ( $query , $field = 0 ) {
$result = $this -> query ( $query );
2010-04-21 15:09:52 +00:00
if ( ! is_object ( $result )) {
2010-04-21 12:01:32 +00:00
return false ;
}
$row = $result -> _result -> fetch ();
return $row [ $field ];
}
}
class Min_Result {
var $_result , $_offset = 0 , $num_rows ;
function __construct ( $result ) {
$this -> _result = $result ;
if ( method_exists ( $result , 'numRows' )) { // not available in unbuffered query
$this -> num_rows = $result -> numRows ();
}
}
function fetch_assoc () {
$row = $this -> _result -> fetch ( SQLITE_ASSOC );
if ( ! $row ) {
return false ;
}
$return = array ();
foreach ( $row as $key => $val ) {
$return [( $key [ 0 ] == '"' ? idf_unescape ( $key ) : $key )] = $val ;
}
return $return ;
}
function fetch_row () {
return $this -> _result -> fetch ( SQLITE_NUM );
}
function fetch_field () {
return ( object ) array (
" name " => $this -> _result -> fieldName ( $this -> _offset ++ ),
//! type, orgtable, charsetnr
);
}
}
} else {
2010-04-21 15:09:52 +00:00
class Min_SQLite {
var $extension = " SQLite3 " , $server_info , $affected_rows , $error , $_connection ;
2010-04-21 12:01:32 +00:00
function __construct () {
2010-04-21 15:09:52 +00:00
$this -> _connection = new SQLite3 ( " :memory: " ); // required to display variables
$version = $this -> _connection -> version ();
2010-04-21 12:01:32 +00:00
$this -> server_info = $version [ " versionString " ];
}
function open ( $filename ) {
2010-04-21 15:09:52 +00:00
$this -> _connection -> open ( $filename );
2010-04-21 12:01:32 +00:00
}
function query ( $query ) {
2010-04-21 15:09:52 +00:00
$result = @ $this -> _connection -> query ( $query );
2010-04-21 12:01:32 +00:00
if ( ! $result ) {
2010-04-21 15:09:52 +00:00
$this -> error = $this -> _connection -> lastErrorMsg ();
2010-04-21 12:01:32 +00:00
return false ;
} elseif ( $result -> numColumns ()) {
return new Min_Result ( $result );
}
2010-04-21 15:09:52 +00:00
$this -> affected_rows = $this -> _connection -> changes ();
2010-04-21 12:01:32 +00:00
return true ;
}
function quote ( $string ) {
2010-04-21 15:09:52 +00:00
return " ' " . $this -> _connection -> escapeString ( $string ) . " ' " ;
2010-04-21 12:01:32 +00:00
}
function result ( $query , $field = 0 ) {
$result = $this -> query ( $query );
2010-04-21 15:09:52 +00:00
if ( ! is_object ( $result )) {
2010-04-21 12:01:32 +00:00
return false ;
}
$row = $result -> _result -> fetchArray ();
return $row [ $field ];
}
}
class Min_Result {
var $_result , $_offset = 0 , $num_rows ;
function __construct ( $result ) {
$this -> _result = $result ;
$this -> num_rows = 1 ; //!
}
function fetch_assoc () {
return $this -> _result -> fetchArray ( SQLITE3_ASSOC );
}
function fetch_row () {
return $this -> _result -> fetchArray ( SQLITE3_NUM );
}
function fetch_field () {
$column = $this -> _offset ++ ;
return ( object ) array (
" name " => $this -> _result -> columnName ( $column ),
" type " => $this -> _result -> columnType ( $column ),
//! orgtable, charsetnr
);
}
function __desctruct () {
return $this -> _result -> finalize ();
}
}
}
class Min_DB extends Min_SQLite {
function select_db ( $filename ) {
static $connected = false ;
if ( $connected ) {
return true ;
}
set_exception_handler ( 'connect_error' ); // try/catch is not compatible with PHP 4
$this -> open ( $filename );
$connected = true ;
restore_exception_handler ();
return true ;
}
function multi_query ( $query ) {
return $this -> _result = $this -> query ( $query );
}
function store_result () {
return $this -> _result ;
}
function next_result () {
return false ;
}
}
} elseif ( extension_loaded ( " pdo_sqlite " )) {
class Min_DB extends Min_PDO {
var $extension = " PDO_SQLite " ;
function select_db ( $filename ) {
static $connected = false ;
if ( $connected ) {
return true ;
}
$connected = true ;
$this -> dsn ( DRIVER . " : $filename " , " " , " " , " connect_error " );
//! $this->server_info needs to be filled in __construct()
return true ;
}
}
}
function idf_escape ( $idf ) {
return '"' . str_replace ( '"' , '""' , $idf ) . '"' ;
}
function connect () {
global $connection ;
if ( $connection ) {
return $connection ; // can connect only once, function to get number of rows doesn't exist anyway
}
return new Min_DB ;
}
function get_databases () {
return array ();
}
function limit ( $query , $limit , $offset = 0 ) {
return " $query " . ( isset ( $limit ) ? " \n LIMIT $limit " . ( $offset ? " OFFSET $offset " : " " ) : " " );
}
function limit1 ( $query ) {
global $connection ;
return ( $connection -> result ( " SELECT sqlite_compileoption_used('ENABLE_UPDATE_DELETE_LIMIT') " ) ? limit ( $query , 1 ) : " $query " );
}
function db_collation ( $db , $collations ) {
return null ;
}
function engines () {
return array ();
}
function logged_user () {
2010-04-21 16:26:16 +00:00
return get_current_user (); // should return effective user
2010-04-21 12:01:32 +00:00
}
function tables_list () {
return get_key_vals ( " SELECT name, type FROM sqlite_master WHERE type IN ('table', 'view') " , 1 );
}
function count_tables ( $databases ) {
return array ();
}
function table_status ( $name = " " ) {
global $connection ;
$return = array ();
$result = $connection -> query ( " SELECT name AS Name, type AS Engine FROM sqlite_master WHERE type IN ('table', 'view') " . ( $name != " " ? " AND name = " . $connection -> quote ( $name ) : " " ));
while ( $row = $result -> fetch_assoc ()) {
2010-04-21 15:09:52 +00:00
$row [ " Auto_increment " ] = " " ;
2010-04-21 12:01:32 +00:00
$return [ $row [ " Name " ]] = $row ;
}
$result = $connection -> query ( " SELECT * FROM sqlite_sequence " );
if ( $result ) {
while ( $row = $result -> fetch_assoc ()) {
$return [ $row [ " name " ]][ " Auto_increment " ] = $row [ " seq " ];
}
}
return ( $name != " " ? $return [ $name ] : $return );
}
function fk_support ( $table_status ) {
global $connection ;
return ! $connection -> result ( " SELECT sqlite_compileoption_used('OMIT_FOREIGN_KEY') " );
}
function fields ( $table ) {
global $connection ;
$return = array ();
$result = $connection -> query ( " PRAGMA table_info( " . idf_escape ( $table ) . " ) " );
if ( is_object ( $result )) {
while ( $row = $result -> fetch_assoc ()) {
$type = strtolower ( $row [ " type " ]);
$return [ $row [ " name " ]] = array (
" field " => $row [ " name " ],
" type " => ( eregi ( " int " , $type ) ? " integer " : ( eregi ( " char|clob|text " , $type ) ? " text " : ( eregi ( " blob " , $type ) ? " blob " : ( eregi ( " real|floa|doub " , $type ) ? " real " : " numeric " )))),
" full_type " => $type ,
" default " => $row [ " dflt_value " ],
" null " => ! $row [ " notnull " ],
" auto_increment " => eregi ( '^integer$' , $type ) && $row [ " pk " ], //! possible false positive
" collation " => null , //!
" privileges " => array ( " select " => 1 , " insert " => 1 , " update " => 1 ),
" primary " => $row [ " pk " ],
);
}
}
return $return ;
}
function indexes ( $table , $connection2 = null ) {
global $connection ;
$return = array ();
$primary = array ();
foreach ( fields ( $table ) as $field ) {
if ( $field [ " primary " ]) {
$primary [] = $field [ " field " ];
}
}
if ( $primary ) {
$return [ " " ] = array ( " type " => " PRIMARY " , " columns " => $primary , " lengths " => array ());
}
$result = $connection -> query ( " PRAGMA index_list( " . idf_escape ( $table ) . " ) " );
if ( is_object ( $result )) {
while ( $row = $result -> fetch_assoc ()) {
$return [ $row [ " name " ]][ " type " ] = ( $row [ " unique " ] ? " UNIQUE " : " INDEX " );
$return [ $row [ " name " ]][ " lengths " ] = array ();
$result1 = $connection -> query ( " PRAGMA index_info( " . idf_escape ( $row [ " name " ]) . " ) " );
while ( $row1 = $result1 -> fetch_assoc ()) {
$return [ $row [ " name " ]][ " columns " ][] = $row1 [ " name " ];
}
}
}
return $return ;
}
function foreign_keys ( $table ) {
global $connection ;
$return = array ();
$result = $connection -> query ( " PRAGMA foreign_key_list( " . idf_escape ( $table ) . " ) " );
if ( is_object ( $result )) {
while ( $row = $result -> fetch_assoc ()) {
$foreign_key = & $return [ $row [ " id " ]];
if ( ! $foreign_key ) {
$foreign_key = $row ;
}
$foreign_key [ " source " ][] = $row [ " from " ];
$foreign_key [ " target " ][] = $row [ " to " ];
}
}
return $return ;
}
function view ( $name ) {
global $connection ;
return array ( " select " => preg_replace ( '~^(?:[^`"[]+|`[^`]*`|"[^"]*")* AS\\s+~iU' , '' , $connection -> result ( " SELECT sql FROM sqlite_master WHERE name = " . $connection -> quote ( $name )))); //! identifiers may be inside []
}
function collations () {
return get_vals ( " PRAGMA collation_list " , 1 );
}
function information_schema ( $db ) {
return false ;
}
function error () {
global $connection ;
return h ( $connection -> error );
}
function exact_value ( $val ) {
global $connection ;
return $connection -> quote ( $val );
}
function rename_database ( $name , $collation ) {
global $connection ;
$connection -> close (); //! not available with all extensions
return rename ( DB , $name );
}
function auto_increment () {
return " PRIMARY KEY " . ( DRIVER == " sqlite " ? " AUTOINCREMENT " : " " );
}
function alter_table ( $table , $name , $fields , $foreign , $comment , $engine , $collation , $auto_increment , $partitioning ) {
global $connection ;
$alter = array ();
foreach ( $fields as $field ) {
$alter [] = ( $table != " " && $field [ 0 ] == " " ? " ADD " : " " ) . implode ( " " , $field [ 1 ]);
}
$alter = array_merge ( $alter , $foreign );
if ( $table != " " ) {
foreach ( $alter as $val ) {
if ( ! queries ( " ALTER TABLE " . idf_escape ( $table ) . " $val " )) {
return false ;
}
}
if ( $table != $name && ! queries ( " ALTER TABLE " . idf_escape ( $table ) . " RENAME TO " . idf_escape ( $name ))) {
return false ;
}
} elseif ( ! queries ( " CREATE TABLE " . idf_escape ( $name ) . " ( \n " . implode ( " , \n " , $alter ) . " \n ) " )) {
return false ;
}
if ( $auto_increment ) {
return queries ( " UPDATE sqlite_sequence SET seq = $auto_increment WHERE name = " . $connection -> quote ( $name ) . " " );
}
return true ;
}
function alter_indexes ( $table , $alter ) {
foreach ( $alter as $val ) {
if ( ! queries (( $val [ 2 ] ? " DROP INDEX " : " CREATE " . ( $val [ 0 ] != " INDEX " ? " UNIQUE " : " " ) . " INDEX " . idf_escape ( uniqid ( $table . " _ " )) . " ON " . idf_escape ( $table )) . " $val[1] " )) { //! primary key must be created in CREATE TABLE
return false ;
}
}
return true ;
}
function truncate_tables ( $tables ) {
foreach ( $tables as $table ) {
if ( ! queries ( " DELETE FROM " . idf_escape ( $table ))) {
return false ;
}
}
return true ;
}
function drop_views ( $views ) {
foreach ( $views as $view ) {
if ( ! queries ( " DROP VIEW " . idf_escape ( $view ))) {
return false ;
}
}
return true ;
}
function drop_tables ( $tables ) {
foreach ( $tables as $table ) {
if ( ! queries ( " DROP TABLE " . idf_escape ( $table ))) {
return false ;
}
}
return true ;
}
function trigger ( $name ) {
global $connection ;
preg_match ( '~^CREATE\\s+TRIGGER\\s*(?:[^`"\\s]+|`[^`]*`|"[^"]*")+\\s*([a-z]+)\\s+([a-z]+)\\s+ON\\s*(?:[^`"\\s]+|`[^`]*`|"[^"]*")+\\s*(?:FOR\\s*EACH\\s*ROW\\s)?(.*)~is' , $connection -> result ( " SELECT sql FROM sqlite_master WHERE name = " . $connection -> quote ( $name )), $match );
return array ( " Timing " => strtoupper ( $match [ 1 ]), " Event " => strtoupper ( $match [ 2 ]), " Trigger " => $name , " Statement " => $match [ 3 ]);
}
function triggers ( $table ) {
global $connection ;
$return = array ();
$result = $connection -> query ( " SELECT * FROM sqlite_master WHERE type = 'trigger' AND tbl_name = " . $connection -> quote ( $table ));
while ( $row = $result -> fetch_assoc ()) {
preg_match ( '~^CREATE\\s+TRIGGER\\s*(?:[^`"\\s]+|`[^`]*`|"[^"]*")+\\s*([a-z]+)\\s*([a-z]+)~i' , $row [ " sql " ], $match );
$return [ $row [ " name " ]] = array ( $match [ 1 ], $match [ 2 ]);
}
return $return ;
}
function explain ( $connection , $query ) {
return $connection -> query ( " EXPLAIN $query " );
}
function create_sql ( $table ) {
global $connection ;
return $connection -> result ( " SELECT sql FROM sqlite_master WHERE name = " . $connection -> quote ( $table ));
}
2010-04-21 15:09:52 +00:00
function show_variables () {
global $connection ;
$return = array ();
foreach ( array ( " auto_vacuum " , " cache_size " , " count_changes " , " default_cache_size " , " empty_result_callbacks " , " encoding " , " foreign_keys " , " full_column_names " , " fullfsync " , " journal_mode " , " journal_size_limit " , " legacy_file_format " , " locking_mode " , " page_size " , " max_page_count " , " read_uncommitted " , " recursive_triggers " , " reverse_unordered_selects " , " secure_delete " , " short_column_names " , " synchronous " , " temp_store " , " temp_store_directory " , " schema_version " , " compile_options " , " integrity_check " , " quick_check " ) as $key ) {
$return [ $key ] = $connection -> result ( " PRAGMA $key " );
}
return $return ;
}
function show_status () {
// not supported
}
2010-04-21 12:01:32 +00:00
function support ( $feature ) {
2010-04-21 15:09:52 +00:00
return ereg ( '^(view|trigger|variables)$' , $feature );
2010-04-21 12:01:32 +00:00
}
$driver = " sqlite " ;
$types = array ( " integer " => 0 , " real " => 0 , " numeric " => 0 , " text " => 0 , " blob " => 0 );
$structured_types = array_keys ( $types );
$unsigned = array ();
$operators = array ( " = " , " < " , " > " , " <= " , " >= " , " != " , " LIKE " , " LIKE %% " , " IN " , " IS NULL " , " NOT LIKE " , " NOT IN " , " IS NOT NULL " ); // REGEXP can be user defined function
$functions = array ( " hex " , " length " , " lower " , " round " , " unixepoch " , " upper " );
$grouping = array ( " avg " , " count " , " count distinct " , " group_concat " , " max " , " min " , " sum " );
$edit_functions = array (
array (
// "text" => "date('now')/time('now')/datetime('now')",
), array (
" integer|real|numeric " => " +/- " ,
// "text" => "date/time/datetime",
" text " => " || " ,
)
);
}