Collection.php 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140
  1. <?php
  2. /**
  3. * PHP Version 5.4
  4. *
  5. * CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
  6. * Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
  7. *
  8. * Licensed under The MIT License
  9. * For full copyright and license information, please see the LICENSE.txt
  10. * Redistributions of files must retain the above copyright notice.
  11. *
  12. * @copyright Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
  13. * @link http://cakephp.org CakePHP(tm) Project
  14. * @since CakePHP(tm) v 3.0.0
  15. * @license MIT License (http://www.opensource.org/licenses/mit-license.php)
  16. */
  17. namespace Cake\Database\Schema;
  18. use Cake\Cache\Cache;
  19. use Cake\Database\Connection;
  20. use Cake\Database\Exception;
  21. use Cake\Database\Schema\Table;
  22. /**
  23. * Represents a database schema collection
  24. *
  25. * Used to access information about the tables,
  26. * and other data in a database.
  27. */
  28. class Collection {
  29. /**
  30. * Connection object
  31. *
  32. * @var Cake\Database\Connection
  33. */
  34. protected $_connection;
  35. /**
  36. * Schema dialect instance.
  37. *
  38. * @var Cake\Database\Schema\BaseSchema
  39. */
  40. protected $_dialect;
  41. /**
  42. * Constructor.
  43. *
  44. * @param Cake\Database\Connection $connection
  45. */
  46. public function __construct(Connection $connection) {
  47. $this->_connection = $connection;
  48. $this->_dialect = $connection->driver()->schemaDialect();
  49. }
  50. /**
  51. * Get the list of tables available in the current connection.
  52. *
  53. * @return array The list of tables in the connected database/schema.
  54. */
  55. public function listTables() {
  56. list($sql, $params) = $this->_dialect->listTablesSql($this->_connection->config());
  57. $result = [];
  58. $statement = $this->_connection->execute($sql, $params);
  59. while ($row = $statement->fetch()) {
  60. $result[] = $row[0];
  61. }
  62. $statement->closeCursor();
  63. return $result;
  64. }
  65. /**
  66. * Get the column metadata for a table.
  67. *
  68. * Caching will be applied if `cacheMetadata` key is present in the Connection
  69. * configuration options. Defaults to _cake_model_ when true.
  70. *
  71. * @param string $name The name of the table to describe.
  72. * @return Cake\Database\Schema\Table Object with column metadata.
  73. * @throws Cake\Database\Exception when table cannot be described.
  74. */
  75. public function describe($name) {
  76. $config = $this->_connection->config();
  77. if (!empty($config['cacheMetadata'])) {
  78. $cacheConfig = ($config['cacheMetadata'] === true) ? '_cake_model_' : $config['cacheMetadata'];
  79. $cacheKey = $this->_connection->configName() . '_' . $name;
  80. $cached = Cache::read($cacheKey, $cacheConfig);
  81. if ($cached !== false) {
  82. return $cached;
  83. }
  84. }
  85. list($sql, $params) = $this->_dialect->describeTableSql($name, $config);
  86. $statement = $this->_executeSql($sql, $params);
  87. if (count($statement) === 0) {
  88. throw new Exception(sprintf('Cannot describe %s. It has 0 columns.', $name));
  89. }
  90. $table = new Table($name);
  91. foreach ($statement->fetchAll('assoc') as $row) {
  92. $this->_dialect->convertFieldDescription($table, $row);
  93. }
  94. list($sql, $params) = $this->_dialect->describeIndexSql($name, $config);
  95. $statement = $this->_executeSql($sql, $params);
  96. foreach ($statement->fetchAll('assoc') as $row) {
  97. $this->_dialect->convertIndexDescription($table, $row);
  98. }
  99. list($sql, $params) = $this->_dialect->describeForeignKeySql($name, $config);
  100. $statement = $this->_executeSql($sql, $params);
  101. foreach ($statement->fetchAll('assoc') as $row) {
  102. $this->_dialect->convertForeignKeyDescription($table, $row);
  103. }
  104. $statement->closeCursor();
  105. if (!empty($config['cacheMetadata'])) {
  106. Cache::write($cacheKey, $table, $cacheConfig);
  107. }
  108. return $table;
  109. }
  110. /**
  111. * Helper method to run queries and convert Exceptions to the correct types.
  112. *
  113. * @param string $sql The sql to run.
  114. * @param array $params Parameters for the statement.
  115. * @return Cake\Database\Statement Prepared statement
  116. * @throws Cake\Database\Exception on query failure.
  117. */
  118. protected function _executeSql($sql, $params) {
  119. try {
  120. return $this->_connection->execute($sql, $params);
  121. } catch (\PDOException $e) {
  122. throw new Exception($e->getMessage(), 500, $e);
  123. }
  124. }
  125. }