PageRenderTime 61ms CodeModel.GetById 14ms RepoModel.GetById 0ms app.codeStats 1ms

/system/database/DB_active_rec.php

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