PageRenderTime 46ms CodeModel.GetById 12ms RepoModel.GetById 0ms app.codeStats 0ms

/system/database/DB_active_rec.php

https://bitbucket.org/siriusdely/codeigniter-reactor
PHP | 2073 lines | 1078 code | 327 blank | 668 comment | 192 complexity | 5c2d2ec63c517d17a7fa13ee148a3541 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 5.1.6 or newer
  6. *
  7. * @package CodeIgniter
  8. * @author ExpressionEngine Dev Team
  9. * @copyright Copyright (c) 2008 - 2011, 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. * Active Record Class
  18. *
  19. * This is the platform-independent base Active Record implementation class.
  20. *
  21. * @package CodeIgniter
  22. * @subpackage Drivers
  23. * @category Database
  24. * @author ExpressionEngine Dev Team
  25. * @link http://codeigniter.com/user_guide/database/
  26. */
  27. class CI_DB_active_record extends CI_DB_driver {
  28. var $ar_select = array();
  29. var $ar_distinct = FALSE;
  30. var $ar_from = array();
  31. var $ar_join = array();
  32. var $ar_where = array();
  33. var $ar_like = array();
  34. var $ar_groupby = array();
  35. var $ar_having = array();
  36. var $ar_keys = array();
  37. var $ar_limit = FALSE;
  38. var $ar_offset = FALSE;
  39. var $ar_order = FALSE;
  40. var $ar_orderby = array();
  41. var $ar_set = array();
  42. var $ar_wherein = array();
  43. var $ar_aliased_tables = array();
  44. var $ar_store_array = array();
  45. // Active Record Caching variables
  46. var $ar_caching = FALSE;
  47. var $ar_cache_exists = array();
  48. var $ar_cache_select = array();
  49. var $ar_cache_from = array();
  50. var $ar_cache_join = array();
  51. var $ar_cache_where = array();
  52. var $ar_cache_like = array();
  53. var $ar_cache_groupby = array();
  54. var $ar_cache_having = array();
  55. var $ar_cache_orderby = array();
  56. var $ar_cache_set = array();
  57. var $ar_no_escape = array();
  58. var $ar_cache_no_escape = array();
  59. // --------------------------------------------------------------------
  60. /**
  61. * Select
  62. *
  63. * Generates the SELECT portion of the query
  64. *
  65. * @access public
  66. * @param string
  67. * @return object
  68. */
  69. function select($select = '*', $escape = NULL)
  70. {
  71. if (is_string($select))
  72. {
  73. $select = explode(',', $select);
  74. }
  75. foreach ($select as $val)
  76. {
  77. $val = trim($val);
  78. if ($val != '')
  79. {
  80. $this->ar_select[] = $val;
  81. $this->ar_no_escape[] = $escape;
  82. if ($this->ar_caching === TRUE)
  83. {
  84. $this->ar_cache_select[] = $val;
  85. $this->ar_cache_exists[] = 'select';
  86. $this->ar_cache_no_escape[] = $escape;
  87. }
  88. }
  89. }
  90. return $this;
  91. }
  92. // --------------------------------------------------------------------
  93. /**
  94. * Select Max
  95. *
  96. * Generates a SELECT MAX(field) portion of a query
  97. *
  98. * @access public
  99. * @param string the field
  100. * @param string an alias
  101. * @return object
  102. */
  103. function select_max($select = '', $alias = '')
  104. {
  105. return $this->_max_min_avg_sum($select, $alias, 'MAX');
  106. }
  107. // --------------------------------------------------------------------
  108. /**
  109. * Select Min
  110. *
  111. * Generates a SELECT MIN(field) portion of a query
  112. *
  113. * @access public
  114. * @param string the field
  115. * @param string an alias
  116. * @return object
  117. */
  118. function select_min($select = '', $alias = '')
  119. {
  120. return $this->_max_min_avg_sum($select, $alias, 'MIN');
  121. }
  122. // --------------------------------------------------------------------
  123. /**
  124. * Select Average
  125. *
  126. * Generates a SELECT AVG(field) portion of a query
  127. *
  128. * @access public
  129. * @param string the field
  130. * @param string an alias
  131. * @return object
  132. */
  133. function select_avg($select = '', $alias = '')
  134. {
  135. return $this->_max_min_avg_sum($select, $alias, 'AVG');
  136. }
  137. // --------------------------------------------------------------------
  138. /**
  139. * Select Sum
  140. *
  141. * Generates a SELECT SUM(field) portion of a query
  142. *
  143. * @access public
  144. * @param string the field
  145. * @param string an alias
  146. * @return object
  147. */
  148. function select_sum($select = '', $alias = '')
  149. {
  150. return $this->_max_min_avg_sum($select, $alias, 'SUM');
  151. }
  152. // --------------------------------------------------------------------
  153. /**
  154. * Processing Function for the four functions above:
  155. *
  156. * select_max()
  157. * select_min()
  158. * select_avg()
  159. * select_sum()
  160. *
  161. * @access public
  162. * @param string the field
  163. * @param string an alias
  164. * @return object
  165. */
  166. function _max_min_avg_sum($select = '', $alias = '', $type = 'MAX')
  167. {
  168. if ( ! is_string($select) OR $select == '')
  169. {
  170. $this->display_error('db_invalid_query');
  171. }
  172. $type = strtoupper($type);
  173. if ( ! in_array($type, array('MAX', 'MIN', 'AVG', 'SUM')))
  174. {
  175. show_error('Invalid function type: '.$type);
  176. }
  177. if ($alias == '')
  178. {
  179. $alias = $this->_create_alias_from_table(trim($select));
  180. }
  181. $sql = $type.'('.$this->_protect_identifiers(trim($select)).') AS '.$alias;
  182. $this->ar_select[] = $sql;
  183. if ($this->ar_caching === TRUE)
  184. {
  185. $this->ar_cache_select[] = $sql;
  186. $this->ar_cache_exists[] = 'select';
  187. }
  188. return $this;
  189. }
  190. // --------------------------------------------------------------------
  191. /**
  192. * Determines the alias name based on the table
  193. *
  194. * @access private
  195. * @param string
  196. * @return string
  197. */
  198. function _create_alias_from_table($item)
  199. {
  200. if (strpos($item, '.') !== FALSE)
  201. {
  202. return end(explode('.', $item));
  203. }
  204. return $item;
  205. }
  206. // --------------------------------------------------------------------
  207. /**
  208. * DISTINCT
  209. *
  210. * Sets a flag which tells the query string compiler to add DISTINCT
  211. *
  212. * @access public
  213. * @param bool
  214. * @return object
  215. */
  216. function distinct($val = TRUE)
  217. {
  218. $this->ar_distinct = (is_bool($val)) ? $val : TRUE;
  219. return $this;
  220. }
  221. // --------------------------------------------------------------------
  222. /**
  223. * From
  224. *
  225. * Generates the FROM portion of the query
  226. *
  227. * @access public
  228. * @param mixed can be a string or array
  229. * @return object
  230. */
  231. function from($from)
  232. {
  233. foreach ((array)$from as $val)
  234. {
  235. if (strpos($val, ',') !== FALSE)
  236. {
  237. foreach (explode(',', $val) as $v)
  238. {
  239. $v = trim($v);
  240. $this->_track_aliases($v);
  241. $this->ar_from[] = $this->_protect_identifiers($v, TRUE, NULL, FALSE);
  242. if ($this->ar_caching === TRUE)
  243. {
  244. $this->ar_cache_from[] = $this->_protect_identifiers($v, TRUE, NULL, FALSE);
  245. $this->ar_cache_exists[] = 'from';
  246. }
  247. }
  248. }
  249. else
  250. {
  251. $val = trim($val);
  252. // Extract any aliases that might exist. We use this information
  253. // in the _protect_identifiers to know whether to add a table prefix
  254. $this->_track_aliases($val);
  255. $this->ar_from[] = $this->_protect_identifiers($val, TRUE, NULL, FALSE);
  256. if ($this->ar_caching === TRUE)
  257. {
  258. $this->ar_cache_from[] = $this->_protect_identifiers($val, TRUE, NULL, FALSE);
  259. $this->ar_cache_exists[] = 'from';
  260. }
  261. }
  262. }
  263. return $this;
  264. }
  265. // --------------------------------------------------------------------
  266. /**
  267. * Join
  268. *
  269. * Generates the JOIN portion of the query
  270. *
  271. * @access public
  272. * @param string
  273. * @param string the join condition
  274. * @param string the type of join
  275. * @return object
  276. */
  277. function join($table, $cond, $type = '')
  278. {
  279. if ($type != '')
  280. {
  281. $type = strtoupper(trim($type));
  282. if ( ! in_array($type, array('LEFT', 'RIGHT', 'OUTER', 'INNER', 'LEFT OUTER', 'RIGHT OUTER')))
  283. {
  284. $type = '';
  285. }
  286. else
  287. {
  288. $type .= ' ';
  289. }
  290. }
  291. // Extract any aliases that might exist. We use this information
  292. // in the _protect_identifiers to know whether to add a table prefix
  293. $this->_track_aliases($table);
  294. // Strip apart the condition and protect the identifiers
  295. if (preg_match('/([\w\.]+)([\W\s]+)(.+)/', $cond, $match))
  296. {
  297. $match[1] = $this->_protect_identifiers($match[1]);
  298. $match[3] = $this->_protect_identifiers($match[3]);
  299. $cond = $match[1].$match[2].$match[3];
  300. }
  301. // Assemble the JOIN statement
  302. $join = $type.'JOIN '.$this->_protect_identifiers($table, TRUE, NULL, FALSE).' ON '.$cond;
  303. $this->ar_join[] = $join;
  304. if ($this->ar_caching === TRUE)
  305. {
  306. $this->ar_cache_join[] = $join;
  307. $this->ar_cache_exists[] = 'join';
  308. }
  309. return $this;
  310. }
  311. // --------------------------------------------------------------------
  312. /**
  313. * Where
  314. *
  315. * Generates the WHERE portion of the query. Separates
  316. * multiple calls with AND
  317. *
  318. * @access public
  319. * @param mixed
  320. * @param mixed
  321. * @return object
  322. */
  323. function where($key, $value = NULL, $escape = TRUE)
  324. {
  325. return $this->_where($key, $value, 'AND ', $escape);
  326. }
  327. // --------------------------------------------------------------------
  328. /**
  329. * OR Where
  330. *
  331. * Generates the WHERE portion of the query. Separates
  332. * multiple calls with OR
  333. *
  334. * @access public
  335. * @param mixed
  336. * @param mixed
  337. * @return object
  338. */
  339. function or_where($key, $value = NULL, $escape = TRUE)
  340. {
  341. return $this->_where($key, $value, 'OR ', $escape);
  342. }
  343. // --------------------------------------------------------------------
  344. /**
  345. * Where
  346. *
  347. * Called by where() or orwhere()
  348. *
  349. * @access private
  350. * @param mixed
  351. * @param mixed
  352. * @param string
  353. * @return object
  354. */
  355. function _where($key, $value = NULL, $type = 'AND ', $escape = NULL)
  356. {
  357. if ( ! is_array($key))
  358. {
  359. $key = array($key => $value);
  360. }
  361. // If the escape value was not set will will base it on the global setting
  362. if ( ! is_bool($escape))
  363. {
  364. $escape = $this->_protect_identifiers;
  365. }
  366. foreach ($key as $k => $v)
  367. {
  368. $prefix = (count($this->ar_where) == 0 AND count($this->ar_cache_where) == 0) ? '' : $type;
  369. if (is_null($v) && ! $this->_has_operator($k))
  370. {
  371. // value appears not to have been set, assign the test to IS NULL
  372. $k .= ' IS NULL';
  373. }
  374. if ( ! is_null($v))
  375. {
  376. if ($escape === TRUE)
  377. {
  378. $k = $this->_protect_identifiers($k, FALSE, $escape);
  379. $v = ' '.$this->escape($v);
  380. }
  381. if ( ! $this->_has_operator($k))
  382. {
  383. $k .= ' = ';
  384. }
  385. }
  386. else
  387. {
  388. $k = $this->_protect_identifiers($k, FALSE, $escape);
  389. }
  390. $this->ar_where[] = $prefix.$k.$v;
  391. if ($this->ar_caching === TRUE)
  392. {
  393. $this->ar_cache_where[] = $prefix.$k.$v;
  394. $this->ar_cache_exists[] = 'where';
  395. }
  396. }
  397. return $this;
  398. }
  399. // --------------------------------------------------------------------
  400. /**
  401. * Where_in
  402. *
  403. * Generates a WHERE field IN ('item', 'item') SQL query joined with
  404. * AND if appropriate
  405. *
  406. * @access public
  407. * @param string The field to search
  408. * @param array The values searched on
  409. * @return object
  410. */
  411. function where_in($key = NULL, $values = NULL)
  412. {
  413. return $this->_where_in($key, $values);
  414. }
  415. // --------------------------------------------------------------------
  416. /**
  417. * Where_in_or
  418. *
  419. * Generates a WHERE field IN ('item', 'item') SQL query joined with
  420. * OR if appropriate
  421. *
  422. * @access public
  423. * @param string The field to search
  424. * @param array The values searched on
  425. * @return object
  426. */
  427. function or_where_in($key = NULL, $values = NULL)
  428. {
  429. return $this->_where_in($key, $values, FALSE, 'OR ');
  430. }
  431. // --------------------------------------------------------------------
  432. /**
  433. * Where_not_in
  434. *
  435. * Generates a WHERE field NOT IN ('item', 'item') SQL query joined
  436. * with AND if appropriate
  437. *
  438. * @access public
  439. * @param string The field to search
  440. * @param array The values searched on
  441. * @return object
  442. */
  443. function where_not_in($key = NULL, $values = NULL)
  444. {
  445. return $this->_where_in($key, $values, TRUE);
  446. }
  447. // --------------------------------------------------------------------
  448. /**
  449. * Where_not_in_or
  450. *
  451. * Generates a WHERE field NOT IN ('item', 'item') SQL query joined
  452. * with OR if appropriate
  453. *
  454. * @access public
  455. * @param string The field to search
  456. * @param array The values searched on
  457. * @return object
  458. */
  459. function or_where_not_in($key = NULL, $values = NULL)
  460. {
  461. return $this->_where_in($key, $values, TRUE, 'OR ');
  462. }
  463. // --------------------------------------------------------------------
  464. /**
  465. * Where_in
  466. *
  467. * Called by where_in, where_in_or, where_not_in, where_not_in_or
  468. *
  469. * @access public
  470. * @param string The field to search
  471. * @param array The values searched on
  472. * @param boolean If the statement would be IN or NOT IN
  473. * @param string
  474. * @return object
  475. */
  476. function _where_in($key = NULL, $values = NULL, $not = FALSE, $type = 'AND ')
  477. {
  478. if ($key === NULL OR $values === NULL)
  479. {
  480. return;
  481. }
  482. if ( ! is_array($values))
  483. {
  484. $values = array($values);
  485. }
  486. $not = ($not) ? ' NOT' : '';
  487. foreach ($values as $value)
  488. {
  489. $this->ar_wherein[] = $this->escape($value);
  490. }
  491. $prefix = (count($this->ar_where) == 0) ? '' : $type;
  492. $where_in = $prefix . $this->_protect_identifiers($key) . $not . " IN (" . implode(", ", $this->ar_wherein) . ") ";
  493. $this->ar_where[] = $where_in;
  494. if ($this->ar_caching === TRUE)
  495. {
  496. $this->ar_cache_where[] = $where_in;
  497. $this->ar_cache_exists[] = 'where';
  498. }
  499. // reset the array for multiple calls
  500. $this->ar_wherein = array();
  501. return $this;
  502. }
  503. // --------------------------------------------------------------------
  504. /**
  505. * Like
  506. *
  507. * Generates a %LIKE% portion of the query. Separates
  508. * multiple calls with AND
  509. *
  510. * @access public
  511. * @param mixed
  512. * @param mixed
  513. * @return object
  514. */
  515. function like($field, $match = '', $side = 'both')
  516. {
  517. return $this->_like($field, $match, 'AND ', $side);
  518. }
  519. // --------------------------------------------------------------------
  520. /**
  521. * Not Like
  522. *
  523. * Generates a NOT LIKE portion of the query. Separates
  524. * multiple calls with AND
  525. *
  526. * @access public
  527. * @param mixed
  528. * @param mixed
  529. * @return object
  530. */
  531. function not_like($field, $match = '', $side = 'both')
  532. {
  533. return $this->_like($field, $match, 'AND ', $side, 'NOT');
  534. }
  535. // --------------------------------------------------------------------
  536. /**
  537. * OR Like
  538. *
  539. * Generates a %LIKE% portion of the query. Separates
  540. * multiple calls with OR
  541. *
  542. * @access public
  543. * @param mixed
  544. * @param mixed
  545. * @return object
  546. */
  547. function or_like($field, $match = '', $side = 'both')
  548. {
  549. return $this->_like($field, $match, 'OR ', $side);
  550. }
  551. // --------------------------------------------------------------------
  552. /**
  553. * OR Not Like
  554. *
  555. * Generates a NOT LIKE portion of the query. Separates
  556. * multiple calls with OR
  557. *
  558. * @access public
  559. * @param mixed
  560. * @param mixed
  561. * @return object
  562. */
  563. function or_not_like($field, $match = '', $side = 'both')
  564. {
  565. return $this->_like($field, $match, 'OR ', $side, 'NOT');
  566. }
  567. // --------------------------------------------------------------------
  568. /**
  569. * Like
  570. *
  571. * Called by like() or orlike()
  572. *
  573. * @access private
  574. * @param mixed
  575. * @param mixed
  576. * @param string
  577. * @return object
  578. */
  579. function _like($field, $match = '', $type = 'AND ', $side = 'both', $not = '')
  580. {
  581. if ( ! is_array($field))
  582. {
  583. $field = array($field => $match);
  584. }
  585. foreach ($field as $k => $v)
  586. {
  587. $k = $this->_protect_identifiers($k);
  588. $prefix = (count($this->ar_like) == 0) ? '' : $type;
  589. $v = $this->escape_like_str($v);
  590. if ($side == 'before')
  591. {
  592. $like_statement = $prefix." $k $not LIKE '%{$v}'";
  593. }
  594. elseif ($side == 'after')
  595. {
  596. $like_statement = $prefix." $k $not LIKE '{$v}%'";
  597. }
  598. else
  599. {
  600. $like_statement = $prefix." $k $not LIKE '%{$v}%'";
  601. }
  602. // some platforms require an escape sequence definition for LIKE wildcards
  603. if ($this->_like_escape_str != '')
  604. {
  605. $like_statement = $like_statement.sprintf($this->_like_escape_str, $this->_like_escape_chr);
  606. }
  607. $this->ar_like[] = $like_statement;
  608. if ($this->ar_caching === TRUE)
  609. {
  610. $this->ar_cache_like[] = $like_statement;
  611. $this->ar_cache_exists[] = 'like';
  612. }
  613. }
  614. return $this;
  615. }
  616. // --------------------------------------------------------------------
  617. /**
  618. * GROUP BY
  619. *
  620. * @access public
  621. * @param string
  622. * @return object
  623. */
  624. function group_by($by)
  625. {
  626. if (is_string($by))
  627. {
  628. $by = explode(',', $by);
  629. }
  630. foreach ($by as $val)
  631. {
  632. $val = trim($val);
  633. if ($val != '')
  634. {
  635. $this->ar_groupby[] = $this->_protect_identifiers($val);
  636. if ($this->ar_caching === TRUE)
  637. {
  638. $this->ar_cache_groupby[] = $this->_protect_identifiers($val);
  639. $this->ar_cache_exists[] = 'groupby';
  640. }
  641. }
  642. }
  643. return $this;
  644. }
  645. // --------------------------------------------------------------------
  646. /**
  647. * Sets the HAVING value
  648. *
  649. * Separates multiple calls with AND
  650. *
  651. * @access public
  652. * @param string
  653. * @param string
  654. * @return object
  655. */
  656. function having($key, $value = '', $escape = TRUE)
  657. {
  658. return $this->_having($key, $value, 'AND ', $escape);
  659. }
  660. // --------------------------------------------------------------------
  661. /**
  662. * Sets the OR HAVING value
  663. *
  664. * Separates multiple calls with OR
  665. *
  666. * @access public
  667. * @param string
  668. * @param string
  669. * @return object
  670. */
  671. function or_having($key, $value = '', $escape = TRUE)
  672. {
  673. return $this->_having($key, $value, 'OR ', $escape);
  674. }
  675. // --------------------------------------------------------------------
  676. /**
  677. * Sets the HAVING values
  678. *
  679. * Called by having() or or_having()
  680. *
  681. * @access private
  682. * @param string
  683. * @param string
  684. * @return object
  685. */
  686. function _having($key, $value = '', $type = 'AND ', $escape = TRUE)
  687. {
  688. if ( ! is_array($key))
  689. {
  690. $key = array($key => $value);
  691. }
  692. foreach ($key as $k => $v)
  693. {
  694. $prefix = (count($this->ar_having) == 0) ? '' : $type;
  695. if ($escape === TRUE)
  696. {
  697. $k = $this->_protect_identifiers($k);
  698. }
  699. if ( ! $this->_has_operator($k))
  700. {
  701. $k .= ' = ';
  702. }
  703. if ($v != '')
  704. {
  705. $v = ' '.$this->escape_str($v);
  706. }
  707. $this->ar_having[] = $prefix.$k.$v;
  708. if ($this->ar_caching === TRUE)
  709. {
  710. $this->ar_cache_having[] = $prefix.$k.$v;
  711. $this->ar_cache_exists[] = 'having';
  712. }
  713. }
  714. return $this;
  715. }
  716. // --------------------------------------------------------------------
  717. /**
  718. * Sets the ORDER BY value
  719. *
  720. * @access public
  721. * @param string
  722. * @param string direction: asc or desc
  723. * @return object
  724. */
  725. function order_by($orderby, $direction = '')
  726. {
  727. if (strtolower($direction) == 'random')
  728. {
  729. $orderby = ''; // Random results want or don't need a field name
  730. $direction = $this->_random_keyword;
  731. }
  732. elseif (trim($direction) != '')
  733. {
  734. $direction = (in_array(strtoupper(trim($direction)), array('ASC', 'DESC'), TRUE)) ? ' '.$direction : ' ASC';
  735. }
  736. if (strpos($orderby, ',') !== FALSE)
  737. {
  738. $temp = array();
  739. foreach (explode(',', $orderby) as $part)
  740. {
  741. $part = trim($part);
  742. if ( ! in_array($part, $this->ar_aliased_tables))
  743. {
  744. $part = $this->_protect_identifiers(trim($part));
  745. }
  746. $temp[] = $part;
  747. }
  748. $orderby = implode(', ', $temp);
  749. }
  750. else if ($direction != $this->_random_keyword)
  751. {
  752. $orderby = $this->_protect_identifiers($orderby);
  753. }
  754. $orderby_statement = $orderby.$direction;
  755. $this->ar_orderby[] = $orderby_statement;
  756. if ($this->ar_caching === TRUE)
  757. {
  758. $this->ar_cache_orderby[] = $orderby_statement;
  759. $this->ar_cache_exists[] = 'orderby';
  760. }
  761. return $this;
  762. }
  763. // --------------------------------------------------------------------
  764. /**
  765. * Sets the LIMIT value
  766. *
  767. * @access public
  768. * @param integer the limit value
  769. * @param integer the offset value
  770. * @return object
  771. */
  772. function limit($value, $offset = '')
  773. {
  774. $this->ar_limit = $value;
  775. if ($offset != '')
  776. {
  777. $this->ar_offset = $offset;
  778. }
  779. return $this;
  780. }
  781. // --------------------------------------------------------------------
  782. /**
  783. * Sets the OFFSET value
  784. *
  785. * @access public
  786. * @param integer the offset value
  787. * @return object
  788. */
  789. function offset($offset)
  790. {
  791. $this->ar_offset = $offset;
  792. return $this;
  793. }
  794. // --------------------------------------------------------------------
  795. /**
  796. * The "set" function. Allows key/value pairs to be set for inserting or updating
  797. *
  798. * @access public
  799. * @param mixed
  800. * @param string
  801. * @param boolean
  802. * @return object
  803. */
  804. function set($key, $value = '', $escape = TRUE)
  805. {
  806. $key = $this->_object_to_array($key);
  807. if ( ! is_array($key))
  808. {
  809. $key = array($key => $value);
  810. }
  811. foreach ($key as $k => $v)
  812. {
  813. if ($escape === FALSE)
  814. {
  815. $this->ar_set[$this->_protect_identifiers($k)] = $v;
  816. }
  817. else
  818. {
  819. $this->ar_set[$this->_protect_identifiers($k, FALSE, TRUE)] = $this->escape($v);
  820. }
  821. }
  822. return $this;
  823. }
  824. // --------------------------------------------------------------------
  825. /**
  826. * Get
  827. *
  828. * Compiles the select statement based on the other functions called
  829. * and runs the query
  830. *
  831. * @access public
  832. * @param string the table
  833. * @param string the limit clause
  834. * @param string the offset clause
  835. * @return object
  836. */
  837. function get($table = '', $limit = null, $offset = null)
  838. {
  839. if ($table != '')
  840. {
  841. $this->_track_aliases($table);
  842. $this->from($table);
  843. }
  844. if ( ! is_null($limit))
  845. {
  846. $this->limit($limit, $offset);
  847. }
  848. $sql = $this->_compile_select();
  849. $result = $this->query($sql);
  850. $this->_reset_select();
  851. return $result;
  852. }
  853. /**
  854. * "Count All Results" query
  855. *
  856. * Generates a platform-specific query string that counts all records
  857. * returned by an Active Record query.
  858. *
  859. * @access public
  860. * @param string
  861. * @return string
  862. */
  863. function count_all_results($table = '')
  864. {
  865. if ($table != '')
  866. {
  867. $this->_track_aliases($table);
  868. $this->from($table);
  869. }
  870. $sql = $this->_compile_select($this->_count_string . $this->_protect_identifiers('numrows'));
  871. $query = $this->query($sql);
  872. $this->_reset_select();
  873. if ($query->num_rows() == 0)
  874. {
  875. return 0;
  876. }
  877. $row = $query->row();
  878. return (int) $row->numrows;
  879. }
  880. // --------------------------------------------------------------------
  881. /**
  882. * Get_Where
  883. *
  884. * Allows the where clause, limit and offset to be added directly
  885. *
  886. * @access public
  887. * @param string the where clause
  888. * @param string the limit clause
  889. * @param string the offset clause
  890. * @return object
  891. */
  892. function get_where($table = '', $where = null, $limit = null, $offset = null)
  893. {
  894. if ($table != '')
  895. {
  896. $this->from($table);
  897. }
  898. if ( ! is_null($where))
  899. {
  900. $this->where($where);
  901. }
  902. if ( ! is_null($limit))
  903. {
  904. $this->limit($limit, $offset);
  905. }
  906. $sql = $this->_compile_select();
  907. $result = $this->query($sql);
  908. $this->_reset_select();
  909. return $result;
  910. }
  911. // --------------------------------------------------------------------
  912. /**
  913. * Insert_Batch
  914. *
  915. * Compiles batch insert strings and runs the queries
  916. *
  917. * @access public
  918. * @param string the table to retrieve the results from
  919. * @param array an associative array of insert values
  920. * @return object
  921. */
  922. function insert_batch($table = '', $set = NULL)
  923. {
  924. if ( ! is_null($set))
  925. {
  926. $this->set_insert_batch($set);
  927. }
  928. if (count($this->ar_set) == 0)
  929. {
  930. if ($this->db_debug)
  931. {
  932. //No valid data array. Folds in cases where keys and values did not match up
  933. return $this->display_error('db_must_use_set');
  934. }
  935. return FALSE;
  936. }
  937. if ($table == '')
  938. {
  939. if ( ! isset($this->ar_from[0]))
  940. {
  941. if ($this->db_debug)
  942. {
  943. return $this->display_error('db_must_set_table');
  944. }
  945. return FALSE;
  946. }
  947. $table = $this->ar_from[0];
  948. }
  949. // Batch this baby
  950. for ($i = 0, $total = count($this->ar_set); $i < $total; $i = $i + 100)
  951. {
  952. $sql = $this->_insert_batch($this->_protect_identifiers($table, TRUE, NULL, FALSE), $this->ar_keys, array_slice($this->ar_set, $i, 100));
  953. //echo $sql;
  954. $this->query($sql);
  955. }
  956. $this->_reset_write();
  957. return TRUE;
  958. }
  959. // --------------------------------------------------------------------
  960. /**
  961. * The "set_insert_batch" function. Allows key/value pairs to be set for batch inserts
  962. *
  963. * @access public
  964. * @param mixed
  965. * @param string
  966. * @param boolean
  967. * @return object
  968. */
  969. function set_insert_batch($key, $value = '', $escape = TRUE)
  970. {
  971. $key = $this->_object_to_array_batch($key);
  972. if ( ! is_array($key))
  973. {
  974. $key = array($key => $value);
  975. }
  976. $keys = array_keys(current($key));
  977. sort($keys);
  978. foreach ($key as $row)
  979. {
  980. if (count(array_diff($keys, array_keys($row))) > 0 OR count(array_diff(array_keys($row), $keys)) > 0)
  981. {
  982. // batch function above returns an error on an empty array
  983. $this->ar_set[] = array();
  984. return;
  985. }
  986. ksort($row); // puts $row in the same order as our keys
  987. if ($escape === FALSE)
  988. {
  989. $this->ar_set[] = '('.implode(',', $row).')';
  990. }
  991. else
  992. {
  993. $clean = array();
  994. foreach ($row as $value)
  995. {
  996. $clean[] = $this->escape($value);
  997. }
  998. $this->ar_set[] = '('.implode(',', $clean).')';
  999. }
  1000. }
  1001. foreach ($keys as $k)
  1002. {
  1003. $this->ar_keys[] = $this->_protect_identifiers($k);
  1004. }
  1005. return $this;
  1006. }
  1007. // --------------------------------------------------------------------
  1008. /**
  1009. * Insert
  1010. *
  1011. * Compiles an insert string and runs the query
  1012. *
  1013. * @access public
  1014. * @param string the table to retrieve the results from
  1015. * @param array an associative array of insert values
  1016. * @return object
  1017. */
  1018. function insert($table = '', $set = NULL)
  1019. {
  1020. if ( ! is_null($set))
  1021. {
  1022. $this->set($set);
  1023. }
  1024. if (count($this->ar_set) == 0)
  1025. {
  1026. if ($this->db_debug)
  1027. {
  1028. return $this->display_error('db_must_use_set');
  1029. }
  1030. return FALSE;
  1031. }
  1032. if ($table == '')
  1033. {
  1034. if ( ! isset($this->ar_from[0]))
  1035. {
  1036. if ($this->db_debug)
  1037. {
  1038. return $this->display_error('db_must_set_table');
  1039. }
  1040. return FALSE;
  1041. }
  1042. $table = $this->ar_from[0];
  1043. }
  1044. $sql = $this->_insert($this->_protect_identifiers($table, TRUE, NULL, FALSE), array_keys($this->ar_set), array_values($this->ar_set));
  1045. $this->_reset_write();
  1046. return $this->query($sql);
  1047. }
  1048. function replace($table = '', $set = NULL)
  1049. {
  1050. if ( ! is_null($set))
  1051. {
  1052. $this->set($set);
  1053. }
  1054. if (count($this->ar_set) == 0)
  1055. {
  1056. if ($this->db_debug)
  1057. {
  1058. return $this->display_error('db_must_use_set');
  1059. }
  1060. return FALSE;
  1061. }
  1062. if ($table == '')
  1063. {
  1064. if ( ! isset($this->ar_from[0]))
  1065. {
  1066. if ($this->db_debug)
  1067. {
  1068. return $this->display_error('db_must_set_table');
  1069. }
  1070. return FALSE;
  1071. }
  1072. $table = $this->ar_from[0];
  1073. }
  1074. $sql = $this->_replace($this->_protect_identifiers($table, TRUE, NULL, FALSE), array_keys($this->ar_set), array_values($this->ar_set));
  1075. $this->_reset_write();
  1076. return $this->query($sql);
  1077. }
  1078. // --------------------------------------------------------------------
  1079. /**
  1080. * Update
  1081. *
  1082. * Compiles an update string and runs the query
  1083. *
  1084. * @access public
  1085. * @param string the table to retrieve the results from
  1086. * @param array an associative array of update values
  1087. * @param mixed the where clause
  1088. * @return object
  1089. */
  1090. function update($table = '', $set = NULL, $where = NULL, $limit = NULL)
  1091. {
  1092. // Combine any cached components with the current statements
  1093. $this->_merge_cache();
  1094. if ( ! is_null($set))
  1095. {
  1096. $this->set($set);
  1097. }
  1098. if (count($this->ar_set) == 0)
  1099. {
  1100. if ($this->db_debug)
  1101. {
  1102. return $this->display_error('db_must_use_set');
  1103. }
  1104. return FALSE;
  1105. }
  1106. if ($table == '')
  1107. {
  1108. if ( ! isset($this->ar_from[0]))
  1109. {
  1110. if ($this->db_debug)
  1111. {
  1112. return $this->display_error('db_must_set_table');
  1113. }
  1114. return FALSE;
  1115. }
  1116. $table = $this->ar_from[0];
  1117. }
  1118. if ($where != NULL)
  1119. {
  1120. $this->where($where);
  1121. }
  1122. if ($limit != NULL)
  1123. {
  1124. $this->limit($limit);
  1125. }
  1126. $sql = $this->_update($this->_protect_identifiers($table, TRUE, NULL, FALSE), $this->ar_set, $this->ar_where, $this->ar_orderby, $this->ar_limit);
  1127. $this->_reset_write();
  1128. return $this->query($sql);
  1129. }
  1130. // --------------------------------------------------------------------
  1131. /**
  1132. * Update_Batch
  1133. *
  1134. * Compiles an update string and runs the query
  1135. *
  1136. * @access public
  1137. * @param string the table to retrieve the results from
  1138. * @param array an associative array of update values
  1139. * @param string the where key
  1140. * @return object
  1141. */
  1142. function update_batch($table = '', $set = NULL, $index = NULL)
  1143. {
  1144. // Combine any cached components with the current statements
  1145. $this->_merge_cache();
  1146. if (is_null($index))
  1147. {
  1148. if ($this->db_debug)
  1149. {
  1150. return $this->display_error('db_myst_use_index');
  1151. }
  1152. return FALSE;
  1153. }
  1154. if ( ! is_null($set))
  1155. {
  1156. $this->set_update_batch($set, $index);
  1157. }
  1158. if (count($this->ar_set) == 0)
  1159. {
  1160. if ($this->db_debug)
  1161. {
  1162. return $this->display_error('db_must_use_set');
  1163. }
  1164. return FALSE;
  1165. }
  1166. if ($table == '')
  1167. {
  1168. if ( ! isset($this->ar_from[0]))
  1169. {
  1170. if ($this->db_debug)
  1171. {
  1172. return $this->display_error('db_must_set_table');
  1173. }
  1174. return FALSE;
  1175. }
  1176. $table = $this->ar_from[0];
  1177. }
  1178. // Batch this baby
  1179. for ($i = 0, $total = count($this->ar_set); $i < $total; $i = $i + 100)
  1180. {
  1181. $sql = $this->_update_batch($this->_protect_identifiers($table, TRUE, NULL, FALSE), array_slice($this->ar_set, $i, 100), $this->_protect_identifiers($index), $this->ar_where);
  1182. $this->query($sql);
  1183. }
  1184. $this->_reset_write();
  1185. }
  1186. // --------------------------------------------------------------------
  1187. /**
  1188. * The "set_update_batch" function. Allows key/value pairs to be set for batch updating
  1189. *
  1190. * @access public
  1191. * @param array
  1192. * @param string
  1193. * @param boolean
  1194. * @return object
  1195. */
  1196. function set_update_batch($key, $index = '', $escape = TRUE)
  1197. {
  1198. $key = $this->_object_to_array_batch($key);
  1199. if ( ! is_array($key))
  1200. {
  1201. // @todo error
  1202. }
  1203. foreach ($key as $k => $v)
  1204. {
  1205. $index_set = FALSE;
  1206. $clean = array();
  1207. foreach ($v as $k2 => $v2)
  1208. {
  1209. if ($k2 == $index)
  1210. {
  1211. $index_set = TRUE;
  1212. }
  1213. else
  1214. {
  1215. $not[] = $k.'-'.$v;
  1216. }
  1217. if ($escape === FALSE)
  1218. {
  1219. $clean[$this->_protect_identifiers($k2)] = $v2;
  1220. }
  1221. else
  1222. {
  1223. $clean[$this->_protect_identifiers($k2)] = $this->escape($v2);
  1224. }
  1225. }
  1226. if ($index_set == FALSE)
  1227. {
  1228. return $this->display_error('db_batch_missing_index');
  1229. }
  1230. $this->ar_set[] = $clean;
  1231. }
  1232. return $this;
  1233. }
  1234. // --------------------------------------------------------------------
  1235. /**
  1236. * Empty Table
  1237. *
  1238. * Compiles a delete string and runs "DELETE FROM table"
  1239. *
  1240. * @access public
  1241. * @param string the table to empty
  1242. * @return object
  1243. */
  1244. function empty_table($table = '')
  1245. {
  1246. if ($table == '')
  1247. {
  1248. if ( ! isset($this->ar_from[0]))
  1249. {
  1250. if ($this->db_debug)
  1251. {
  1252. return $this->display_error('db_must_set_table');
  1253. }
  1254. return FALSE;
  1255. }
  1256. $table = $this->ar_from[0];
  1257. }
  1258. else
  1259. {
  1260. $table = $this->_protect_identifiers($table, TRUE, NULL, FALSE);
  1261. }
  1262. $sql = $this->_delete($table);
  1263. $this->_reset_write();
  1264. return $this->query($sql);
  1265. }
  1266. // --------------------------------------------------------------------
  1267. /**
  1268. * Truncate
  1269. *
  1270. * Compiles a truncate string and runs the query
  1271. * If the database does not support the truncate() command
  1272. * This function maps to "DELETE FROM table"
  1273. *
  1274. * @access public
  1275. * @param string the table to truncate
  1276. * @return object
  1277. */
  1278. function truncate($table = '')
  1279. {
  1280. if ($table == '')
  1281. {
  1282. if ( ! isset($this->ar_from[0]))
  1283. {
  1284. if ($this->db_debug)
  1285. {
  1286. return $this->display_error('db_must_set_table');
  1287. }
  1288. return FALSE;
  1289. }
  1290. $table = $this->ar_from[0];
  1291. }
  1292. else
  1293. {
  1294. $table = $this->_protect_identifiers($table, TRUE, NULL, FALSE);
  1295. }
  1296. $sql = $this->_truncate($table);
  1297. $this->_reset_write();
  1298. return $this->query($sql);
  1299. }
  1300. // --------------------------------------------------------------------
  1301. /**
  1302. * Delete
  1303. *
  1304. * Compiles a delete string and runs the query
  1305. *
  1306. * @access public
  1307. * @param mixed the table(s) to delete from. String or array
  1308. * @param mixed the where clause
  1309. * @param mixed the limit clause
  1310. * @param boolean
  1311. * @return object
  1312. */
  1313. function delete($table = '', $where = '', $limit = NULL, $reset_data = TRUE)
  1314. {
  1315. // Combine any cached components with the current statements
  1316. $this->_merge_cache();
  1317. if ($table == '')
  1318. {
  1319. if ( ! isset($this->ar_from[0]))
  1320. {
  1321. if ($this->db_debug)
  1322. {
  1323. return $this->display_error('db_must_set_table');
  1324. }
  1325. return FALSE;
  1326. }
  1327. $table = $this->ar_from[0];
  1328. }
  1329. elseif (is_array($table))
  1330. {
  1331. foreach ($table as $single_table)
  1332. {
  1333. $this->delete($single_table, $where, $limit, FALSE);
  1334. }
  1335. $this->_reset_write();
  1336. return;
  1337. }
  1338. else
  1339. {
  1340. $table = $this->_protect_identifiers($table, TRUE, NULL, FALSE);
  1341. }
  1342. if ($where != '')
  1343. {
  1344. $this->where($where);
  1345. }
  1346. if ($limit != NULL)
  1347. {
  1348. $this->limit($limit);
  1349. }
  1350. if (count($this->ar_where) == 0 && count($this->ar_wherein) == 0 && count($this->ar_like) == 0)
  1351. {
  1352. if ($this->db_debug)
  1353. {
  1354. return $this->display_error('db_del_must_use_where');
  1355. }
  1356. return FALSE;
  1357. }
  1358. $sql = $this->_delete($table, $this->ar_where, $this->ar_like, $this->ar_limit);
  1359. if ($reset_data)
  1360. {
  1361. $this->_reset_write();
  1362. }
  1363. return $this->query($sql);
  1364. }
  1365. // --------------------------------------------------------------------
  1366. /**
  1367. * DB Prefix
  1368. *
  1369. * Prepends a database prefix if one exists in configuration
  1370. *
  1371. * @access public
  1372. * @param string the table
  1373. * @return string
  1374. */
  1375. function dbprefix($table = '')
  1376. {
  1377. if ($table == '')
  1378. {
  1379. $this->display_error('db_table_name_required');
  1380. }
  1381. return $this->dbprefix.$table;
  1382. }
  1383. // --------------------------------------------------------------------
  1384. /**
  1385. * Track Aliases
  1386. *
  1387. * Used to track SQL statements written with aliased tables.
  1388. *
  1389. * @access private
  1390. * @param string The table to inspect
  1391. * @return string
  1392. */
  1393. function _track_aliases($table)
  1394. {
  1395. if (is_array($table))
  1396. {
  1397. foreach ($table as $t)
  1398. {
  1399. $this->_track_aliases($t);
  1400. }
  1401. return;
  1402. }
  1403. // Does the string contain a comma? If so, we need to separate
  1404. // the string into discreet statements
  1405. if (strpos($table, ',') !== FALSE)
  1406. {
  1407. return $this->_track_aliases(explode(',', $table));
  1408. }
  1409. // if a table alias is used we can recognize it by a space
  1410. if (strpos($table, " ") !== FALSE)
  1411. {
  1412. // if the alias is written with the AS keyword, remove it
  1413. $table = preg_replace('/ AS /i', ' ', $table);
  1414. // Grab the alias
  1415. $table = trim(strrchr($table, " "));
  1416. // Store the alias, if it doesn't already exist
  1417. if ( ! in_array($table, $this->ar_aliased_tables))
  1418. {
  1419. $this->ar_aliased_tables[] = $table;
  1420. }
  1421. }
  1422. }
  1423. // --------------------------------------------------------------------
  1424. /**
  1425. * Compile the SELECT statement
  1426. *
  1427. * Generates a query string based on which functions were used.
  1428. * Should not be called directly. The get() function calls it.
  1429. *
  1430. * @access private
  1431. * @return string
  1432. */
  1433. function _compile_select($select_override = FALSE)
  1434. {
  1435. // Combine any cached components with the current statements
  1436. $this->_merge_cache();
  1437. // ----------------------------------------------------------------
  1438. // Write the "select" portion of the query
  1439. if ($select_override !== FALSE)
  1440. {
  1441. $sql = $select_override;
  1442. }
  1443. else
  1444. {
  1445. $sql = ( ! $this->ar_distinct) ? 'SELECT ' : 'SELECT DISTINCT ';
  1446. if (count($this->ar_select) == 0)
  1447. {
  1448. $sql .= '*';
  1449. }
  1450. else
  1451. {
  1452. // Cycle through the "select" portion of the query and prep each column name.
  1453. // The reason we protect identifiers here rather then in the select() function
  1454. // is because until the user calls the from() function we don't know if there are aliases
  1455. foreach ($this->ar_select as $key => $val)
  1456. {
  1457. $this->ar_select[$key] = $this->_protect_identifiers($val, FALSE, $this->ar_no_escape[$key]);
  1458. }
  1459. $sql .= implode(', ', $this->ar_select);
  1460. }
  1461. }
  1462. // ----------------------------------------------------------------
  1463. // Write the "FROM" portion of the query
  1464. if (count($this->ar_from) > 0)
  1465. {
  1466. $sql .= "\nFROM ";
  1467. $sql .= $this->_from_tables($this->ar_from);
  1468. }
  1469. // ----------------------------------------------------------------
  1470. // Write the "JOIN" portion of the query
  1471. if (count($this->ar_join) > 0)
  1472. {
  1473. $sql .= "\n";
  1474. $sql .= implode("\n", $this->ar_join);
  1475. }
  1476. // ----------------------------------------------------------------
  1477. // Write the "WHERE" portion of the query
  1478. if (count($this->ar_where) > 0 OR count($this->ar_like) > 0)
  1479. {
  1480. $sql .= "\nWHERE ";
  1481. }
  1482. $sql .= implode("\n", $this->ar_where);
  1483. // ----------------------------------------------------------------
  1484. // Write the "LIKE" portion of the query
  1485. if (count($this->ar_like) > 0)
  1486. {
  1487. if (count($this->ar_where) > 0)
  1488. {
  1489. $sql .= "\nAND ";
  1490. }
  1491. $sql .= implode("\n", $this->ar_like);
  1492. }
  1493. // ----------------------------------------------------------------
  1494. // Write the "GROUP BY" portion of the query
  1495. if (count($this->ar_groupby) > 0)
  1496. {
  1497. $sql .= "\nGROUP BY ";
  1498. $sql .= implode(', ', $this->ar_groupby);
  1499. }
  1500. // ----------------------------------------------------------------
  1501. // Write the "HAVING" portion of the query
  1502. if (count($this->ar_having) > 0)
  1503. {
  1504. $sql .= "\nHAVING ";
  1505. $sql .= implode("\n", $this->ar_having);
  1506. }
  1507. // ----------------------------------------------------------------
  1508. // Write the "ORDER BY" portion of the query
  1509. if (count($this->ar_orderby) > 0)
  1510. {
  1511. $sql .= "\nORDER BY ";
  1512. $sql .= implode(', ', $this->ar_orderby);
  1513. if ($this->ar_order !== FALSE)
  1514. {
  1515. $sql .= ($this->ar_order == 'desc') ? ' DESC' : ' ASC';
  1516. }
  1517. }
  1518. // ----------------------------------------------------------------
  1519. // Write the "LIMIT" portion of the query
  1520. if (is_numeric($this->ar_limit))
  1521. {
  1522. $sql .= "\n";
  1523. $sql = $this->_limit($sql, $this->ar_limit, $this->ar_offset);
  1524. }
  1525. return $sql;
  1526. }
  1527. // --------------------------------------------------------------------
  1528. /**
  1529. * Object to Array
  1530. *
  1531. * Takes an object as input and converts the class variables to array key/vals
  1532. *
  1533. * @access public
  1534. * @param object
  1535. * @return array
  1536. */
  1537. function _object_to_array($object)
  1538. {
  1539. if ( ! is_object($object))
  1540. {
  1541. return $object;
  1542. }
  1543. $array = array();
  1544. foreach (get_object_vars($object) as $key => $val)
  1545. {
  1546. // There are some built in keys we need to ignore for this conversion
  1547. if ( ! is_object($val) && ! is_array($val) && $key != '_parent_name')
  1548. {
  1549. $array[$key] = $val;
  1550. }
  1551. }
  1552. return $array;
  1553. }
  1554. // --------------------------------------------------------------------
  1555. /**
  1556. * Object to Array
  1557. *
  1558. * Takes an object as input and converts the class variables to array key/vals
  1559. *
  1560. * @access public
  1561. * @param object
  1562. * @return array
  1563. */
  1564. function _object_to_array_batch($object)
  1565. {
  1566. if ( ! is_object($object))
  1567. {
  1568. return $object;
  1569. }
  1570. $array = array();
  1571. $out = get_object_vars($object);
  1572. $fields = array_keys($out);
  1573. foreach ($fields as $val)
  1574. {
  1575. // There are some built in keys we need to ignore for this conversion
  1576. if ($val != '_parent_name')
  1577. {
  1578. $i = 0;
  1579. foreach ($out[$val] as $data)
  1580. {
  1581. $array[$i][$val] = $data;
  1582. $i++;
  1583. }
  1584. }
  1585. }
  1586. return $array;
  1587. }
  1588. // --------------------------------------------------------------------
  1589. /**
  1590. * Start Cache
  1591. *
  1592. * Starts AR caching
  1593. *
  1594. * @access public
  1595. * @return void
  1596. */
  1597. function start_cache()
  1598. {
  1599. $this->ar_caching = TRUE;
  1600. }
  1601. // --------------------------------------------------------------------
  1602. /**
  1603. * Stop Cache
  1604. *
  1605. * Stops AR caching
  1606. *
  1607. * @access public
  1608. * @return void
  1609. */
  1610. function stop_cache()
  1611. {
  1612. $this->ar_caching = FALSE;
  1613. }
  1614. // --------------------------------------------------------------------
  1615. /**
  1616. * Flush Cache
  1617. *
  1618. * Empties the AR cache
  1619. *
  1620. * @access public
  1621. * @return void
  1622. */
  1623. function flush_cache()
  1624. {
  1625. $this->_reset_run(
  1626. array(
  1627. 'ar_cache_select' => array(),
  1628. 'ar_cache_from' => array(),
  1629. 'ar_cache_join' => array(),
  1630. 'ar_cache_where' => array(),
  1631. 'ar_cache_like' => array(),
  1632. 'ar_cache_groupby' => array(),
  1633. 'ar_cache_having' => array(),
  1634. 'ar_cache_orderby' => array(),
  1635. 'ar_cache_set' => array(),
  1636. 'ar_cache_exists' => array(),
  1637. 'ar_cache_no_escape' => array()
  1638. )
  1639. );
  1640. }
  1641. // --------------------------------------------------------------------
  1642. /**
  1643. * Merge Cache
  1644. *
  1645. * When called, this function merges any cached AR arrays with
  1646. * locally called ones.
  1647. *
  1648. * @access private
  1649. * @return void
  1650. */
  1651. function _merge_cache()
  1652. {
  1653. if (count($this->ar_cache_exists) == 0)
  1654. {
  1655. return;
  1656. }
  1657. foreach ($this->ar_cache_exists as $val)
  1658. {
  1659. $ar_variable = 'ar_'.$val;
  1660. $ar_cache_var = 'ar_cache_'.$val;
  1661. if (count($this->$ar_cache_var) == 0)
  1662. {
  1663. continue;
  1664. }
  1665. $this->$ar_variable = array_unique(array_merge($this->$ar_cache_var, $this->$ar_variable));
  1666. }
  1667. // If we are "protecting identifiers" we need to examine the "from"
  1668. // portion of the query to determine if there are any aliases
  1669. if ($this->_protect_identifiers === TRUE AND count($this->ar_cache_from) > 0)
  1670. {
  1671. $this->_track_aliases($this->ar_from);
  1672. }
  1673. $this->ar_no_escape = $this->ar_cache_no_escape;
  1674. }
  1675. // --------------------------------------------------------------------
  1676. /**
  1677. * Resets the active record values. Called by the get() function
  1678. *
  1679. * @access private
  1680. * @param array An array of fields to reset
  1681. * @return void
  1682. */
  1683. function _reset_run($ar_reset_items)
  1684. {
  1685. foreach ($ar_reset_items as $item => $default_value)
  1686. {
  1687. if ( ! in_array($item, $this->ar_store_array))
  1688. {
  1689. $this->$item = $default_value;
  1690. }
  1691. }
  1692. }
  1693. // --------------------------------------------------------------------
  1694. /**
  1695. * Resets the active record values. Called by the get() function
  1696. *
  1697. * @access private
  1698. * @return void
  1699. */
  1700. function _reset_select()
  1701. {
  1702. $ar_reset_items = array(
  1703. 'ar_select' => array(),
  1704. 'ar_from' => array(),
  1705. 'ar_join' => array(),
  1706. 'ar_where' => array(),
  1707. 'ar_like' => array(),
  1708. 'ar_groupby' => array(),
  1709. 'ar_having' => array(),
  1710. 'ar_orderby' => array(),
  1711. 'ar_wherein' => array(),
  1712. 'ar_aliased_tables' => array(),
  1713. 'ar_no_escape' => array(),
  1714. 'ar_distinct' => FALSE,
  1715. 'ar_limit' => FALSE,
  1716. 'ar_offset' => FALSE,
  1717. 'ar_order' => FALSE,
  1718. );
  1719. $this->_reset_run($ar_reset_items);
  1720. }
  1721. // --------------------------------------------------------------------
  1722. /**
  1723. * Resets the active record "write" values.
  1724. *
  1725. * Called by the insert() update() insert_batch() update_batch() and delete() functions
  1726. *
  1727. * @access private
  1728. * @return void
  1729. */
  1730. function _reset_write()
  1731. {
  1732. $ar_reset_items = array(
  1733. 'ar_set' => array(),
  1734. 'ar_from' => array(),
  1735. 'ar_where' => array(),
  1736. 'ar_like' => array(),
  1737. 'ar_orderby' => array(),
  1738. 'ar_keys' => array(),
  1739. 'ar_limit' => FALSE,
  1740. 'ar_order' => FALSE
  1741. );
  1742. $this->_reset_run($ar_reset_items);
  1743. }
  1744. }
  1745. /* End of file DB_active_rec.php */
  1746. /* Location: ./system/database/DB_active_rec.php */