Merge "resourceloader: Fix RLQ script to support IE8 quirk"
[mediawiki.git] / includes / db / DatabaseUtility.php
blob9a520ff98047958c5b358bab6b266c5ac7df942a
1 <?php
2 /**
3 * This file contains database-related utility classes.
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
18 * http://www.gnu.org/copyleft/gpl.html
20 * @file
21 * @ingroup Database
24 /**
25 * Utility class
26 * @ingroup Database
28 * This allows us to distinguish a blob from a normal string and an array of strings
30 class Blob {
31 /** @var string */
32 protected $mData;
34 function __construct( $data ) {
35 $this->mData = $data;
38 function fetch() {
39 return $this->mData;
43 /**
44 * Base for all database-specific classes representing information about database fields
45 * @ingroup Database
47 interface Field {
48 /**
49 * Field name
50 * @return string
52 function name();
54 /**
55 * Name of table this field belongs to
56 * @return string
58 function tableName();
60 /**
61 * Database type
62 * @return string
64 function type();
66 /**
67 * Whether this field can store NULL values
68 * @return bool
70 function isNullable();
73 /**
74 * Result wrapper for grabbing data queried by someone else
75 * @ingroup Database
77 class ResultWrapper implements Iterator {
78 /** @var resource */
79 public $result;
81 /** @var DatabaseBase */
82 protected $db;
84 /** @var int */
85 protected $pos = 0;
87 /** @var object|null */
88 protected $currentRow = null;
90 /**
91 * Create a new result object from a result resource and a Database object
93 * @param DatabaseBase $database
94 * @param resource|ResultWrapper $result
96 function __construct( $database, $result ) {
97 $this->db = $database;
99 if ( $result instanceof ResultWrapper ) {
100 $this->result = $result->result;
101 } else {
102 $this->result = $result;
107 * Get the number of rows in a result object
109 * @return int
111 function numRows() {
112 return $this->db->numRows( $this );
116 * Fetch the next row from the given result object, in object form.
117 * Fields can be retrieved with $row->fieldname, with fields acting like
118 * member variables.
120 * @return stdClass
121 * @throws DBUnexpectedError Thrown if the database returns an error
123 function fetchObject() {
124 return $this->db->fetchObject( $this );
128 * Fetch the next row from the given result object, in associative array
129 * form. Fields are retrieved with $row['fieldname'].
131 * @return array
132 * @throws DBUnexpectedError Thrown if the database returns an error
134 function fetchRow() {
135 return $this->db->fetchRow( $this );
139 * Free a result object
141 function free() {
142 $this->db->freeResult( $this );
143 unset( $this->result );
144 unset( $this->db );
148 * Change the position of the cursor in a result object.
149 * See mysql_data_seek()
151 * @param int $row
153 function seek( $row ) {
154 $this->db->dataSeek( $this, $row );
158 * ======= Iterator functions =======
159 * Note that using these in combination with the non-iterator functions
160 * above may cause rows to be skipped or repeated.
163 function rewind() {
164 if ( $this->numRows() ) {
165 $this->db->dataSeek( $this, 0 );
167 $this->pos = 0;
168 $this->currentRow = null;
172 * @return stdClass|array|bool
174 function current() {
175 if ( is_null( $this->currentRow ) ) {
176 $this->next();
179 return $this->currentRow;
183 * @return int
185 function key() {
186 return $this->pos;
190 * @return stdClass
192 function next() {
193 $this->pos++;
194 $this->currentRow = $this->fetchObject();
196 return $this->currentRow;
200 * @return bool
202 function valid() {
203 return $this->current() !== false;
208 * Overloads the relevant methods of the real ResultsWrapper so it
209 * doesn't go anywhere near an actual database.
211 class FakeResultWrapper extends ResultWrapper {
212 /** @var array */
213 public $result = array();
215 /** @var null And it's going to stay that way :D */
216 protected $db = null;
218 /** @var int */
219 protected $pos = 0;
221 /** @var array|stdClass|bool */
222 protected $currentRow = null;
224 function __construct( $array ) {
225 $this->result = $array;
229 * @return int
231 function numRows() {
232 return count( $this->result );
236 * @return array|bool
238 function fetchRow() {
239 if ( $this->pos < count( $this->result ) ) {
240 $this->currentRow = $this->result[$this->pos];
241 } else {
242 $this->currentRow = false;
244 $this->pos++;
245 if ( is_object( $this->currentRow ) ) {
246 return get_object_vars( $this->currentRow );
247 } else {
248 return $this->currentRow;
252 function seek( $row ) {
253 $this->pos = $row;
256 function free() {
260 * Callers want to be able to access fields with $this->fieldName
261 * @return bool|stdClass
263 function fetchObject() {
264 $this->fetchRow();
265 if ( $this->currentRow ) {
266 return (object)$this->currentRow;
267 } else {
268 return false;
272 function rewind() {
273 $this->pos = 0;
274 $this->currentRow = null;
278 * @return bool|stdClass
280 function next() {
281 return $this->fetchObject();
286 * Used by DatabaseBase::buildLike() to represent characters that have special
287 * meaning in SQL LIKE clauses and thus need no escaping. Don't instantiate it
288 * manually, use DatabaseBase::anyChar() and anyString() instead.
290 class LikeMatch {
291 /** @var string */
292 private $str;
295 * Store a string into a LikeMatch marker object.
297 * @param string $s
299 public function __construct( $s ) {
300 $this->str = $s;
304 * Return the original stored string.
306 * @return string
308 public function toString() {
309 return $this->str;
314 * An object representing a master or slave position in a replicated setup.
316 * The implementation details of this opaque type are up to the database subclass.
318 interface DBMasterPos {
320 * @return float UNIX timestamp
322 public function asOfTime();