MediaWiki  master
PoolCounterWork.php
Go to the documentation of this file.
1 <?php
27 abstract class PoolCounterWork {
29  protected $type = 'generic';
31  protected $cacheable = false; // does this override getCachedWork() ?
33  private $poolCounter;
34 
40  public function __construct( string $type, string $key, PoolCounter $poolCounter = null ) {
41  $this->type = $type;
42  // MW >= 1.35
43  $this->poolCounter = $poolCounter ?? PoolCounter::factory( $type, $key );
44  }
45 
50  abstract public function doWork();
51 
56  public function getCachedWork() {
57  return false;
58  }
59 
65  public function fallback() {
66  return false;
67  }
68 
76  public function error( $status ) {
77  return false;
78  }
79 
86  public function logError( $status ) {
87  $key = $this->poolCounter->getKey();
88 
89  wfDebugLog( 'poolcounter', "Pool key '$key' ({$this->type}): "
90  . $status->getMessage()->inLanguage( 'en' )->useDatabase( false )->text() );
91  }
92 
108  public function execute( $skipcache = false ) {
109  if ( $this->cacheable && !$skipcache ) {
110  $status = $this->poolCounter->acquireForAnyone();
111  } else {
112  $status = $this->poolCounter->acquireForMe();
113  }
114 
115  if ( !$status->isOK() ) {
116  // Respond gracefully to complete server breakage: just log it and do the work
117  $this->logError( $status );
118  return $this->doWork();
119  }
120 
121  switch ( $status->value ) {
123  // Better to ignore nesting pool counter limits than to fail.
124  // Assume that the outer pool limiting is reasonable enough.
125  /* no break */
126  case PoolCounter::LOCKED:
127  try {
128  $result = $this->doWork();
129  } finally {
130  $this->poolCounter->release();
131  }
132  return $result;
133 
134  case PoolCounter::DONE:
135  $result = $this->getCachedWork();
136  if ( $result === false ) {
137  /* That someone else work didn't serve us.
138  * Acquire the lock for me
139  */
140  return $this->execute( true );
141  }
142  return $result;
143 
146  $result = $this->fallback();
147 
148  if ( $result !== false ) {
149  return $result;
150  }
151  /* no break */
152 
153  /* These two cases should never be hit... */
154  case PoolCounter::ERROR:
155  default:
156  $errors = [
157  PoolCounter::QUEUE_FULL => 'pool-queuefull',
158  PoolCounter::TIMEOUT => 'pool-timeout' ];
159 
160  $status = Status::newFatal( $errors[$status->value] ?? 'pool-errorunknown' );
161  $this->logError( $status );
162  return $this->error( $status );
163  }
164  }
165 }
PoolCounterWork\fallback
fallback()
A work not so good (eg.
Definition: PoolCounterWork.php:65
PoolCounterWork\$cacheable
bool $cacheable
Definition: PoolCounterWork.php:31
StatusValue\newFatal
static newFatal( $message,... $parameters)
Factory function for fatal errors.
Definition: StatusValue.php:69
PoolCounterWork\__construct
__construct(string $type, string $key, PoolCounter $poolCounter=null)
Definition: PoolCounterWork.php:40
PoolCounter\LOCK_HELD
const LOCK_HELD
Definition: PoolCounter.php:55
PoolCounter\LOCKED
const LOCKED
Definition: PoolCounter.php:47
PoolCounterWork\doWork
doWork()
Actually perform the work, caching it if needed.
wfDebugLog
wfDebugLog( $logGroup, $text, $dest='all', array $context=[])
Send a line to a supplementary debug log file, if configured, or main debug log if not.
Definition: GlobalFunctions.php:992
PoolCounter
When you have many workers (threads/servers) giving service, and a cached item expensive to produce e...
Definition: PoolCounter.php:45
PoolCounterWork\execute
execute( $skipcache=false)
Get the result of the work (whatever it is), or the result of the error() function.
Definition: PoolCounterWork.php:108
PoolCounterWork\getCachedWork
getCachedWork()
Retrieve the work from cache.
Definition: PoolCounterWork.php:56
PoolCounter\factory
static factory(string $type, string $key)
Create a Pool counter.
Definition: PoolCounter.php:111
PoolCounter\QUEUE_FULL
const QUEUE_FULL
Definition: PoolCounter.php:53
PoolCounter\ERROR
const ERROR
Definition: PoolCounter.php:51
PoolCounterWork\$poolCounter
PoolCounter $poolCounter
Definition: PoolCounterWork.php:33
PoolCounterWork\error
error( $status)
Do something with the error, like showing it to the user.
Definition: PoolCounterWork.php:76
PoolCounterWork
Class for dealing with PoolCounters using class members.
Definition: PoolCounterWork.php:27
PoolCounter\TIMEOUT
const TIMEOUT
Definition: PoolCounter.php:54
PoolCounterWork\$type
string $type
Definition: PoolCounterWork.php:29
PoolCounterWork\logError
logError( $status)
Log an error.
Definition: PoolCounterWork.php:86
PoolCounter\DONE
const DONE
Definition: PoolCounter.php:49