Statement.php 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184
  1. <?php
  2. namespace Drupal\Core\Database;
  3. /**
  4. * Default implementation of StatementInterface.
  5. *
  6. * \PDO allows us to extend the \PDOStatement class to provide additional
  7. * functionality beyond that offered by default. We do need extra
  8. * functionality. By default, this class is not driver-specific. If a given
  9. * driver needs to set a custom statement class, it may do so in its
  10. * constructor.
  11. *
  12. * @see http://php.net/pdostatement
  13. */
  14. class Statement extends \PDOStatement implements StatementInterface {
  15. /**
  16. * Reference to the database connection object for this statement.
  17. *
  18. * The name $dbh is inherited from \PDOStatement.
  19. *
  20. * @var \Drupal\Core\Database\Connection
  21. */
  22. public $dbh;
  23. /**
  24. * Is rowCount() execution allowed.
  25. *
  26. * @var bool
  27. */
  28. public $allowRowCount = FALSE;
  29. protected function __construct(Connection $dbh) {
  30. $this->dbh = $dbh;
  31. $this->setFetchMode(\PDO::FETCH_OBJ);
  32. }
  33. /**
  34. * {@inheritdoc}
  35. */
  36. public function execute($args = [], $options = []) {
  37. if (isset($options['fetch'])) {
  38. if (is_string($options['fetch'])) {
  39. // \PDO::FETCH_PROPS_LATE tells __construct() to run before properties
  40. // are added to the object.
  41. $this->setFetchMode(\PDO::FETCH_CLASS | \PDO::FETCH_PROPS_LATE, $options['fetch']);
  42. }
  43. else {
  44. $this->setFetchMode($options['fetch']);
  45. }
  46. }
  47. $logger = $this->dbh->getLogger();
  48. if (!empty($logger)) {
  49. $query_start = microtime(TRUE);
  50. }
  51. $return = parent::execute($args);
  52. if (!empty($logger)) {
  53. $query_end = microtime(TRUE);
  54. $logger->log($this, $args, $query_end - $query_start);
  55. }
  56. return $return;
  57. }
  58. /**
  59. * {@inheritdoc}
  60. */
  61. public function getQueryString() {
  62. return $this->queryString;
  63. }
  64. /**
  65. * {@inheritdoc}
  66. */
  67. public function fetchCol($index = 0) {
  68. return $this->fetchAll(\PDO::FETCH_COLUMN, $index);
  69. }
  70. /**
  71. * {@inheritdoc}
  72. */
  73. public function fetchAllAssoc($key, $fetch = NULL) {
  74. $return = [];
  75. if (isset($fetch)) {
  76. if (is_string($fetch)) {
  77. $this->setFetchMode(\PDO::FETCH_CLASS, $fetch);
  78. }
  79. else {
  80. $this->setFetchMode($fetch);
  81. }
  82. }
  83. foreach ($this as $record) {
  84. $record_key = is_object($record) ? $record->$key : $record[$key];
  85. $return[$record_key] = $record;
  86. }
  87. return $return;
  88. }
  89. /**
  90. * {@inheritdoc}
  91. */
  92. public function fetchAllKeyed($key_index = 0, $value_index = 1) {
  93. $return = [];
  94. $this->setFetchMode(\PDO::FETCH_NUM);
  95. foreach ($this as $record) {
  96. $return[$record[$key_index]] = $record[$value_index];
  97. }
  98. return $return;
  99. }
  100. /**
  101. * {@inheritdoc}
  102. */
  103. public function fetchField($index = 0) {
  104. // Call \PDOStatement::fetchColumn to fetch the field.
  105. return $this->fetchColumn($index);
  106. }
  107. /**
  108. * {@inheritdoc}
  109. */
  110. public function fetchAssoc() {
  111. // Call \PDOStatement::fetch to fetch the row.
  112. return $this->fetch(\PDO::FETCH_ASSOC);
  113. }
  114. /**
  115. * {@inheritdoc}
  116. */
  117. public function rowCount() {
  118. // SELECT query should not use the method.
  119. if ($this->allowRowCount) {
  120. return parent::rowCount();
  121. }
  122. else {
  123. throw new RowCountException();
  124. }
  125. }
  126. /**
  127. * {@inheritdoc}
  128. */
  129. public function setFetchMode($mode, $a1 = NULL, $a2 = []) {
  130. // Call \PDOStatement::setFetchMode to set fetch mode.
  131. // \PDOStatement is picky about the number of arguments in some cases so we
  132. // need to be pass the exact number of arguments we where given.
  133. switch (func_num_args()) {
  134. case 1:
  135. return parent::setFetchMode($mode);
  136. case 2:
  137. return parent::setFetchMode($mode, $a1);
  138. case 3:
  139. default:
  140. return parent::setFetchMode($mode, $a1, $a2);
  141. }
  142. }
  143. /**
  144. * {@inheritdoc}
  145. */
  146. public function fetchAll($mode = NULL, $column_index = NULL, $constructor_arguments = NULL) {
  147. // Call \PDOStatement::fetchAll to fetch all rows.
  148. // \PDOStatement is picky about the number of arguments in some cases so we
  149. // need to be pass the exact number of arguments we where given.
  150. switch (func_num_args()) {
  151. case 0:
  152. return parent::fetchAll();
  153. case 1:
  154. return parent::fetchAll($mode);
  155. case 2:
  156. return parent::fetchAll($mode, $column_index);
  157. case 3:
  158. default:
  159. return parent::fetchAll($mode, $column_index, $constructor_arguments);
  160. }
  161. }
  162. }