MediaWiki  REL1_19
ApiFormatBase.php
Go to the documentation of this file.
00001 <?php
00032 abstract class ApiFormatBase extends ApiBase {
00033 
00034         private $mIsHtml, $mFormat, $mUnescapeAmps, $mHelp, $mCleared;
00035         private $mBufferResult = false, $mBuffer, $mDisabled = false;
00036 
00043         public function __construct( $main, $format ) {
00044                 parent::__construct( $main, $format );
00045 
00046                 $this->mIsHtml = ( substr( $format, - 2, 2 ) === 'fm' ); // ends with 'fm'
00047                 if ( $this->mIsHtml ) {
00048                         $this->mFormat = substr( $format, 0, - 2 ); // remove ending 'fm'
00049                 } else {
00050                         $this->mFormat = $format;
00051                 }
00052                 $this->mFormat = strtoupper( $this->mFormat );
00053                 $this->mCleared = false;
00054         }
00055 
00061         public abstract function getMimeType();
00062 
00067         public function getNeedsRawData() {
00068                 return false;
00069         }
00070 
00075         public function getFormat() {
00076                 return $this->mFormat;
00077         }
00078 
00088         public function setUnescapeAmps ( $b ) {
00089                 $this->mUnescapeAmps = $b;
00090         }
00091 
00098         public function getIsHtml() {
00099                 return $this->mIsHtml;
00100         }
00101 
00108         public function getWantsHelp() {
00109                 return $this->getIsHtml();
00110         }
00111 
00116         public function disable() {
00117                 $this->mDisabled = true;
00118         }
00119 
00120         public function isDisabled() {
00121                 return $this->mDisabled;
00122         }
00123 
00130         function initPrinter( $isError ) {
00131                 if ( $this->mDisabled ) {
00132                         return;
00133                 }
00134                 $isHtml = $this->getIsHtml();
00135                 $mime = $isHtml ? 'text/html' : $this->getMimeType();
00136                 $script = wfScript( 'api' );
00137 
00138                 // Some printers (ex. Feed) do their own header settings,
00139                 // in which case $mime will be set to null
00140                 if ( is_null( $mime ) ) {
00141                         return; // skip any initialization
00142                 }
00143 
00144                 $this->getMain()->getRequest()->response()->header( "Content-Type: $mime; charset=utf-8" );
00145 
00146                 //Set X-Frame-Options API results (bug 39180)
00147                 global $wgApiFrameOptions;
00148                 if ( $wgApiFrameOptions ) {
00149                         $this->getMain()->getRequest()->response()->header( "X-Frame-Options: $wgApiFrameOptions" );
00150                 }
00151 
00152                 if ( $isHtml ) {
00153 ?>
00154 <!DOCTYPE HTML>
00155 <html>
00156 <head>
00157 <?php if ( $this->mUnescapeAmps ) {
00158 ?>      <title>MediaWiki API</title>
00159 <?php } else {
00160 ?>      <title>MediaWiki API Result</title>
00161 <?php } ?>
00162 </head>
00163 <body>
00164 <?php
00165 
00166 
00167                         if ( !$isError ) {
00168 ?>
00169 <br />
00170 <small>
00171 You are looking at the HTML representation of the <?php echo( $this->mFormat ); ?> format.<br />
00172 HTML is good for debugging, but probably is not suitable for your application.<br />
00173 See <a href='https://www.mediawiki.org/wiki/API'>complete documentation</a>, or
00174 <a href='<?php echo( $script ); ?>'>API help</a> for more information.
00175 </small>
00176 <?php
00177 
00178 
00179                         }
00180 ?>
00181 <pre>
00182 <?php
00183 
00184 
00185                 }
00186         }
00187 
00191         public function closePrinter() {
00192                 if ( $this->mDisabled ) {
00193                         return;
00194                 }
00195                 if ( $this->getIsHtml() ) {
00196 ?>
00197 
00198 </pre>
00199 </body>
00200 </html>
00201 <?php
00202 
00203 
00204                 }
00205         }
00206 
00213         public function printText( $text ) {
00214                 if ( $this->mDisabled ) {
00215                         return;
00216                 }
00217                 if ( $this->mBufferResult ) {
00218                         $this->mBuffer = $text;
00219                 } elseif ( $this->getIsHtml() ) {
00220                         echo $this->formatHTML( $text );
00221                 } else {
00222                         // For non-HTML output, clear all errors that might have been
00223                         // displayed if display_errors=On
00224                         // Do this only once, of course
00225                         if ( !$this->mCleared ) {
00226                                 ob_clean();
00227                                 $this->mCleared = true;
00228                         }
00229                         echo $text;
00230                 }
00231         }
00232 
00236         public function getBuffer() {
00237                 return $this->mBuffer;
00238         }
00239 
00244         public function setBufferResult( $value ) {
00245                 $this->mBufferResult = $value;
00246         }
00247 
00252         public function setHelp( $help = true ) {
00253                 $this->mHelp = $help;
00254         }
00255 
00262         protected function formatHTML( $text ) {
00263                 // Escape everything first for full coverage
00264                 $text = htmlspecialchars( $text );
00265 
00266                 // encode all comments or tags as safe blue strings
00267                 $text = preg_replace( '/\&lt;(!--.*?--|.*?)\&gt;/', '<span style="color:blue;">&lt;\1&gt;</span>', $text );
00268                 // identify requests to api.php
00269                 $text = preg_replace( '#^(\s*)(api\.php\?[^ <\n\t]+)$#m', '\1<a href="\2">\2</a>', $text );
00270                 if ( $this->mHelp ) {
00271                         // make strings inside * bold
00272                         $text = preg_replace( "#\\*[^<>\n]+\\*#", '<b>\\0</b>', $text );
00273                         // make strings inside $ italic
00274                         $text = preg_replace( "#\\$[^<>\n]+\\$#", '<b><i>\\0</i></b>', $text );
00275                 }
00276 
00277                 // Armor links (bug 61362)
00278                 $masked = array();
00279                 $text = preg_replace_callback( '#<a .*?</a>#', function ( $matches ) use ( &$masked ) {
00280                         $sha = sha1( $matches[0] );
00281                         $masked[$sha] = $matches[0];
00282                         return "<$sha>";
00283                 }, $text );
00284 
00285                 // identify URLs
00286                 $protos = wfUrlProtocolsWithoutProtRel();
00287                 // This regex hacks around bug 13218 (&quot; included in the URL)
00288                 $text = preg_replace( "#(($protos).*?)(&quot;)?([ \\'\"<>\n]|&lt;|&gt;|&quot;)#", '<a href="\\1">\\1</a>\\3\\4', $text );
00289 
00290                 // Unarmor links
00291                 $text = preg_replace_callback( '#<([0-9a-f]{40})>#', function ( $matches ) use ( &$masked ) {
00292                         $sha = $matches[1];
00293                         return isset( $masked[$sha] ) ? $masked[$sha] : $matches[0];
00294                 }, $text );
00295 
00302                 if ( $this->mUnescapeAmps ) {
00303                         $text = preg_replace( '/&amp;(amp|quot|lt|gt);/', '&\1;', $text );
00304                 }
00305 
00306                 return $text;
00307         }
00308 
00309         public function getExamples() {
00310                 return array(
00311                         'api.php?action=query&meta=siteinfo&siprop=namespaces&format=' . $this->getModuleName()
00312                                 => "Format the query result in the {$this->getModuleName()} format",
00313                 );
00314         }
00315 
00316         public function getHelpUrls() {
00317                 return 'https://www.mediawiki.org/wiki/API:Data_formats';
00318         }
00319 
00320         public function getDescription() {
00321                 return $this->getIsHtml() ? ' (pretty-print in HTML)' : '';
00322         }
00323 
00324         public static function getBaseVersion() {
00325                 return __CLASS__ . ': $Id$';
00326         }
00327 }
00328 
00333 class ApiFormatFeedWrapper extends ApiFormatBase {
00334 
00335         public function __construct( $main ) {
00336                 parent::__construct( $main, 'feed' );
00337         }
00338 
00345         public static function setResult( $result, $feed, $feedItems ) {
00346                 // Store output in the Result data.
00347                 // This way we can check during execution if any error has occured
00348                 // Disable size checking for this because we can't continue
00349                 // cleanly; size checking would cause more problems than it'd
00350                 // solve
00351                 $result->disableSizeCheck();
00352                 $result->addValue( null, '_feed', $feed );
00353                 $result->addValue( null, '_feeditems', $feedItems );
00354                 $result->enableSizeCheck();
00355         }
00356 
00362         public function getMimeType() {
00363                 return null;
00364         }
00365 
00371         public function getNeedsRawData() {
00372                 return true;
00373         }
00374 
00380         public function execute() {
00381                 $data = $this->getResultData();
00382                 if ( isset( $data['_feed'] ) && isset( $data['_feeditems'] ) ) {
00383                         $feed = $data['_feed'];
00384                         $items = $data['_feeditems'];
00385 
00386                         $feed->outHeader();
00387                         foreach ( $items as & $item ) {
00388                                 $feed->outItem( $item );
00389                         }
00390                         $feed->outFooter();
00391                 } else {
00392                         // Error has occured, print something useful
00393                         ApiBase::dieDebug( __METHOD__, 'Invalid feed class/item' );
00394                 }
00395         }
00396 
00397         public function getVersion() {
00398                 return __CLASS__ . ': $Id$';
00399         }
00400 }