PageRenderTime 288ms CodeModel.GetById 160ms app.highlight 17ms RepoModel.GetById 104ms app.codeStats 0ms

/halogy/database/drivers/mysqli/mysqli_driver.php

https://bitbucket.org/haloweb/halogy-1.0/
PHP | 671 lines | 261 code | 103 blank | 307 comment | 31 complexity | 11747a60c96116c877b9e8ba8aca239a MD5 | raw file
  1<?php  if ( ! defined('BASEPATH')) exit('No direct script access allowed');
  2/**
  3 * CodeIgniter
  4 *
  5 * An open source application development framework for PHP 4.3.2 or newer
  6 *
  7 * @package		CodeIgniter
  8 * @author		ExpressionEngine Dev Team
  9 * @copyright	Copyright (c) 2008 - 2009, EllisLab, Inc.
 10 * @license		http://codeigniter.com/user_guide/license.html
 11 * @link		http://codeigniter.com
 12 * @since		Version 1.0
 13 * @filesource
 14 */
 15
 16// ------------------------------------------------------------------------
 17
 18/**
 19 * MySQLi Database Adapter Class - MySQLi only works with PHP 5
 20 *
 21 * Note: _DB is an extender class that the app controller
 22 * creates dynamically based on whether the active record
 23 * class is being used or not.
 24 *
 25 * @package		CodeIgniter
 26 * @subpackage	Drivers
 27 * @category	Database
 28 * @author		ExpressionEngine Dev Team
 29 * @link		http://codeigniter.com/user_guide/database/
 30 */
 31class CI_DB_mysqli_driver extends CI_DB {
 32
 33	var $dbdriver = 'mysqli';
 34	
 35	// The character used for escaping
 36	var $_escape_char = '`';
 37
 38	// clause and character used for LIKE escape sequences - not used in MySQL
 39	var $_like_escape_str = '';
 40	var $_like_escape_chr = '';
 41
 42	/**
 43	 * The syntax to count rows is slightly different across different
 44	 * database engines, so this string appears in each driver and is
 45	 * used for the count_all() and count_all_results() functions.
 46	 */
 47	var $_count_string = "SELECT COUNT(*) AS ";
 48	var $_random_keyword = ' RAND()'; // database specific random keyword
 49
 50	/**
 51	 * Whether to use the MySQL "delete hack" which allows the number
 52	 * of affected rows to be shown. Uses a preg_replace when enabled,
 53	 * adding a bit more processing to all queries.
 54	 */	
 55	var $delete_hack = TRUE;
 56
 57	// --------------------------------------------------------------------
 58
 59	/**
 60	 * Non-persistent database connection
 61	 *
 62	 * @access	private called by the base class
 63	 * @return	resource
 64	 */	
 65	function db_connect()
 66	{
 67		if ($this->port != '')
 68		{
 69			return @mysqli_connect($this->hostname, $this->username, $this->password, $this->database, $this->port);			
 70		}
 71		else
 72		{
 73			return @mysqli_connect($this->hostname, $this->username, $this->password, $this->database);
 74		}
 75
 76	}
 77
 78	// --------------------------------------------------------------------
 79
 80	/**
 81	 * Persistent database connection
 82	 *
 83	 * @access	private called by the base class
 84	 * @return	resource
 85	 */	
 86	function db_pconnect()
 87	{
 88		return $this->db_connect();
 89	}
 90	
 91	// --------------------------------------------------------------------
 92
 93	/**
 94	 * Reconnect
 95	 *
 96	 * Keep / reestablish the db connection if no queries have been
 97	 * sent for a length of time exceeding the server's idle timeout
 98	 *
 99	 * @access	public
100	 * @return	void
101	 */
102	function reconnect()
103	{
104		if (mysqli_ping($this->conn_id) === FALSE)
105		{
106			$this->conn_id = FALSE;
107		}
108	}
109
110	// --------------------------------------------------------------------
111
112	/**
113	 * Select the database
114	 *
115	 * @access	private called by the base class
116	 * @return	resource
117	 */	
118	function db_select()
119	{
120		return @mysqli_select_db($this->conn_id, $this->database);
121	}
122
123	// --------------------------------------------------------------------
124
125	/**
126	 * Set client character set
127	 *
128	 * @access	private
129	 * @param	string
130	 * @param	string
131	 * @return	resource
132	 */
133	function _db_set_charset($charset, $collation)
134	{
135		return @mysqli_query($this->conn_id, "SET NAMES '".$this->escape_str($charset)."' COLLATE '".$this->escape_str($collation)."'");
136	}
137
138	// --------------------------------------------------------------------
139	
140	/**
141	 * Version number query string
142	 *
143	 * @access	public
144	 * @return	string
145	 */
146	function _version()
147	{
148		return "SELECT version() AS ver";
149	}
150
151	// --------------------------------------------------------------------
152
153	/**
154	 * Execute the query
155	 *
156	 * @access	private called by the base class
157	 * @param	string	an SQL query
158	 * @return	resource
159	 */	
160	function _execute($sql)
161	{
162		$sql = $this->_prep_query($sql);	
163		$result = @mysqli_query($this->conn_id, $sql);
164		return $result;
165	}
166	
167	// --------------------------------------------------------------------
168
169	/**
170	 * Prep the query
171	 *
172	 * If needed, each database adapter can prep the query string
173	 *
174	 * @access	private called by execute()
175	 * @param	string	an SQL query
176	 * @return	string
177	 */	
178	function _prep_query($sql)
179	{
180		// "DELETE FROM TABLE" returns 0 affected rows This hack modifies
181		// the query so that it returns the number of affected rows
182		if ($this->delete_hack === TRUE)
183		{
184			if (preg_match('/^\s*DELETE\s+FROM\s+(\S+)\s*$/i', $sql))
185			{
186				$sql = preg_replace("/^\s*DELETE\s+FROM\s+(\S+)\s*$/", "DELETE FROM \\1 WHERE 1=1", $sql);
187			}
188		}
189		
190		return $sql;
191	}
192
193	// --------------------------------------------------------------------
194
195	/**
196	 * Begin Transaction
197	 *
198	 * @access	public
199	 * @return	bool		
200	 */	
201	function trans_begin($test_mode = FALSE)
202	{
203		if ( ! $this->trans_enabled)
204		{
205			return TRUE;
206		}
207		
208		// When transactions are nested we only begin/commit/rollback the outermost ones
209		if ($this->_trans_depth > 0)
210		{
211			return TRUE;
212		}
213
214		// Reset the transaction failure flag.
215		// If the $test_mode flag is set to TRUE transactions will be rolled back
216		// even if the queries produce a successful result.
217		$this->_trans_failure = ($test_mode === TRUE) ? TRUE : FALSE;
218
219		$this->simple_query('SET AUTOCOMMIT=0');
220		$this->simple_query('START TRANSACTION'); // can also be BEGIN or BEGIN WORK
221		return TRUE;
222	}
223
224	// --------------------------------------------------------------------
225
226	/**
227	 * Commit Transaction
228	 *
229	 * @access	public
230	 * @return	bool		
231	 */	
232	function trans_commit()
233	{
234		if ( ! $this->trans_enabled)
235		{
236			return TRUE;
237		}
238
239		// When transactions are nested we only begin/commit/rollback the outermost ones
240		if ($this->_trans_depth > 0)
241		{
242			return TRUE;
243		}
244
245		$this->simple_query('COMMIT');
246		$this->simple_query('SET AUTOCOMMIT=1');
247		return TRUE;
248	}
249
250	// --------------------------------------------------------------------
251
252	/**
253	 * Rollback Transaction
254	 *
255	 * @access	public
256	 * @return	bool		
257	 */	
258	function trans_rollback()
259	{
260		if ( ! $this->trans_enabled)
261		{
262			return TRUE;
263		}
264
265		// When transactions are nested we only begin/commit/rollback the outermost ones
266		if ($this->_trans_depth > 0)
267		{
268			return TRUE;
269		}
270
271		$this->simple_query('ROLLBACK');
272		$this->simple_query('SET AUTOCOMMIT=1');
273		return TRUE;
274	}
275
276	// --------------------------------------------------------------------
277
278	/**
279	 * Escape String
280	 *
281	 * @access	public
282	 * @param	string
283	 * @param	bool	whether or not the string will be used in a LIKE condition
284	 * @return	string
285	 */
286	function escape_str($str, $like = FALSE)	
287	{
288		if (is_array($str))
289		{
290			foreach($str as $key => $val)
291	   		{
292				$str[$key] = $this->escape_str($val, $like);
293	   		}
294   		
295	   		return $str;
296	   	}
297
298		if (function_exists('mysqli_real_escape_string') AND is_object($this->conn_id))
299		{
300			$str = mysqli_real_escape_string($this->conn_id, $str);
301		}
302		elseif (function_exists('mysql_escape_string'))
303		{
304			$str = mysql_escape_string($str);
305		}
306		else
307		{
308			$str = addslashes($str);
309		}
310		
311		// escape LIKE condition wildcards
312		if ($like === TRUE)
313		{
314			$str = str_replace(array('%', '_'), array('\\%', '\\_'), $str);
315		}
316		
317		return $str;
318	}
319		
320	// --------------------------------------------------------------------
321
322	/**
323	 * Affected Rows
324	 *
325	 * @access	public
326	 * @return	integer
327	 */
328	function affected_rows()
329	{
330		return @mysqli_affected_rows($this->conn_id);
331	}
332	
333	// --------------------------------------------------------------------
334
335	/**
336	 * Insert ID
337	 *
338	 * @access	public
339	 * @return	integer
340	 */
341	function insert_id()
342	{
343		return @mysqli_insert_id($this->conn_id);
344	}
345
346	// --------------------------------------------------------------------
347
348	/**
349	 * "Count All" query
350	 *
351	 * Generates a platform-specific query string that counts all records in
352	 * the specified database
353	 *
354	 * @access	public
355	 * @param	string
356	 * @return	string
357	 */
358	function count_all($table = '')
359	{
360		if ($table == '')
361		{
362			return 0;
363		}
364
365		$query = $this->query($this->_count_string . $this->_protect_identifiers('numrows') . " FROM " . $this->_protect_identifiers($table, TRUE, NULL, FALSE));
366
367		if ($query->num_rows() == 0)
368		{
369			return 0;
370		}
371
372		$row = $query->row();
373		return (int) $row->numrows;
374	}
375
376	// --------------------------------------------------------------------
377
378	/**
379	 * List table query
380	 *
381	 * Generates a platform-specific query string so that the table names can be fetched
382	 *
383	 * @access	private
384	 * @param	boolean
385	 * @return	string
386	 */
387	function _list_tables($prefix_limit = FALSE)
388	{
389		$sql = "SHOW TABLES FROM ".$this->_escape_char.$this->database.$this->_escape_char;	
390		
391		if ($prefix_limit !== FALSE AND $this->dbprefix != '')
392		{
393			$sql .= " LIKE '".$this->escape_like_str($this->dbprefix)."%'";
394		}
395		
396		return $sql;
397	}
398
399	// --------------------------------------------------------------------
400
401	/**
402	 * Show column query
403	 *
404	 * Generates a platform-specific query string so that the column names can be fetched
405	 *
406	 * @access	public
407	 * @param	string	the table name
408	 * @return	string
409	 */
410	function _list_columns($table = '')
411	{
412		return "SHOW COLUMNS FROM ".$table;
413	}
414
415	// --------------------------------------------------------------------
416
417	/**
418	 * Field data query
419	 *
420	 * Generates a platform-specific query so that the column data can be retrieved
421	 *
422	 * @access	public
423	 * @param	string	the table name
424	 * @return	object
425	 */
426	function _field_data($table)
427	{
428		return "SELECT * FROM ".$table." LIMIT 1";
429	}
430
431	// --------------------------------------------------------------------
432
433	/**
434	 * The error message string
435	 *
436	 * @access	private
437	 * @return	string
438	 */
439	function _error_message()
440	{
441		return mysqli_error($this->conn_id);
442	}
443	
444	// --------------------------------------------------------------------
445
446	/**
447	 * The error message number
448	 *
449	 * @access	private
450	 * @return	integer
451	 */
452	function _error_number()
453	{
454		return mysqli_errno($this->conn_id);
455	}
456
457	// --------------------------------------------------------------------
458
459	/**
460	 * Escape the SQL Identifiers
461	 *
462	 * This function escapes column and table names
463	 *
464	 * @access	private
465	 * @param	string
466	 * @return	string
467	 */
468	function _escape_identifiers($item)
469	{
470		if ($this->_escape_char == '')
471		{
472			return $item;
473		}
474		
475		foreach ($this->_reserved_identifiers as $id)
476		{
477			if (strpos($item, '.'.$id) !== FALSE)
478			{
479				$str = $this->_escape_char. str_replace('.', $this->_escape_char.'.', $item);  
480				
481				// remove duplicates if the user already included the escape
482				return preg_replace('/['.$this->_escape_char.']+/', $this->_escape_char, $str);
483			}		
484		}
485		
486		if (strpos($item, '.') !== FALSE)
487		{
488			$str = $this->_escape_char.str_replace('.', $this->_escape_char.'.'.$this->_escape_char, $item).$this->_escape_char;			
489		}
490		else
491		{
492			$str = $this->_escape_char.$item.$this->_escape_char;
493		}
494		
495		// remove duplicates if the user already included the escape
496		return preg_replace('/['.$this->_escape_char.']+/', $this->_escape_char, $str);
497	}
498			
499	// --------------------------------------------------------------------
500
501	/**
502	 * From Tables
503	 *
504	 * This function implicitly groups FROM tables so there is no confusion
505	 * about operator precedence in harmony with SQL standards
506	 *
507	 * @access	public
508	 * @param	type
509	 * @return	type
510	 */
511	function _from_tables($tables)
512	{
513		if ( ! is_array($tables))
514		{
515			$tables = array($tables);
516		}
517		
518		return '('.implode(', ', $tables).')';
519	}
520
521	// --------------------------------------------------------------------
522	
523	/**
524	 * Insert statement
525	 *
526	 * Generates a platform-specific insert string from the supplied data
527	 *
528	 * @access	public
529	 * @param	string	the table name
530	 * @param	array	the insert keys
531	 * @param	array	the insert values
532	 * @return	string
533	 */
534	function _insert($table, $keys, $values)
535	{	
536		return "INSERT INTO ".$table." (".implode(', ', $keys).") VALUES (".implode(', ', $values).")";
537	}
538	
539	// --------------------------------------------------------------------
540
541	/**
542	 * Update statement
543	 *
544	 * Generates a platform-specific update string from the supplied data
545	 *
546	 * @access	public
547	 * @param	string	the table name
548	 * @param	array	the update data
549	 * @param	array	the where clause
550	 * @param	array	the orderby clause
551	 * @param	array	the limit clause
552	 * @return	string
553	 */
554	function _update($table, $values, $where, $orderby = array(), $limit = FALSE)
555	{
556		foreach($values as $key => $val)
557		{
558			$valstr[] = $key." = ".$val;
559		}
560		
561		$limit = ( ! $limit) ? '' : ' LIMIT '.$limit;
562		
563		$orderby = (count($orderby) >= 1)?' ORDER BY '.implode(", ", $orderby):'';
564	
565		$sql = "UPDATE ".$table." SET ".implode(', ', $valstr);
566		
567		$sql .= ($where != '' AND count($where) >=1) ? " WHERE ".implode(" ", $where) : '';
568		
569		$sql .= $orderby.$limit;
570		
571		return $sql;
572	}
573
574	
575	// --------------------------------------------------------------------
576
577	/**
578	 * Truncate statement
579	 *
580	 * Generates a platform-specific truncate string from the supplied data
581	 * If the database does not support the truncate() command
582	 * This function maps to "DELETE FROM table"
583	 *
584	 * @access	public
585	 * @param	string	the table name
586	 * @return	string
587	 */	
588	function _truncate($table)
589	{
590		return "TRUNCATE ".$table;
591	}
592	
593	// --------------------------------------------------------------------
594
595	/**
596	 * Delete statement
597	 *
598	 * Generates a platform-specific delete string from the supplied data
599	 *
600	 * @access	public
601	 * @param	string	the table name
602	 * @param	array	the where clause
603	 * @param	string	the limit clause
604	 * @return	string
605	 */	
606	function _delete($table, $where = array(), $like = array(), $limit = FALSE)
607	{
608		$conditions = '';
609
610		if (count($where) > 0 OR count($like) > 0)
611		{
612			$conditions = "\nWHERE ";
613			$conditions .= implode("\n", $this->ar_where);
614
615			if (count($where) > 0 && count($like) > 0)
616			{
617				$conditions .= " AND ";
618			}
619			$conditions .= implode("\n", $like);
620		}
621
622		$limit = ( ! $limit) ? '' : ' LIMIT '.$limit;
623	
624		return "DELETE FROM ".$table.$conditions.$limit;
625	}
626
627	// --------------------------------------------------------------------
628
629	/**
630	 * Limit string
631	 *
632	 * Generates a platform-specific LIMIT clause
633	 *
634	 * @access	public
635	 * @param	string	the sql query string
636	 * @param	integer	the number of rows to limit the query to
637	 * @param	integer	the offset value
638	 * @return	string
639	 */
640	function _limit($sql, $limit, $offset)
641	{	
642		$sql .= "LIMIT ".$limit;
643	
644		if ($offset > 0)
645		{
646			$sql .= " OFFSET ".$offset;
647		}
648		
649		return $sql;
650	}
651
652	// --------------------------------------------------------------------
653
654	/**
655	 * Close DB Connection
656	 *
657	 * @access	public
658	 * @param	resource
659	 * @return	void
660	 */
661	function _close($conn_id)
662	{
663		@mysqli_close($conn_id);
664	}
665
666
667}
668
669
670/* End of file mysqli_driver.php */
671/* Location: ./system/database/drivers/mysqli/mysqli_driver.php */