MediaWiki
REL1_20
|
00001 <?php 00033 class RawAction extends FormlessAction { 00034 private $mGen; 00035 00036 public function getName() { 00037 return 'raw'; 00038 } 00039 00040 public function requiresWrite() { 00041 return false; 00042 } 00043 00044 public function requiresUnblock() { 00045 return false; 00046 } 00047 00048 function onView() { 00049 global $wgGroupPermissions, $wgSquidMaxage, $wgForcedRawSMaxage, $wgJsMimeType; 00050 00051 $this->getOutput()->disable(); 00052 $request = $this->getRequest(); 00053 00054 if ( !$request->checkUrlExtension() ) { 00055 return; 00056 } 00057 00058 if ( $this->getOutput()->checkLastModified( $this->page->getTouched() ) ) { 00059 return; // Client cache fresh and headers sent, nothing more to do. 00060 } 00061 00062 # special case for 'generated' raw things: user css/js 00063 # This is deprecated and will only return empty content 00064 $gen = $request->getVal( 'gen' ); 00065 $smaxage = $request->getIntOrNull( 'smaxage' ); 00066 00067 if ( $gen == 'css' || $gen == 'js' ) { 00068 $this->mGen = $gen; 00069 if ( $smaxage === null ) { 00070 $smaxage = $wgSquidMaxage; 00071 } 00072 } else { 00073 $this->mGen = false; 00074 } 00075 00076 $contentType = $this->getContentType(); 00077 00078 # Force caching for CSS and JS raw content, default: 5 minutes 00079 if ( $smaxage === null ) { 00080 if ( $contentType == 'text/css' || $contentType == $wgJsMimeType ) { 00081 $smaxage = intval( $wgForcedRawSMaxage ); 00082 } else { 00083 $smaxage = 0; 00084 } 00085 } 00086 00087 $maxage = $request->getInt( 'maxage', $wgSquidMaxage ); 00088 00089 $response = $request->response(); 00090 00091 $response->header( 'Content-type: ' . $contentType . '; charset=UTF-8' ); 00092 # Output may contain user-specific data; 00093 # vary generated content for open sessions on private wikis 00094 $privateCache = !$wgGroupPermissions['*']['read'] && ( $smaxage == 0 || session_id() != '' ); 00095 // Bug 53032 - make this private if user is logged in, 00096 // so we don't accidentally cache cookies 00097 $privateCache = $privateCache ?: $this->getUser()->isLoggedIn(); 00098 # allow the client to cache this for 24 hours 00099 $mode = $privateCache ? 'private' : 'public'; 00100 $response->header( 'Cache-Control: ' . $mode . ', s-maxage=' . $smaxage . ', max-age=' . $maxage ); 00101 00102 $text = $this->getRawText(); 00103 00104 if ( $text === false && $contentType == 'text/x-wiki' ) { 00105 # Don't return a 404 response for CSS or JavaScript; 00106 # 404s aren't generally cached and it would create 00107 # extra hits when user CSS/JS are on and the user doesn't 00108 # have the pages. 00109 $response->header( 'HTTP/1.x 404 Not Found' ); 00110 } 00111 00112 if ( !wfRunHooks( 'RawPageViewBeforeOutput', array( &$this, &$text ) ) ) { 00113 wfDebug( __METHOD__ . ": RawPageViewBeforeOutput hook broke raw page output.\n" ); 00114 } 00115 00116 echo $text; 00117 } 00118 00125 public function getRawText() { 00126 global $wgParser; 00127 00128 # No longer used 00129 if( $this->mGen ) { 00130 return ''; 00131 } 00132 00133 $text = false; 00134 $title = $this->getTitle(); 00135 $request = $this->getRequest(); 00136 00137 // If it's a MediaWiki message we can just hit the message cache 00138 if ( $request->getBool( 'usemsgcache' ) && $title->getNamespace() == NS_MEDIAWIKI ) { 00139 // The first "true" is to use the database, the second is to use the content langue 00140 // and the last one is to specify the message key already contains the language in it ("/de", etc.) 00141 $text = MessageCache::singleton()->get( $title->getDBkey(), true, true, true ); 00142 // If the message doesn't exist, return a blank 00143 if ( $text === false ) { 00144 $text = ''; 00145 } 00146 } else { 00147 // Get it from the DB 00148 $rev = Revision::newFromTitle( $title, $this->getOldId() ); 00149 if ( $rev ) { 00150 $lastmod = wfTimestamp( TS_RFC2822, $rev->getTimestamp() ); 00151 $request->response()->header( "Last-modified: $lastmod" ); 00152 00153 // Public-only due to cache headers 00154 $text = $rev->getText(); 00155 $section = $request->getIntOrNull( 'section' ); 00156 if ( $section !== null ) { 00157 $text = $wgParser->getSection( $text, $section ); 00158 } 00159 } 00160 } 00161 00162 if ( $text !== false && $text !== '' && $request->getVal( 'templates' ) === 'expand' ) { 00163 $text = $wgParser->preprocess( $text, $title, ParserOptions::newFromContext( $this->getContext() ) ); 00164 } 00165 00166 return $text; 00167 } 00168 00174 public function getOldId() { 00175 $oldid = $this->getRequest()->getInt( 'oldid' ); 00176 switch ( $this->getRequest()->getText( 'direction' ) ) { 00177 case 'next': 00178 # output next revision, or nothing if there isn't one 00179 if( $oldid ) { 00180 $oldid = $this->getTitle()->getNextRevisionId( $oldid ); 00181 } 00182 $oldid = $oldid ? $oldid : -1; 00183 break; 00184 case 'prev': 00185 # output previous revision, or nothing if there isn't one 00186 if( !$oldid ) { 00187 # get the current revision so we can get the penultimate one 00188 $oldid = $this->page->getLatest(); 00189 } 00190 $prev = $this->getTitle()->getPreviousRevisionId( $oldid ); 00191 $oldid = $prev ? $prev : -1 ; 00192 break; 00193 case 'cur': 00194 $oldid = 0; 00195 break; 00196 } 00197 return $oldid; 00198 } 00199 00205 public function getContentType() { 00206 global $wgJsMimeType; 00207 00208 $ctype = $this->getRequest()->getVal( 'ctype' ); 00209 00210 if ( $ctype == '' ) { 00211 $gen = $this->getRequest()->getVal( 'gen' ); 00212 if ( $gen == 'js' ) { 00213 $ctype = $wgJsMimeType; 00214 } elseif ( $gen == 'css' ) { 00215 $ctype = 'text/css'; 00216 } 00217 } 00218 00219 $allowedCTypes = array( 'text/x-wiki', $wgJsMimeType, 'text/css', 'application/x-zope-edit' ); 00220 if ( $ctype == '' || !in_array( $ctype, $allowedCTypes ) ) { 00221 $ctype = 'text/x-wiki'; 00222 } 00223 00224 return $ctype; 00225 } 00226 } 00227 00233 class RawPage extends RawAction { 00234 public $mOldId; 00235 00236 function __construct( Page $page, $request = false ) { 00237 wfDeprecated( __CLASS__, '1.19' ); 00238 parent::__construct( $page ); 00239 00240 if ( $request !== false ) { 00241 $context = new DerivativeContext( $this->getContext() ); 00242 $context->setRequest( $request ); 00243 $this->context = $context; 00244 } 00245 } 00246 00247 public function view() { 00248 $this->onView(); 00249 } 00250 00251 public function getOldId() { 00252 # Some extensions like to set $mOldId 00253 if ( $this->mOldId !== null ) { 00254 return $this->mOldId; 00255 } 00256 return parent::getOldId(); 00257 } 00258 }