AbstractAdapter.php 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884
  1. <?php
  2. /**
  3. *
  4. * Ported from Zend Framework
  5. *
  6. * @copyright Copyright (c) 2005-2013 Zend Technologies USA Inc. (http://www.zend.com)
  7. * @license http://framework.zend.com/license/new-bsd New BSD License
  8. */
  9. namespace Cube\Db\Adapter;
  10. use Cube\Db,
  11. Cube\Db\Select,
  12. Cube\Config\AbstractConfig,
  13. Cube\Debug;
  14. abstract class AbstractAdapter
  15. {
  16. /**
  17. * User-provided configuration
  18. *
  19. * @var array
  20. */
  21. protected $_config = array();
  22. /**
  23. * Fetch mode
  24. *
  25. * @var integer
  26. */
  27. protected $_fetchMode = Db::FETCH_ASSOC;
  28. /**
  29. * Database connection
  30. *
  31. * @var object|resource|null
  32. */
  33. protected $_connection = null;
  34. /**
  35. * Keys are UPPERCASE SQL data types or the constants
  36. * \Cube\Db::INT_TYPE, \Cube\Db::FLOAT_TYPE.
  37. *
  38. * Values are:
  39. * 0 = 32-bit integer
  40. * 1 = float or decimal
  41. *
  42. * @var array Associative array of data types to values 0 or 1
  43. */
  44. protected $_numericDataTypes = array(
  45. Db::INT_TYPE => Db::INT_TYPE,
  46. Db::FLOAT_TYPE => Db::FLOAT_TYPE,
  47. );
  48. /**
  49. * Constructor.
  50. *
  51. * $config is an array of key/value pairs or an instance of \Cube\ConfigAbstract
  52. * containing configuration options. These options are common to most adapters:
  53. *
  54. * dbname => (string) The name of the database to user
  55. * username => (string) Connect to the database as this username.
  56. * password => (string) Password associated with the username.
  57. * host => (string) What host to connect to, defaults to localhost
  58. *
  59. * @param array|\Cube\Config\AbstractConfig $config An array or instance of \Cube\ConfigAbstract having configuration data
  60. *
  61. * @throws \RuntimeException
  62. */
  63. public function __construct($config)
  64. {
  65. /*
  66. * Verify that adapter parameters are in an array.
  67. */
  68. if (!is_array($config)) {
  69. if ($config instanceof AbstractConfig) {
  70. $config = $config->getData();
  71. }
  72. else {
  73. throw new \RuntimeException('Adapter parameters must be in an array or a \Cube\ConfigAbstract object');
  74. }
  75. }
  76. $this->_checkRequiredOptions($config);
  77. if (!isset($config['charset'])) {
  78. $config['charset'] = null;
  79. }
  80. $this->_config = array_merge($this->_config, $config);
  81. }
  82. /**
  83. *
  84. * Check for config options that are mandatory.
  85. * Throw exceptions if any are missing.
  86. *
  87. * @param array $config
  88. *
  89. * @throws \RuntimeException
  90. */
  91. protected function _checkRequiredOptions(array $config)
  92. {
  93. // we need at least a dbname
  94. if (!array_key_exists('dbname', $config)) {
  95. throw new \RuntimeException("Configuration array must have a key
  96. for 'dbname' that names the database instance");
  97. }
  98. if (!array_key_exists('password', $config)) {
  99. throw new \RuntimeException("Configuration array must have a key
  100. for 'password' for login credentials");
  101. }
  102. if (!array_key_exists('username', $config)) {
  103. throw new \RuntimeException("Configuration array must have a key
  104. for 'username' for login credentials");
  105. }
  106. }
  107. /**
  108. *
  109. * Returns the underlying database connection object or resource.
  110. * If not presently connected, this initiates the connection.
  111. *
  112. * @return object|resource|null
  113. */
  114. public function getConnection()
  115. {
  116. $this->_connect();
  117. return $this->_connection;
  118. }
  119. /**
  120. *
  121. * Returns the configuration variables in this adapter.
  122. *
  123. * @return array
  124. */
  125. public function getConfig()
  126. {
  127. return $this->_config;
  128. }
  129. /**
  130. *
  131. * Prepares and executes an SQL statement with bound data.
  132. *
  133. * @param mixed $sql the SQL statement with placeholders.
  134. * May be a string or \Cube\Db\Select
  135. * @param mixed $bind an array of data to bind to the placeholders.
  136. *
  137. * @return \Cube\Db\Statement\StatementInterface
  138. */
  139. public function query($sql, $bind = array())
  140. {
  141. $this->_connect();
  142. if ($sql instanceof Select) {
  143. if (empty($bind)) {
  144. $bind = $sql->getBind();
  145. }
  146. $sql = $sql->assemble();
  147. }
  148. if (!is_array($bind)) {
  149. $bind = array($bind);
  150. }
  151. // query profiler - start
  152. $debugCount = Debug::getSqlCount();
  153. Debug::addSqlQuery($sql, $debugCount);
  154. // prepare and execute the statement with profiling
  155. $stmt = $this->prepare($sql);
  156. $stmt->execute($bind);
  157. // query profiler - end
  158. Debug::addSqlQuery($sql, $debugCount);
  159. Debug::addSqlCount();
  160. $stmt->setFetchMode($this->_fetchMode);
  161. return $stmt;
  162. }
  163. /**
  164. *
  165. * leave autocommit mode and begin a transaction.
  166. *
  167. * @return \Cube\Db\Adapter\AbstractAdapter
  168. */
  169. public function beginTransaction()
  170. {
  171. $this->_connect();
  172. $this->_beginTransaction();
  173. return $this;
  174. }
  175. /**
  176. * Commit a transaction and return to autocommit mode.
  177. *
  178. * @return \Cube\Db\Adapter\AbstractAdapter
  179. */
  180. public function commit()
  181. {
  182. $this->_connect();
  183. $this->_commit();
  184. return $this;
  185. }
  186. /**
  187. * Roll back a transaction and return to autocommit mode.
  188. *
  189. * @return \Cube\Db\Adapter\AbstractAdapter
  190. */
  191. public function rollBack()
  192. {
  193. $this->_connect();
  194. $this->_rollBack();
  195. return $this;
  196. }
  197. /**
  198. * Inserts a table row with specified data.
  199. *
  200. * @param mixed $table The table to insert data into.
  201. * @param array $bind Column-value pairs.
  202. *
  203. * @return int The number of affected rows.
  204. * @throws \RuntimeException
  205. */
  206. public function insert($table, array $bind)
  207. {
  208. // extract and quote col names from the array keys
  209. $cols = array();
  210. $vals = array();
  211. $i = 0;
  212. foreach ($bind as $col => $val) {
  213. $cols[] = $this->quoteIdentifier($col, true);
  214. if ($val instanceof Db\Expr) {
  215. $vals[] = $val->__toString();
  216. unset($bind[$col]);
  217. }
  218. else {
  219. if ($this->supportsParameters('positional')) {
  220. $vals[] = '?';
  221. }
  222. else {
  223. if ($this->supportsParameters('named')) {
  224. unset($bind[$col]);
  225. $bind[':col' . $i] = $val;
  226. $vals[] = ':col' . $i;
  227. $i++;
  228. }
  229. else {
  230. throw new \RuntimeException(
  231. sprintf("%s doesn't support positional or named binding", get_class($this)));
  232. }
  233. }
  234. }
  235. }
  236. // build the statement
  237. $sql = "INSERT INTO "
  238. . $this->quoteIdentifier($table, true)
  239. . ' (' . implode(', ', $cols) . ') '
  240. . 'VALUES (' . implode(', ', $vals) . ')';
  241. // execute the statement and return the number of affected rows
  242. if ($this->supportsParameters('positional')) {
  243. $bind = array_values($bind);
  244. }
  245. $stmt = $this->query($sql, $bind);
  246. $result = $stmt->rowCount();
  247. return $result;
  248. }
  249. /**
  250. *
  251. * Updates table rows with specified data based on a WHERE clause.
  252. *
  253. * @param mixed $table The table to update.
  254. * @param array $bind Column-value pairs.
  255. * @param mixed $where UPDATE WHERE clause(s).
  256. *
  257. * @return int The number of affected rows.
  258. * @throws \RuntimeException
  259. */
  260. public function update($table, array $bind, $where = '')
  261. {
  262. /**
  263. * Build "col = ?" pairs for the statement,
  264. * except for \Cube\Db\Expr which is treated literally.
  265. */
  266. $set = array();
  267. $i = 0;
  268. foreach ($bind as $col => $val) {
  269. if ($val instanceof Db\Expr) {
  270. $val = $val->__toString();
  271. unset($bind[$col]);
  272. }
  273. else {
  274. if ($this->supportsParameters('positional')) {
  275. $val = '?';
  276. }
  277. else {
  278. if ($this->supportsParameters('named')) {
  279. unset($bind[$col]);
  280. $bind[':col' . $i] = $val;
  281. $val = ':col' . $i;
  282. $i++;
  283. }
  284. else {
  285. throw new \RuntimeException(
  286. sprintf("%s doesn't support positional or named binding", get_class($this)));
  287. }
  288. }
  289. }
  290. $set[] = $this->quoteIdentifier($col, true) . ' = ' . $val;
  291. }
  292. $where = $this->_whereExpr($where);
  293. /**
  294. * Build the UPDATE statement
  295. */
  296. $sql = "UPDATE "
  297. . $this->quoteIdentifier($table, true)
  298. . ' SET ' . implode(', ', $set)
  299. . (($where) ? " WHERE $where" : '');
  300. /**
  301. * Execute the statement and return the number of affected rows
  302. */
  303. if ($this->supportsParameters('positional')) {
  304. $stmt = $this->query($sql, array_values($bind));
  305. }
  306. else {
  307. $stmt = $this->query($sql, $bind);
  308. }
  309. $result = $stmt->rowCount();
  310. return $result;
  311. }
  312. /**
  313. *
  314. * Deletes table rows based on a WHERE clause.
  315. *
  316. * @param mixed $table The table to update.
  317. * @param mixed $where DELETE WHERE clause(s).
  318. *
  319. * @return int The number of affected rows.
  320. */
  321. public function delete($table, $where = '')
  322. {
  323. $where = $this->_whereExpr($where);
  324. /**
  325. * Build the DELETE statement
  326. */
  327. $sql = "DELETE FROM "
  328. . $this->quoteIdentifier($table, true)
  329. . (($where) ? " WHERE $where" : '');
  330. /**
  331. * Execute the statement and return the number of affected rows
  332. */
  333. $stmt = $this->query($sql);
  334. $result = $stmt->rowCount();
  335. return $result;
  336. }
  337. /**
  338. *
  339. * Convert an array, string, or \Cube\Db\Expr object
  340. * into a string to put in a WHERE clause.
  341. *
  342. * @param mixed $where
  343. *
  344. * @return string
  345. */
  346. protected function _whereExpr($where)
  347. {
  348. if (empty($where)) {
  349. return $where;
  350. }
  351. if (!is_array($where)) {
  352. $where = array($where);
  353. }
  354. foreach ($where as $cond => &$term) {
  355. // is $cond an int? (i.e. Not a condition)
  356. if (is_int($cond)) {
  357. // $term is the full condition
  358. if ($term instanceof Db\Expr) {
  359. $term = $term->__toString();
  360. }
  361. }
  362. else {
  363. // $cond is the condition with placeholder,
  364. // and $term is quoted into the condition
  365. $term = $this->quoteInto($cond, $term);
  366. }
  367. $term = '(' . $term . ')';
  368. }
  369. $where = implode(' AND ', $where);
  370. return $where;
  371. }
  372. /**
  373. * Creates and returns a new \Cube\Db\Select object for this adapter.
  374. *
  375. * @return \Cube\Db\Select
  376. */
  377. public function select()
  378. {
  379. return new Select($this);
  380. }
  381. /**
  382. * Get the fetch mode.
  383. *
  384. * @return int
  385. */
  386. public function getFetchMode()
  387. {
  388. return $this->_fetchMode;
  389. }
  390. /**
  391. *
  392. * Fetches all SQL result rows as a sequential array.
  393. * Uses the current fetchMode for the adapter.
  394. *
  395. * @param string|\Cube\Db\Select $sql An SQL SELECT statement.
  396. * @param mixed $bind Data to bind into SELECT placeholders.
  397. * @param mixed $fetchMode Override current fetch mode.
  398. *
  399. * @return array
  400. */
  401. public function fetchAll($sql, $bind = array(), $fetchMode = null)
  402. {
  403. if ($fetchMode === null) {
  404. $fetchMode = $this->_fetchMode;
  405. }
  406. $stmt = $this->query($sql, $bind);
  407. $result = $stmt->fetchAll($fetchMode);
  408. return $result;
  409. }
  410. /**
  411. *
  412. * Fetches the first row of the SQL result.
  413. * Uses the current fetchMode for the adapter.
  414. *
  415. * @param string|\Cube\Db\Select $sql An SQL SELECT statement.
  416. * @param mixed $bind Data to bind into SELECT placeholders.
  417. * @param mixed $fetchMode Override current fetch mode.
  418. *
  419. * @return array
  420. */
  421. public function fetchRow($sql, $bind = array(), $fetchMode = null)
  422. {
  423. if ($fetchMode === null) {
  424. $fetchMode = $this->_fetchMode;
  425. }
  426. $stmt = $this->query($sql, $bind);
  427. $result = $stmt->fetch($fetchMode);
  428. return $result;
  429. }
  430. /**
  431. * Fetches the first column of the first row of the SQL result.
  432. *
  433. * @param string|\Cube\Db\Select $sql An SQL SELECT statement.
  434. * @param mixed $bind Data to bind into SELECT placeholders.
  435. *
  436. * @return string
  437. */
  438. public function fetchOne($sql, $bind = array())
  439. {
  440. $stmt = $this->query($sql, $bind);
  441. $result = $stmt->fetchColumn(0);
  442. return $result;
  443. }
  444. /**
  445. * Quote a raw string.
  446. *
  447. * @param string $value Raw string
  448. *
  449. * @return string Quoted string
  450. */
  451. protected function _quote($value)
  452. {
  453. if (is_int($value)) {
  454. return $value;
  455. }
  456. elseif (is_float($value)) {
  457. return sprintf('%F', $value);
  458. }
  459. return "'" . addcslashes($value, "\000\n\r\\'\"\032") . "'";
  460. }
  461. /**
  462. * Safely quotes a value for an SQL statement.
  463. *
  464. * If an array is passed as the value, the array values are quoted
  465. * and then returned as a comma-separated string.
  466. *
  467. * @param mixed $value The value to quote.
  468. * @param mixed $type OPTIONAL the SQL datatype name, or constant, or null.
  469. *
  470. * @return mixed An SQL-safe quoted value (or string of separated values).
  471. */
  472. public function quote($value, $type = null)
  473. {
  474. $this->_connect();
  475. if ($value instanceof Select) {
  476. return '(' . $value->assemble() . ')';
  477. }
  478. if ($value instanceof Db\Expr) {
  479. return $value->__toString();
  480. }
  481. if (is_array($value)) {
  482. foreach ($value as &$val) {
  483. $val = $this->quote($val, $type);
  484. }
  485. return implode(', ', $value);
  486. }
  487. if ($type !== null && array_key_exists($type = strtoupper($type), $this->_numericDataTypes)) {
  488. $quotedValue = '0';
  489. switch ($this->_numericDataTypes[$type]) {
  490. case Db::INT_TYPE: // 32-bit integer
  491. $quotedValue = (string)intval($value);
  492. break;
  493. case Db::FLOAT_TYPE: // float or decimal
  494. $quotedValue = sprintf('%F', $value);
  495. }
  496. return $quotedValue;
  497. }
  498. return $this->_quote($value);
  499. }
  500. /**
  501. * Quotes a value and places into a piece of text at a placeholder.
  502. *
  503. * The placeholder is a question-mark; all placeholders will be replaced
  504. * with the quoted value. For example:
  505. *
  506. * <code>
  507. * $text = "WHERE date < ?";
  508. * $date = "2005-01-02";
  509. * $safe = $sql->quoteInto($text, $date);
  510. * // $safe = "WHERE date < '2005-01-02'"
  511. * </code>
  512. *
  513. * @param string $text The text with a placeholder.
  514. * @param mixed $value The value to quote.
  515. * @param string $type OPTIONAL SQL datatype
  516. * @param integer $count OPTIONAL count of placeholders to replace
  517. *
  518. * @return string An SQL-safe quoted value placed into the original text.
  519. */
  520. public function quoteInto($text, $value, $type = null, $count = null)
  521. {
  522. if ($count === null) {
  523. return str_replace('?', $this->quote($value, $type), $text);
  524. }
  525. else {
  526. while ($count > 0) {
  527. if (strpos($text, '?') !== false) {
  528. $text = substr_replace($text, $this->quote($value, $type), strpos($text, '?'), 1);
  529. }
  530. --$count;
  531. }
  532. return $text;
  533. }
  534. }
  535. /**
  536. * Quotes an identifier.
  537. *
  538. * Accepts a string representing a qualified identifier. For Example:
  539. * <code>
  540. * $adapter->quoteIdentifier('myschema.mytable')
  541. * </code>
  542. * Returns: "myschema"."mytable"
  543. *
  544. * Or, an array of one or more identifiers that may form a qualified identifier:
  545. * <code>
  546. * $adapter->quoteIdentifier(array('myschema','my.table'))
  547. * </code>
  548. * Returns: "myschema"."my.table"
  549. *
  550. * The actual quote character surrounding the identifiers may vary depending on
  551. * the adapter.
  552. *
  553. * @param string|array|\Cube\Db\Expr $ident The identifier.
  554. * @param bool $auto
  555. *
  556. * @return string The quoted identifier.
  557. */
  558. public function quoteIdentifier($ident, $auto = false)
  559. {
  560. return $this->_quoteIdentifierAs($ident, null, $auto);
  561. }
  562. /**
  563. * Quote a column identifier and alias.
  564. *
  565. * @param string|array|\Cube\Db\Expr $ident The identifier or expression.
  566. * @param string $alias An alias for the column.
  567. * @param bool $auto
  568. *
  569. * @return string The quoted identifier and alias.
  570. */
  571. public function quoteColumnAs($ident, $alias, $auto = false)
  572. {
  573. return $this->_quoteIdentifierAs($ident, $alias, $auto);
  574. }
  575. /**
  576. * Quote a table identifier and alias.
  577. *
  578. * @param string|array|\Cube\Db\Expr $ident The identifier or expression.
  579. * @param string $alias An alias for the table.
  580. * @param bool $auto If true, heed the AUTO_QUOTE_IDENTIFIERS config option.
  581. *
  582. * @return string The quoted identifier and alias.
  583. */
  584. public function quoteTableAs($ident, $alias = null, $auto = false)
  585. {
  586. return $this->_quoteIdentifierAs($ident, $alias, $auto);
  587. }
  588. /**
  589. * Quote an identifier and an optional alias.
  590. *
  591. * @param string|array|\Cube\Db\Expr $ident The identifier or expression.
  592. * @param string $alias An optional alias.
  593. * @param bool $auto If true, heed the AUTO_QUOTE_IDENTIFIERS config option.
  594. * @param string $as The string to add between the identifier/expression and the alias.
  595. *
  596. * @return string The quoted identifier and alias.
  597. */
  598. protected function _quoteIdentifierAs($ident, $alias = null, $auto = false, $as = ' AS ')
  599. {
  600. if ($ident instanceof Db\Expr) {
  601. $quoted = $ident->__toString();
  602. }
  603. elseif ($ident instanceof Select) {
  604. $quoted = '(' . $ident->assemble() . ')';
  605. }
  606. else {
  607. if (is_string($ident)) {
  608. $ident = explode('.', $ident);
  609. }
  610. if (is_array($ident)) {
  611. $segments = array();
  612. foreach ($ident as $segment) {
  613. if ($segment instanceof Db\Expr) {
  614. $segments[] = $segment->__toString();
  615. }
  616. else {
  617. $segments[] = $this->_quoteIdentifier($segment, $auto);
  618. }
  619. }
  620. if ($alias !== null && end($ident) == $alias) {
  621. $alias = null;
  622. }
  623. $quoted = implode('.', $segments);
  624. }
  625. else {
  626. $quoted = $this->_quoteIdentifier($ident, $auto);
  627. }
  628. }
  629. if ($alias !== null) {
  630. $quoted .= $as . $this->_quoteIdentifier($alias, $auto);
  631. }
  632. return $quoted;
  633. }
  634. /**
  635. * Quote an identifier.
  636. *
  637. * @param string $value The identifier or expression.
  638. * @param bool $auto If true, heed the AUTO_QUOTE_IDENTIFIERS config option.
  639. *
  640. * @return string The quoted identifier and alias.
  641. */
  642. protected function _quoteIdentifier($value, $auto = false)
  643. {
  644. if ($auto === false) {
  645. $q = $this->getQuoteIdentifierSymbol();
  646. return ($q . str_replace("$q", "$q$q", $value) . $q);
  647. }
  648. return $value;
  649. }
  650. /**
  651. * Returns the symbol the adapter uses for delimited identifiers.
  652. *
  653. * @return string
  654. */
  655. public function getQuoteIdentifierSymbol()
  656. {
  657. return '"';
  658. }
  659. /**
  660. * Return the most recent value from the specified sequence in the database.
  661. * This is supported only on RDBMS brands that support sequences
  662. * (e.g. Oracle, PostgreSQL, DB2). Other RDBMS brands return null.
  663. *
  664. * @return string
  665. */
  666. public function lastSequenceId()
  667. {
  668. return null;
  669. }
  670. /**
  671. * Generate a new value from the specified sequence in the database, and return it.
  672. * This is supported only on RDBMS brands that support sequences
  673. * (e.g. Oracle, PostgreSQL, DB2). Other RDBMS brands return null.
  674. *
  675. * @return string
  676. */
  677. public function nextSequenceId()
  678. {
  679. return null;
  680. }
  681. /**
  682. * Returns the column descriptions for a table.
  683. *
  684. * The return value is an associative array keyed by the column name,
  685. * as returned by the RDBMS.
  686. *
  687. * The value of each array element is an associative array
  688. * with the following keys:
  689. *
  690. * TABLE_NAME => string;
  691. * COLUMN_NAME => string; column name
  692. * COLUMN_POSITION => number; ordinal position of column in table
  693. * DATA_TYPE => string; SQL datatype name of column
  694. * DEFAULT => string; default expression of column, null if none
  695. * NULLABLE => bool; true if column can have nulls
  696. * LENGTH => number; length of CHAR/VARCHAR
  697. * SCALE => number; scale of NUMERIC/DECIMAL
  698. * PRECISION => number; precision of NUMERIC/DECIMAL
  699. * UNSIGNED => bool; unsigned property of an integer type
  700. * PRIMARY => bool; true if column is part of the primary key
  701. * PRIMARY_POSITION => integer; position of column in primary key
  702. *
  703. * @param string $tableName
  704. *
  705. * @return array
  706. */
  707. abstract public function describeTable($tableName);
  708. /**
  709. * Creates a connection to the database.
  710. *
  711. * @return void
  712. */
  713. abstract protected function _connect();
  714. /**
  715. * Test if a connection is active
  716. *
  717. * @return bool
  718. */
  719. abstract public function isConnected();
  720. /**
  721. * Force the connection to close.
  722. *
  723. * @return void
  724. */
  725. abstract public function closeConnection();
  726. /**
  727. * Prepare a statement and return a PDOStatement-like object.
  728. *
  729. * @param string|\Cube\Db\Select $sql SQL query
  730. *
  731. * @return \Cube\Db\Statement\AbstractStatement|\PDOStatement
  732. */
  733. abstract public function prepare($sql);
  734. /**
  735. * Gets the last ID generated automatically by an IDENTITY/AUTOINCREMENT column.
  736. *
  737. * As a convention, on RDBMS brands that support sequences
  738. * (e.g. Oracle, PostgreSQL, DB2), this method forms the name of a sequence
  739. * from the arguments and returns the last id generated by that sequence.
  740. * On RDBMS brands that support IDENTITY/AUTOINCREMENT columns, this method
  741. * returns the last value generated for such a column, and the table name
  742. * argument is disregarded.
  743. *
  744. * @param string $tableName OPTIONAL Name of table.
  745. * @param string $primaryKey OPTIONAL Name of primary key column.
  746. *
  747. * @return string
  748. */
  749. abstract public function lastInsertId($tableName = null, $primaryKey = null);
  750. /**
  751. * Begin a transaction.
  752. */
  753. abstract protected function _beginTransaction();
  754. /**
  755. * Commit a transaction.
  756. */
  757. abstract protected function _commit();
  758. /**
  759. * Roll-back a transaction.
  760. */
  761. abstract protected function _rollBack();
  762. /**
  763. * Set the fetch mode.
  764. *
  765. * @param integer $mode
  766. *
  767. * @return void
  768. */
  769. abstract public function setFetchMode($mode);
  770. /**
  771. * Adds an adapter-specific LIMIT clause to the SELECT statement.
  772. *
  773. * @param mixed $sql
  774. * @param integer $count
  775. * @param integer $offset
  776. *
  777. * @return string
  778. */
  779. abstract public function limit($sql, $count, $offset = 0);
  780. /**
  781. * Check if the adapter supports real SQL parameters.
  782. *
  783. * @param string $type 'positional' or 'named'
  784. *
  785. * @return bool
  786. */
  787. abstract public function supportsParameters($type);
  788. }