* Actual format of the file depends on the $wgLocalMessageCacheSerialized
* setting.
*
- * @param $hash String: the hash of contents, to check validity.
+ * @param string $hash the hash of contents, to check validity.
* @param $code Mixed: Optional language code, see documenation of load().
* @return bool on failure.
*/
$where[] = 'cache is empty';
$where[] = 'loading from database';
- $this->lock( $cacheKey );
+ if ( $this->lock( $cacheKey ) ) {
+ $that = $this;
+ $osc = new ScopedCallback( function() use ( $that, $cacheKey ) {
+ $that->unlock( $cacheKey );
+ } );
+ }
# Limit the concurrency of loadFromDB to a single process
# This prevents the site from going down when the cache expires
$statusKey = wfMemcKey( 'messages', $code, 'status' );
$success = $this->mMemc->add( $statusKey, 'loading', MSG_LOAD_TIMEOUT );
if ( $success ) { // acquired lock
+ $cache = $this->mMemc;
+ $isc = new ScopedCallback( function() use ( $cache, $statusKey ) {
+ $cache->delete( $statusKey );
+ } );
$cache = $this->loadFromDB( $code );
$success = $this->setCache( $cache, $code );
if ( $success ) { // messages loaded
$success = $this->saveToCaches( $cache, true, $code );
- if ( $success ) {
- $this->mMemc->delete( $statusKey );
- } else {
+ $isc = null; // unlock
+ if ( !$success ) {
$this->mMemc->set( $statusKey, 'error', 60 * 5 );
wfDebug( __METHOD__ . ": set() error: restart memcached server!\n" );
$exception = new MWException( "Could not save cache for '$code'." );
}
} else {
- $this->mMemc->delete( $statusKey );
+ $isc = null; // unlock
$exception = new MWException( "Could not load cache from DB for '$code'." );
}
} else {
$exception = new MWException( "Could not acquire '$statusKey' lock." );
}
- $this->unlock( $cacheKey );
+ $osc = null; // unlock
}
if ( !$success ) {
* $wgMaxMsgCacheEntrySize are assigned a special value, and are loaded
* on-demand from the database later.
*
- * @param $code String: language code.
+ * @param string $code language code.
* @return Array: loaded messages for storing in caches.
*/
function loadFromDB( $code ) {
/**
* Updates cache as necessary when message page is changed
*
- * @param $title String: name of the page changed.
+ * @param string $title name of the page changed.
* @param $text Mixed: new contents of the page.
*/
public function replace( $title, $text ) {
// Also delete cached sidebar... just in case it is affected
$codes = array( $code );
- if ( $code === 'en' ) {
+ if ( $code === 'en' ) {
// Delete all sidebars, like for example on action=purge on the
// sidebar messages
$codes = array_keys( Language::fetchLanguageNames() );
/**
* Shortcut to update caches.
*
- * @param $cache Array: cached messages with a version.
- * @param $memc Bool: Wether to update or not memcache.
- * @param $code String: Language code.
+ * @param array $cache cached messages with a version.
+ * @param bool $memc Wether to update or not memcache.
+ * @param string $code Language code.
* @return bool on somekind of error.
*/
protected function saveToCaches( $cache, $memc = true, $code = false ) {
* Get a message from the MediaWiki namespace, with caching. The key must
* first be converted to two-part lang/msg form if necessary.
*
- * @param $title String: Message cache key with initial uppercase letter.
- * @param $code String: code denoting the language to try.
+ * Unlike self::get(), this function doesn't resolve fallback chains, and
+ * some callers require this behavior. LanguageConverter::parseCachedTable()
+ * and self::get() are some examples in core.
+ *
+ * @param string $title Message cache key with initial uppercase letter.
+ * @param string $code code denoting the language to try.
*
* @return string|bool False on failure
*/