/libraries/Zend/Db/Sql/Insert.php

https://github.com/kiranatama/sagalaya · PHP · 273 lines · 140 code · 32 blank · 101 comment · 16 complexity · 447358c08a87a069beb537ab4fc5ecc7 MD5 · raw file

  1. <?php
  2. /**
  3. * Zend Framework (http://framework.zend.com/)
  4. *
  5. * @link http://github.com/zendframework/zf2 for the canonical source repository
  6. * @copyright Copyright (c) 2005-2012 Zend Technologies USA Inc. (http://www.zend.com)
  7. * @license http://framework.zend.com/license/new-bsd New BSD License
  8. * @package Zend_Db
  9. */
  10. namespace Zend\Db\Sql;
  11. use Zend\Db\Adapter\Adapter;
  12. use Zend\Db\Adapter\Driver\StatementInterface;
  13. use Zend\Db\Adapter\ParameterContainer;
  14. use Zend\Db\Adapter\Platform\PlatformInterface;
  15. use Zend\Db\Adapter\Platform\Sql92;
  16. /**
  17. * @category Zend
  18. * @package Zend_Db
  19. * @subpackage Sql
  20. */
  21. class Insert extends AbstractSql implements SqlInterface, PreparableSqlInterface
  22. {
  23. /**#@+
  24. * Constants
  25. *
  26. * @const
  27. */
  28. const SPECIFICATION_INSERT = 'insert';
  29. const VALUES_MERGE = 'merge';
  30. const VALUES_SET = 'set';
  31. /**#@-*/
  32. /**
  33. * @var array Specification array
  34. */
  35. protected $specifications = array(
  36. self::SPECIFICATION_INSERT => 'INSERT INTO %1$s (%2$s) VALUES (%3$s)'
  37. );
  38. /**
  39. * @var string
  40. */
  41. protected $table = null;
  42. protected $columns = array();
  43. /**
  44. * @var array
  45. */
  46. protected $values = array();
  47. /**
  48. * Constructor
  49. *
  50. * @param null|string $table
  51. * @param null|string $schema
  52. * @return void
  53. */
  54. public function __construct($table = null)
  55. {
  56. if ($table) {
  57. $this->into($table);
  58. }
  59. }
  60. /**
  61. * Crete INTO clause
  62. *
  63. * @param string $table
  64. * @param null|string $databaseOrSchema
  65. * @return Insert
  66. */
  67. public function into($table)
  68. {
  69. $this->table = $table;
  70. return $this;
  71. }
  72. /**
  73. * Specify columns
  74. *
  75. * @param array $columns
  76. * @return Insert
  77. */
  78. public function columns(array $columns)
  79. {
  80. $this->columns = $columns;
  81. return $this;
  82. }
  83. /**
  84. * Specify values to insert
  85. *
  86. * @param array $values
  87. * @param string $flag one of VALUES_MERGE or VALUES_SET; defaults to VALUES_SET
  88. * @return Insert
  89. */
  90. public function values(array $values, $flag = self::VALUES_SET)
  91. {
  92. if ($values == null) {
  93. throw new \InvalidArgumentException('values() expects an array of values');
  94. }
  95. $keys = array_keys($values);
  96. $firstKey = current($keys);
  97. if (is_string($firstKey)) {
  98. $this->columns($keys);
  99. $values = array_values($values);
  100. } elseif (is_int($firstKey)) {
  101. $values = array_values($values);
  102. }
  103. if ($flag == self::VALUES_MERGE) {
  104. $this->values = array_merge($this->values, $values);
  105. } else {
  106. $this->values = $values;
  107. }
  108. return $this;
  109. }
  110. public function getRawState($key = null)
  111. {
  112. $rawState = array(
  113. 'table' => $this->table,
  114. 'columns' => $this->columns,
  115. 'values' => $this->values
  116. );
  117. return (isset($key) && array_key_exists($key, $rawState)) ? $rawState[$key] : $rawState;
  118. }
  119. /**
  120. * Prepare statement
  121. *
  122. * @param Adapter $adapter
  123. * @param StatementInterface $statement
  124. * @return void
  125. */
  126. public function prepareStatement(Adapter $adapter, StatementInterface $statement)
  127. {
  128. $driver = $adapter->getDriver();
  129. $platform = $adapter->getPlatform();
  130. $parameterContainer = $statement->getParameterContainer();
  131. if (!$parameterContainer instanceof ParameterContainer) {
  132. $parameterContainer = new ParameterContainer();
  133. $statement->setParameterContainer($parameterContainer);
  134. }
  135. $table = $platform->quoteIdentifier($this->table);
  136. $columns = array();
  137. $values = array();
  138. foreach ($this->columns as $cIndex => $column) {
  139. $columns[$cIndex] = $platform->quoteIdentifier($column);
  140. if ($this->values[$cIndex] instanceof Expression) {
  141. $exprData = $this->processExpression($this->values[$cIndex], $platform, $driver);
  142. $values[$cIndex] = $exprData['sql'];
  143. if (count($exprData['parameters']) > 0) {
  144. $parameterContainer->merge($exprData['parameters']);
  145. }
  146. } else {
  147. $values[$cIndex] = $driver->formatParameterName($column);
  148. $parameterContainer->offsetSet($column, $this->values[$cIndex]);
  149. }
  150. }
  151. $sql = sprintf(
  152. $this->specifications[self::SPECIFICATION_INSERT],
  153. $table,
  154. implode(', ', $columns),
  155. implode(', ', $values)
  156. );
  157. $statement->setSql($sql);
  158. }
  159. /**
  160. * Get SQL string for this statement
  161. *
  162. * @param null|PlatformInterface $adapterPlatform Defaults to Sql92 if none provided
  163. * @return string
  164. */
  165. public function getSqlString(PlatformInterface $adapterPlatform = null)
  166. {
  167. $adapterPlatform = ($adapterPlatform) ?: new Sql92;
  168. $table = $adapterPlatform->quoteIdentifier($this->table);
  169. $columns = array_map(array($adapterPlatform, 'quoteIdentifier'), $this->columns);
  170. $columns = implode(', ', $columns);
  171. $values = array();
  172. foreach ($this->values as $value) {
  173. if ($value instanceof Expression) {
  174. $exprData = $this->processExpression($value, $adapterPlatform);
  175. $values[] = $exprData['sql'];
  176. } else {
  177. $values[] = $adapterPlatform->quoteValue($value);
  178. }
  179. }
  180. $values = implode(', ', $values);
  181. return sprintf($this->specifications[self::SPECIFICATION_INSERT], $table, $columns, $values);
  182. }
  183. /**
  184. * Overloading: variable setting
  185. *
  186. * Proxies to values, using VALUES_MERGE strategy
  187. *
  188. * @param string $name
  189. * @param mixed $value
  190. * @return Insert
  191. */
  192. public function __set($name, $value)
  193. {
  194. $values = array($name => $value);
  195. $this->values($values, self::VALUES_MERGE);
  196. return $this;
  197. }
  198. /**
  199. * Overloading: variable unset
  200. *
  201. * Proxies to values and columns
  202. *
  203. * @param string $name
  204. * @return void
  205. */
  206. public function __unset($name)
  207. {
  208. if (($position = array_search($name, $this->columns)) === false) {
  209. throw new \InvalidArgumentException('The key ' . $name . ' was not found in this objects column list');
  210. }
  211. unset($this->columns[$position]);
  212. unset($this->values[$position]);
  213. }
  214. /**
  215. * Overloading: variable isset
  216. *
  217. * Proxies to columns; does a column of that name exist?
  218. *
  219. * @param string $name
  220. * @return bool
  221. */
  222. public function __isset($name)
  223. {
  224. return in_array($name, $this->columns);
  225. }
  226. /**
  227. * Overloading: variable retrieval
  228. *
  229. * Retrieves value by column name
  230. *
  231. * @param string $name
  232. * @return mixed
  233. */
  234. public function __get($name)
  235. {
  236. if (($position = array_search($name, $this->columns)) === false) {
  237. throw new \InvalidArgumentException('The key ' . $name . ' was not found in this objects column list');
  238. }
  239. return $this->values[$position];
  240. }
  241. }