MediaWiki  REL1_22
HTMLFileCache.php
Go to the documentation of this file.
00001 <?php
00031 class HTMLFileCache extends FileCacheBase {
00039     public static function newFromTitle( $title, $action ) {
00040         $cache = new self();
00041 
00042         $allowedTypes = self::cacheablePageActions();
00043         if ( !in_array( $action, $allowedTypes ) ) {
00044             throw new MWException( "Invalid filecache type given." );
00045         }
00046         $cache->mKey = ( $title instanceof Title )
00047             ? $title->getPrefixedDBkey()
00048             : (string)$title;
00049         $cache->mType = (string)$action;
00050         $cache->mExt = 'html';
00051 
00052         return $cache;
00053     }
00054 
00059     protected static function cacheablePageActions() {
00060         return array( 'view', 'history' );
00061     }
00062 
00067     protected function cacheDirectory() {
00068         return $this->baseCacheDirectory(); // no subdir for b/c with old cache files
00069     }
00070 
00077     protected function typeSubdirectory() {
00078         if ( $this->mType === 'view' ) {
00079             return ''; //  b/c to not skip existing cache
00080         } else {
00081             return $this->mType . '/';
00082         }
00083     }
00084 
00090     public static function useFileCache( IContextSource $context ) {
00091         global $wgUseFileCache, $wgShowIPinHeader, $wgDebugToolbar, $wgContLang;
00092         if ( !$wgUseFileCache ) {
00093             return false;
00094         }
00095         if ( $wgShowIPinHeader || $wgDebugToolbar ) {
00096             wfDebug( "HTML file cache skipped. Either \$wgShowIPinHeader and/or \$wgDebugToolbar on\n" );
00097             return false;
00098         }
00099 
00100         // Get all query values
00101         $queryVals = $context->getRequest()->getValues();
00102         foreach ( $queryVals as $query => $val ) {
00103             if ( $query === 'title' || $query === 'curid' ) {
00104                 continue; // note: curid sets title
00105             // Normal page view in query form can have action=view.
00106             } elseif ( $query === 'action' && in_array( $val, self::cacheablePageActions() ) ) {
00107                 continue;
00108             // Below are header setting params
00109             } elseif ( $query === 'maxage' || $query === 'smaxage' ) {
00110                 continue;
00111             }
00112             return false;
00113         }
00114         $user = $context->getUser();
00115         // Check for non-standard user language; this covers uselang,
00116         // and extensions for auto-detecting user language.
00117         $ulang = $context->getLanguage()->getCode();
00118         $clang = $wgContLang->getCode();
00119         // Check that there are no other sources of variation
00120         return !$user->getId() && !$user->getNewtalk() && $ulang == $clang;
00121     }
00122 
00128     public function loadFromFileCache( IContextSource $context ) {
00129         global $wgMimeType, $wgLanguageCode;
00130 
00131         wfDebug( __METHOD__ . "()\n" );
00132         $filename = $this->cachePath();
00133 
00134         $context->getOutput()->sendCacheControl();
00135         header( "Content-Type: $wgMimeType; charset=UTF-8" );
00136         header( "Content-Language: $wgLanguageCode" );
00137         if ( $this->useGzip() ) {
00138             if ( wfClientAcceptsGzip() ) {
00139                 header( 'Content-Encoding: gzip' );
00140                 readfile( $filename );
00141             } else {
00142                 /* Send uncompressed */
00143                 wfDebug( __METHOD__ . " uncompressing cache file and sending it\n" );
00144                 readgzfile( $filename );
00145             }
00146         } else {
00147             readfile( $filename );
00148         }
00149         $context->getOutput()->disable(); // tell $wgOut that output is taken care of
00150     }
00151 
00158     public function saveToFileCache( $text ) {
00159         global $wgUseFileCache;
00160 
00161         if ( !$wgUseFileCache || strlen( $text ) < 512 ) {
00162             // Disabled or empty/broken output (OOM and PHP errors)
00163             return $text;
00164         }
00165 
00166         wfDebug( __METHOD__ . "()\n", false );
00167 
00168         $now = wfTimestampNow();
00169         if ( $this->useGzip() ) {
00170             $text = str_replace(
00171                 '</html>', '<!-- Cached/compressed ' . $now . " -->\n</html>", $text );
00172         } else {
00173             $text = str_replace(
00174                 '</html>', '<!-- Cached ' . $now . " -->\n</html>", $text );
00175         }
00176 
00177         // Store text to FS...
00178         $compressed = $this->saveText( $text );
00179         if ( $compressed === false ) {
00180             return $text; // error
00181         }
00182 
00183         // gzip output to buffer as needed and set headers...
00184         if ( $this->useGzip() ) {
00185             // @todo Ugly wfClientAcceptsGzip() function - use context!
00186             if ( wfClientAcceptsGzip() ) {
00187                 header( 'Content-Encoding: gzip' );
00188                 return $compressed;
00189             } else {
00190                 return $text;
00191             }
00192         } else {
00193             return $text;
00194         }
00195     }
00196 
00202     public static function clearFileCache( Title $title ) {
00203         global $wgUseFileCache;
00204 
00205         if ( !$wgUseFileCache ) {
00206             return false;
00207         }
00208 
00209         foreach ( self::cacheablePageActions() as $type ) {
00210             $fc = self::newFromTitle( $title, $type );
00211             $fc->clearCache();
00212         }
00213 
00214         return true;
00215     }
00216 }