Completed
Branch master (098997)
by
unknown
28:44
created

DBConnRef::getSlavePos()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 2
nc 1
nop 0
dl 0
loc 3
rs 10
c 0
b 0
f 0
1
<?php
2
/**
3
 * Helper class to handle automatically marking connections as reusable (via RAII pattern)
4
 * as well handling deferring the actual network connection until the handle is used
5
 *
6
 * @note: proxy methods are defined explicity to avoid interface errors
7
 * @ingroup Database
8
 * @since 1.22
9
 */
10
class DBConnRef implements IDatabase {
11
	/** @var ILoadBalancer */
12
	private $lb;
13
14
	/** @var IDatabase|null Live connection handle */
15
	private $conn;
16
17
	/** @var array|null N-tuple of (server index, group, DatabaseDomain|string) */
18
	private $params;
19
20
	const FLD_INDEX = 0;
21
	const FLD_GROUP = 1;
22
	const FLD_DOMAIN = 2;
23
24
	/**
25
	 * @param ILoadBalancer $lb
26
	 * @param IDatabase|array $conn Connection or (server index, group, DatabaseDomain|string)
27
	 */
28
	public function __construct( ILoadBalancer $lb, $conn ) {
29
		$this->lb = $lb;
30
		if ( $conn instanceof IDatabase ) {
31
			$this->conn = $conn; // live handle
32
		} elseif ( count( $conn ) >= 3 && $conn[self::FLD_DOMAIN] !== false ) {
33
			$this->params = $conn;
34
		} else {
35
			throw new InvalidArgumentException( "Missing lazy connection arguments." );
36
		}
37
	}
38
39
	function __call( $name, array $arguments ) {
40
		if ( $this->conn === null ) {
41
			list( $db, $groups, $wiki ) = $this->params;
42
			$this->conn = $this->lb->getConnection( $db, $groups, $wiki );
43
		}
44
45
		return call_user_func_array( [ $this->conn, $name ], $arguments );
46
	}
47
48
	public function getServerInfo() {
49
		return $this->__call( __FUNCTION__, func_get_args() );
50
	}
51
52
	public function bufferResults( $buffer = null ) {
53
		return $this->__call( __FUNCTION__, func_get_args() );
54
	}
55
56
	public function trxLevel() {
57
		return $this->__call( __FUNCTION__, func_get_args() );
58
	}
59
60
	public function trxTimestamp() {
61
		return $this->__call( __FUNCTION__, func_get_args() );
62
	}
63
64
	public function explicitTrxActive() {
65
		return $this->__call( __FUNCTION__, func_get_args() );
66
	}
67
68
	public function tablePrefix( $prefix = null ) {
69
		return $this->__call( __FUNCTION__, func_get_args() );
70
	}
71
72
	public function dbSchema( $schema = null ) {
73
		return $this->__call( __FUNCTION__, func_get_args() );
74
	}
75
76
	public function getLBInfo( $name = null ) {
77
		return $this->__call( __FUNCTION__, func_get_args() );
78
	}
79
80
	public function setLBInfo( $name, $value = null ) {
81
		return $this->__call( __FUNCTION__, func_get_args() );
82
	}
83
84
	public function setLazyMasterHandle( IDatabase $conn ) {
85
		return $this->__call( __FUNCTION__, func_get_args() );
86
	}
87
88
	public function implicitGroupby() {
89
		return $this->__call( __FUNCTION__, func_get_args() );
90
	}
91
92
	public function implicitOrderby() {
93
		return $this->__call( __FUNCTION__, func_get_args() );
94
	}
95
96
	public function lastQuery() {
97
		return $this->__call( __FUNCTION__, func_get_args() );
98
	}
99
100
	public function doneWrites() {
101
		return $this->__call( __FUNCTION__, func_get_args() );
102
	}
103
104
	public function lastDoneWrites() {
105
		return $this->__call( __FUNCTION__, func_get_args() );
106
	}
107
108
	public function writesPending() {
109
		return $this->__call( __FUNCTION__, func_get_args() );
110
	}
111
112
	public function writesOrCallbacksPending() {
113
		return $this->__call( __FUNCTION__, func_get_args() );
114
	}
115
116
	public function pendingWriteQueryDuration( $type = self::ESTIMATE_TOTAL ) {
117
		return $this->__call( __FUNCTION__, func_get_args() );
118
	}
119
120
	public function pendingWriteCallers() {
121
		return $this->__call( __FUNCTION__, func_get_args() );
122
	}
123
124
	public function isOpen() {
125
		return $this->__call( __FUNCTION__, func_get_args() );
126
	}
127
128
	public function setFlag( $flag, $remember = self::REMEMBER_NOTHING ) {
129
		return $this->__call( __FUNCTION__, func_get_args() );
130
	}
131
132
	public function clearFlag( $flag, $remember = self::REMEMBER_NOTHING ) {
133
		return $this->__call( __FUNCTION__, func_get_args() );
134
	}
135
136
	public function restoreFlags( $state = self::RESTORE_PRIOR ) {
137
		return $this->__call( __FUNCTION__, func_get_args() );
138
	}
139
140
	public function getFlag( $flag ) {
141
		return $this->__call( __FUNCTION__, func_get_args() );
142
	}
143
144
	public function getProperty( $name ) {
145
		return $this->__call( __FUNCTION__, func_get_args() );
146
	}
147
148
	public function getDomainID() {
149
		if ( $this->conn === null ) {
150
			$domain = $this->params[self::FLD_DOMAIN];
151
			// Avoid triggering a database connection
152
			return $domain instanceof DatabaseDomain ? $domain->getId() : $domain;
153
		}
154
155
		return $this->__call( __FUNCTION__, func_get_args() );
156
	}
157
158
	public function getWikiID() {
159
		return $this->getDomainID();
160
	}
161
162
	public function getType() {
163
		return $this->__call( __FUNCTION__, func_get_args() );
164
	}
165
166
	public function open( $server, $user, $password, $dbName ) {
167
		return $this->__call( __FUNCTION__, func_get_args() );
168
	}
169
170
	public function fetchObject( $res ) {
171
		return $this->__call( __FUNCTION__, func_get_args() );
172
	}
173
174
	public function fetchRow( $res ) {
175
		return $this->__call( __FUNCTION__, func_get_args() );
176
	}
177
178
	public function numRows( $res ) {
179
		return $this->__call( __FUNCTION__, func_get_args() );
180
	}
181
182
	public function numFields( $res ) {
183
		return $this->__call( __FUNCTION__, func_get_args() );
184
	}
185
186
	public function fieldName( $res, $n ) {
187
		return $this->__call( __FUNCTION__, func_get_args() );
188
	}
189
190
	public function insertId() {
191
		return $this->__call( __FUNCTION__, func_get_args() );
192
	}
193
194
	public function dataSeek( $res, $row ) {
195
		return $this->__call( __FUNCTION__, func_get_args() );
196
	}
197
198
	public function lastErrno() {
199
		return $this->__call( __FUNCTION__, func_get_args() );
200
	}
201
202
	public function lastError() {
203
		return $this->__call( __FUNCTION__, func_get_args() );
204
	}
205
206
	public function fieldInfo( $table, $field ) {
207
		return $this->__call( __FUNCTION__, func_get_args() );
208
	}
209
210
	public function affectedRows() {
211
		return $this->__call( __FUNCTION__, func_get_args() );
212
	}
213
214
	public function getSoftwareLink() {
215
		return $this->__call( __FUNCTION__, func_get_args() );
216
	}
217
218
	public function getServerVersion() {
219
		return $this->__call( __FUNCTION__, func_get_args() );
220
	}
221
222
	public function close() {
223
		return $this->__call( __FUNCTION__, func_get_args() );
224
	}
225
226
	public function reportConnectionError( $error = 'Unknown error' ) {
227
		return $this->__call( __FUNCTION__, func_get_args() );
228
	}
229
230
	public function query( $sql, $fname = __METHOD__, $tempIgnore = false ) {
231
		return $this->__call( __FUNCTION__, func_get_args() );
232
	}
233
234
	public function reportQueryError( $error, $errno, $sql, $fname, $tempIgnore = false ) {
235
		return $this->__call( __FUNCTION__, func_get_args() );
236
	}
237
238
	public function freeResult( $res ) {
239
		return $this->__call( __FUNCTION__, func_get_args() );
240
	}
241
242
	public function selectField(
243
		$table, $var, $cond = '', $fname = __METHOD__, $options = []
244
	) {
245
		return $this->__call( __FUNCTION__, func_get_args() );
246
	}
247
248
	public function selectFieldValues(
249
		$table, $var, $cond = '', $fname = __METHOD__, $options = []
250
	) {
251
		return $this->__call( __FUNCTION__, func_get_args() );
252
	}
253
254
	public function select(
255
		$table, $vars, $conds = '', $fname = __METHOD__,
256
		$options = [], $join_conds = []
257
	) {
258
		return $this->__call( __FUNCTION__, func_get_args() );
259
	}
260
261
	public function selectSQLText(
262
		$table, $vars, $conds = '', $fname = __METHOD__,
263
		$options = [], $join_conds = []
264
	) {
265
		return $this->__call( __FUNCTION__, func_get_args() );
266
	}
267
268
	public function selectRow(
269
		$table, $vars, $conds, $fname = __METHOD__,
270
		$options = [], $join_conds = []
271
	) {
272
		return $this->__call( __FUNCTION__, func_get_args() );
273
	}
274
275
	public function estimateRowCount(
276
		$table, $vars = '*', $conds = '', $fname = __METHOD__, $options = []
277
	) {
278
		return $this->__call( __FUNCTION__, func_get_args() );
279
	}
280
281
	public function selectRowCount(
282
		$tables, $vars = '*', $conds = '', $fname = __METHOD__, $options = [], $join_conds = []
283
	) {
284
		return $this->__call( __FUNCTION__, func_get_args() );
285
	}
286
287
	public function fieldExists( $table, $field, $fname = __METHOD__ ) {
288
		return $this->__call( __FUNCTION__, func_get_args() );
289
	}
290
291
	public function indexExists( $table, $index, $fname = __METHOD__ ) {
292
		return $this->__call( __FUNCTION__, func_get_args() );
293
	}
294
295
	public function tableExists( $table, $fname = __METHOD__ ) {
296
		return $this->__call( __FUNCTION__, func_get_args() );
297
	}
298
299
	public function indexUnique( $table, $index ) {
300
		return $this->__call( __FUNCTION__, func_get_args() );
301
	}
302
303
	public function insert( $table, $a, $fname = __METHOD__, $options = [] ) {
304
		return $this->__call( __FUNCTION__, func_get_args() );
305
	}
306
307
	public function update( $table, $values, $conds, $fname = __METHOD__, $options = [] ) {
308
		return $this->__call( __FUNCTION__, func_get_args() );
309
	}
310
311
	public function makeList( $a, $mode = self::LIST_COMMA ) {
312
		return $this->__call( __FUNCTION__, func_get_args() );
313
	}
314
315
	public function makeWhereFrom2d( $data, $baseKey, $subKey ) {
316
		return $this->__call( __FUNCTION__, func_get_args() );
317
	}
318
319
	public function aggregateValue( $valuedata, $valuename = 'value' ) {
320
		return $this->__call( __FUNCTION__, func_get_args() );
321
	}
322
323
	public function bitNot( $field ) {
324
		return $this->__call( __FUNCTION__, func_get_args() );
325
	}
326
327
	public function bitAnd( $fieldLeft, $fieldRight ) {
328
		return $this->__call( __FUNCTION__, func_get_args() );
329
	}
330
331
	public function bitOr( $fieldLeft, $fieldRight ) {
332
		return $this->__call( __FUNCTION__, func_get_args() );
333
	}
334
335
	public function buildConcat( $stringList ) {
336
		return $this->__call( __FUNCTION__, func_get_args() );
337
	}
338
339
	public function buildGroupConcatField(
340
		$delim, $table, $field, $conds = '', $join_conds = []
341
	) {
342
		return $this->__call( __FUNCTION__, func_get_args() );
343
	}
344
345
	public function buildStringCast( $field ) {
346
		return $this->__call( __FUNCTION__, func_get_args() );
347
	}
348
349
	public function selectDB( $db ) {
350
		return $this->__call( __FUNCTION__, func_get_args() );
351
	}
352
353
	public function getDBname() {
354
		return $this->__call( __FUNCTION__, func_get_args() );
355
	}
356
357
	public function getServer() {
358
		return $this->__call( __FUNCTION__, func_get_args() );
359
	}
360
361
	public function addQuotes( $s ) {
362
		return $this->__call( __FUNCTION__, func_get_args() );
363
	}
364
365
	public function buildLike() {
366
		return $this->__call( __FUNCTION__, func_get_args() );
367
	}
368
369
	public function anyChar() {
370
		return $this->__call( __FUNCTION__, func_get_args() );
371
	}
372
373
	public function anyString() {
374
		return $this->__call( __FUNCTION__, func_get_args() );
375
	}
376
377
	public function nextSequenceValue( $seqName ) {
378
		return $this->__call( __FUNCTION__, func_get_args() );
379
	}
380
381
	public function replace( $table, $uniqueIndexes, $rows, $fname = __METHOD__ ) {
382
		return $this->__call( __FUNCTION__, func_get_args() );
383
	}
384
385
	public function upsert(
386
		$table, array $rows, array $uniqueIndexes, array $set, $fname = __METHOD__
387
	) {
388
		return $this->__call( __FUNCTION__, func_get_args() );
389
	}
390
391
	public function deleteJoin(
392
		$delTable, $joinTable, $delVar, $joinVar, $conds, $fname = __METHOD__
393
	) {
394
		return $this->__call( __FUNCTION__, func_get_args() );
395
	}
396
397
	public function delete( $table, $conds, $fname = __METHOD__ ) {
398
		return $this->__call( __FUNCTION__, func_get_args() );
399
	}
400
401
	public function insertSelect(
402
		$destTable, $srcTable, $varMap, $conds,
403
		$fname = __METHOD__, $insertOptions = [], $selectOptions = []
404
	) {
405
		return $this->__call( __FUNCTION__, func_get_args() );
406
	}
407
408
	public function unionSupportsOrderAndLimit() {
409
		return $this->__call( __FUNCTION__, func_get_args() );
410
	}
411
412
	public function unionQueries( $sqls, $all ) {
413
		return $this->__call( __FUNCTION__, func_get_args() );
414
	}
415
416
	public function conditional( $cond, $trueVal, $falseVal ) {
417
		return $this->__call( __FUNCTION__, func_get_args() );
418
	}
419
420
	public function strreplace( $orig, $old, $new ) {
421
		return $this->__call( __FUNCTION__, func_get_args() );
422
	}
423
424
	public function getServerUptime() {
425
		return $this->__call( __FUNCTION__, func_get_args() );
426
	}
427
428
	public function wasDeadlock() {
429
		return $this->__call( __FUNCTION__, func_get_args() );
430
	}
431
432
	public function wasLockTimeout() {
433
		return $this->__call( __FUNCTION__, func_get_args() );
434
	}
435
436
	public function wasErrorReissuable() {
437
		return $this->__call( __FUNCTION__, func_get_args() );
438
	}
439
440
	public function wasReadOnlyError() {
441
		return $this->__call( __FUNCTION__, func_get_args() );
442
	}
443
444
	public function masterPosWait( DBMasterPos $pos, $timeout ) {
445
		return $this->__call( __FUNCTION__, func_get_args() );
446
	}
447
448
	public function getReplicaPos() {
449
		return $this->__call( __FUNCTION__, func_get_args() );
450
	}
451
452
	public function getMasterPos() {
453
		return $this->__call( __FUNCTION__, func_get_args() );
454
	}
455
456
	public function serverIsReadOnly() {
457
		return $this->__call( __FUNCTION__, func_get_args() );
458
	}
459
460
	public function onTransactionResolution( callable $callback, $fname = __METHOD__ ) {
461
		return $this->__call( __FUNCTION__, func_get_args() );
462
	}
463
464
	public function onTransactionIdle( callable $callback, $fname = __METHOD__ ) {
465
		return $this->__call( __FUNCTION__, func_get_args() );
466
	}
467
468
	public function onTransactionPreCommitOrIdle( callable $callback, $fname = __METHOD__ ) {
469
		return $this->__call( __FUNCTION__, func_get_args() );
470
	}
471
472
	public function setTransactionListener( $name, callable $callback = null ) {
473
		return $this->__call( __FUNCTION__, func_get_args() );
474
	}
475
476
	public function startAtomic( $fname = __METHOD__ ) {
477
		return $this->__call( __FUNCTION__, func_get_args() );
478
	}
479
480
	public function endAtomic( $fname = __METHOD__ ) {
481
		return $this->__call( __FUNCTION__, func_get_args() );
482
	}
483
484
	public function doAtomicSection( $fname, callable $callback ) {
485
		return $this->__call( __FUNCTION__, func_get_args() );
486
	}
487
488
	public function begin( $fname = __METHOD__, $mode = IDatabase::TRANSACTION_EXPLICIT ) {
489
		return $this->__call( __FUNCTION__, func_get_args() );
490
	}
491
492
	public function commit( $fname = __METHOD__, $flush = '' ) {
493
		return $this->__call( __FUNCTION__, func_get_args() );
494
	}
495
496
	public function rollback( $fname = __METHOD__, $flush = '' ) {
497
		return $this->__call( __FUNCTION__, func_get_args() );
498
	}
499
500
	public function flushSnapshot( $fname = __METHOD__ ) {
501
		return $this->__call( __FUNCTION__, func_get_args() );
502
	}
503
504
	public function listTables( $prefix = null, $fname = __METHOD__ ) {
505
		return $this->__call( __FUNCTION__, func_get_args() );
506
	}
507
508
	public function timestamp( $ts = 0 ) {
509
		return $this->__call( __FUNCTION__, func_get_args() );
510
	}
511
512
	public function timestampOrNull( $ts = null ) {
513
		return $this->__call( __FUNCTION__, func_get_args() );
514
	}
515
516
	public function ping( &$rtt = null ) {
517
		return func_num_args()
518
			? $this->__call( __FUNCTION__, [ &$rtt ] )
519
			: $this->__call( __FUNCTION__, [] ); // method cares about null vs missing
520
	}
521
522
	public function getLag() {
523
		return $this->__call( __FUNCTION__, func_get_args() );
524
	}
525
526
	public function getSessionLagStatus() {
527
		return $this->__call( __FUNCTION__, func_get_args() );
528
	}
529
530
	public function maxListLen() {
531
		return $this->__call( __FUNCTION__, func_get_args() );
532
	}
533
534
	public function encodeBlob( $b ) {
535
		return $this->__call( __FUNCTION__, func_get_args() );
536
	}
537
538
	public function decodeBlob( $b ) {
539
		return $this->__call( __FUNCTION__, func_get_args() );
540
	}
541
542
	public function setSessionOptions( array $options ) {
543
		return $this->__call( __FUNCTION__, func_get_args() );
544
	}
545
546
	public function setSchemaVars( $vars ) {
547
		return $this->__call( __FUNCTION__, func_get_args() );
548
	}
549
550
	public function lockIsFree( $lockName, $method ) {
551
		return $this->__call( __FUNCTION__, func_get_args() );
552
	}
553
554
	public function lock( $lockName, $method, $timeout = 5 ) {
555
		return $this->__call( __FUNCTION__, func_get_args() );
556
	}
557
558
	public function unlock( $lockName, $method ) {
559
		return $this->__call( __FUNCTION__, func_get_args() );
560
	}
561
562
	public function getScopedLockAndFlush( $lockKey, $fname, $timeout ) {
563
		return $this->__call( __FUNCTION__, func_get_args() );
564
	}
565
566
	public function namedLocksEnqueue() {
567
		return $this->__call( __FUNCTION__, func_get_args() );
568
	}
569
570
	public function getInfinity() {
571
		return $this->__call( __FUNCTION__, func_get_args() );
572
	}
573
574
	public function encodeExpiry( $expiry ) {
575
		return $this->__call( __FUNCTION__, func_get_args() );
576
	}
577
578
	public function decodeExpiry( $expiry, $format = TS_MW ) {
579
		return $this->__call( __FUNCTION__, func_get_args() );
580
	}
581
582
	public function setBigSelects( $value = true ) {
583
		return $this->__call( __FUNCTION__, func_get_args() );
584
	}
585
586
	public function isReadOnly() {
587
		return $this->__call( __FUNCTION__, func_get_args() );
588
	}
589
590
	public function setTableAliases( array $aliases ) {
591
		return $this->__call( __FUNCTION__, func_get_args() );
592
	}
593
594
	/**
595
	 * Clean up the connection when out of scope
596
	 */
597
	function __destruct() {
598
		if ( $this->conn !== null ) {
599
			$this->lb->reuseConnection( $this->conn );
600
		}
601
	}
602
}
603