public function execute() { if ($this->hasArg()) { $files = $this->mArgs; } else { $this->maybeHelp(true); // @todo fixme this is a lame API :) exit(1); // it should exit from the above first... } $parser = new JSParser(); foreach ($files as $filename) { MediaWiki\suppressWarnings(); $js = file_get_contents($filename); MediaWiki\restoreWarnings(); if ($js === false) { $this->output("{$filename} ERROR: could not read file\n"); $this->errs++; continue; } try { $parser->parse($js, $filename, 1); } catch (Exception $e) { $this->errs++; $this->output("{$filename} ERROR: " . $e->getMessage() . "\n"); continue; } $this->output("{$filename} OK\n"); } if ($this->errs > 0) { exit(1); } }
public function run() { $done = false; $startTime = microtime(true); while (!$done) { $readSockets = $writeSockets = array(); /** * @var $client SquidPurgeClient */ foreach ($this->clients as $clientIndex => $client) { $sockets = $client->getReadSocketsForSelect(); foreach ($sockets as $i => $socket) { $readSockets["{$clientIndex}/{$i}"] = $socket; } $sockets = $client->getWriteSocketsForSelect(); foreach ($sockets as $i => $socket) { $writeSockets["{$clientIndex}/{$i}"] = $socket; } } if (!count($readSockets) && !count($writeSockets)) { break; } $exceptSockets = null; $timeout = min($startTime + $this->timeout - microtime(true), 1); MediaWiki\suppressWarnings(); $numReady = socket_select($readSockets, $writeSockets, $exceptSockets, $timeout); MediaWiki\restoreWarnings(); if ($numReady === false) { wfDebugLog('squid', __METHOD__ . ': Error in stream_select: ' . socket_strerror(socket_last_error()) . "\n"); break; } // Check for timeout, use 1% tolerance since we aimed at having socket_select() // exit at precisely the overall timeout if (microtime(true) - $startTime > $this->timeout * 0.99) { wfDebugLog('squid', __CLASS__ . ": timeout ({$this->timeout}s)\n"); break; } elseif (!$numReady) { continue; } foreach ($readSockets as $key => $socket) { list($clientIndex, ) = explode('/', $key); $client = $this->clients[$clientIndex]; $client->doReads(); } foreach ($writeSockets as $key => $socket) { list($clientIndex, ) = explode('/', $key); $client = $this->clients[$clientIndex]; $client->doWrites(); } $done = true; foreach ($this->clients as $client) { if (!$client->isIdle()) { $done = false; } } } foreach ($this->clients as $client) { $client->close(); } }
/** * Try to set session.serialize_handler to a supported format * * This may change the format even if the current format is also supported. * * @return string Format set * @throws \\DomainException */ public static function setSerializeHandler() { $formats = array('php_serialize', 'php', 'php_binary'); // First, try php_serialize since that's the only one that doesn't suck in some way. \MediaWiki\suppressWarnings(); ini_set('session.serialize_handler', 'php_serialize'); \MediaWiki\restoreWarnings(); if (ini_get('session.serialize_handler') === 'php_serialize') { return 'php_serialize'; } // Next, just use the current format if it's supported. $format = ini_get('session.serialize_handler'); if (in_array($format, $formats, true)) { return $format; } // Last chance, see if any of our supported formats are accepted. foreach ($formats as $format) { \MediaWiki\suppressWarnings(); ini_set('session.serialize_handler', $format); \MediaWiki\restoreWarnings(); if (ini_get('session.serialize_handler') === $format) { return $format; } } throw new \DomainException('Failed to set serialize handler to a supported format.' . ' Supported formats are: ' . join(', ', $formats) . '.'); }
public function testGetUnknownTemplate() { $registry = new TemplateRegistry(array()); \MediaWiki\suppressWarnings(); $html = $registry->getTemplate('unknown'); \MediaWiki\restoreWarnings(); $this->assertNull($html); }
protected function getSourceSha1Base36() { MediaWiki\suppressWarnings(); $hash = sha1_file($this->params['src']); MediaWiki\restoreWarnings(); if ($hash !== false) { $hash = Wikimedia\base_convert($hash, 16, 36, 31); } return $hash; }
/** * @param string $filename * @return Status */ static function newFromFile($filename) { MediaWiki\suppressWarnings(); $file = fopen($filename, 'rt'); MediaWiki\restoreWarnings(); if (!$file) { return Status::newFatal("importcantopen"); } return Status::newGood(new ImportStreamSource($file)); }
public function testOtherProjectSiteIds_unknownSite() { $siteStore = $this->getSiteStoreMock(); $otherProjectsSitesProvider = new OtherProjectsSitesGenerator($siteStore, 'kittenswiki', array('wikidata')); // getOtherProjectsSiteIds does wfWarn in case it's being called with a siteid // it doesn't know about. That's fine, we can just ignore that. \MediaWiki\suppressWarnings(); $result = $otherProjectsSitesProvider->getOtherProjectsSiteIds(array('wikipedia', 'wikisource')); \MediaWiki\restoreWarnings(); $this->assertSame(array(), $result); }
/** * @dataProvider provideCases * @covers JavaScriptMinifier::minify */ public function testJavaScriptMinifierOutput($code, $expectedOutput) { $minified = JavaScriptMinifier::minify($code); // JSMin+'s parser will throw an exception if output is not valid JS. // suppression of warnings needed for stupid crap MediaWiki\suppressWarnings(); $parser = new JSParser(); MediaWiki\restoreWarnings(); $parser->parse($minified, 'minify-test.js', 1); $this->assertEquals($expectedOutput, $minified, "Minified output should be in the form expected."); }
/** * @dataProvider projectLinkSidebarHookProvider */ public function testBuildProjectLinkSidebar_hook($handler, array $siteIdsToOutput, array $result, $suppressErrors = false) { $this->setMwGlobals('wgHooks', array('WikibaseClientOtherProjectsSidebar' => array($handler))); $otherProjectSidebarGenerator = new OtherProjectsSidebarGenerator('enwiki', $this->getSiteLinkLookup(), $this->getSiteStore(), $siteIdsToOutput); if ($suppressErrors) { \MediaWiki\suppressWarnings(); } $this->assertEquals($result, $otherProjectSidebarGenerator->buildProjectLinkSidebar(Title::makeTitle(NS_MAIN, 'Nyan Cat'))); if ($suppressErrors) { \MediaWiki\restoreWarnings(); } }
/** * Build the list of files we'll check for syntax errors */ private function buildFileList() { global $IP; $this->mIgnorePaths = array("includes/NamespaceCompat.php\$"); $this->mNoStyleCheckPaths = array("/activemq_stomp/", "EmailPage/PHPMailer", "FCKeditor/fckeditor/", '\\bphplot-', "/svggraph/", "\\bjsmin.php\$", "PEAR/File_Ogg/", "QPoll/Excel/", "/geshi/", "/smarty/"); if ($this->hasOption('path')) { $path = $this->getOption('path'); if (!$this->addPath($path)) { $this->error("Error: can't find file or directory {$path}\n", true); } return; // process only this path } elseif ($this->hasOption('list-file')) { $file = $this->getOption('list-file'); MediaWiki\suppressWarnings(); $f = fopen($file, 'r'); MediaWiki\restoreWarnings(); if (!$f) { $this->error("Can't open file {$file}\n", true); } $path = trim(fgets($f)); while ($path) { $this->addPath($path); } fclose($f); return; } elseif ($this->hasOption('modified')) { $this->output("Retrieving list from Git... "); $files = $this->getGitModifiedFiles($IP); $this->output("done\n"); foreach ($files as $file) { if ($this->isSuitableFile($file) && !is_dir($file)) { $this->mFiles[] = $file; } } return; } $this->output('Building file list...', 'listfiles'); // Only check files in these directories. // Don't just put $IP, because the recursive dir thingie goes into all subdirs $dirs = array($IP . '/includes', $IP . '/mw-config', $IP . '/languages', $IP . '/maintenance', $IP . '/skins'); if ($this->hasOption('with-extensions')) { $dirs[] = $IP . '/extensions'; } foreach ($dirs as $d) { $this->addDirectoryContent($d); } // Manually add two user-editable files that are usually sources of problems if (file_exists("{$IP}/LocalSettings.php")) { $this->mFiles[] = "{$IP}/LocalSettings.php"; } $this->output('done.', 'listfiles'); }
public function testSchemaNotAvailableReturnValue() { $formatter = new AvroFormatter([]); $noticeEnabled = PHPUnit_Framework_Error_Notice::$enabled; // disable conversion of notices PHPUnit_Framework_Error_Notice::$enabled = false; // have to keep the user notice from being output \MediaWiki\suppressWarnings(); $res = $formatter->format(['channel' => 'marty']); \MediaWiki\restoreWarnings(); PHPUnit_Framework_Error_Notice::$enabled = $noticeEnabled; $this->assertNull($res); }
/** * @dataProvider wikiIdProvider */ public function testPidLock($wikiId) { $pidLock = new PidLock('PidLockTest', $wikiId); $this->assertTrue($pidLock->getLock(), 'Get an initial log'); $this->assertFalse($pidLock->getLock(), 'Try to get the lock, although some already has it'); $this->assertTrue($pidLock->getLock(true), 'Force getting the lock'); $this->assertTrue($pidLock->removeLock()); // Make sure that the given file has actually been removed. // unlink gives a warning if you use it a file that doesn't exist, suppress that \MediaWiki\suppressWarnings(); $this->assertFalse($pidLock->removeLock()); \MediaWiki\restoreWarnings(); }
protected function setUp() { parent::setUp(); // Make sure MWDebug class is enabled static $MWDebugEnabled = false; if (!$MWDebugEnabled) { MWDebug::init(); $MWDebugEnabled = true; } /** Clear log before each test */ MWDebug::clearLog(); MediaWiki\suppressWarnings(); }
protected function __construct($text) { $this->doc = new DOMDocument('1.0', 'utf-8'); // Note: parsing a supposedly XHTML document with an XML parser is not // guaranteed to give accurate results. For example, it may introduce // differences in the number of line breaks in <pre> tags. MediaWiki\suppressWarnings(); if (!$this->doc->loadXML('<html><body>' . $text . '</body></html>')) { $this->invalid = true; } MediaWiki\restoreWarnings(); $this->xpath = new DOMXPath($this->doc); $this->body = $this->xpath->query('//body')->item(0); }
public function onSubmit(array $data) { if (!$data['Confirm']) { return Status::newFatal('locknoconfirm'); } $readOnlyFile = $this->getConfig()->get('ReadOnlyFile'); MediaWiki\suppressWarnings(); $res = unlink($readOnlyFile); MediaWiki\restoreWarnings(); if ($res) { return Status::newGood(); } else { return Status::newFatal('filedeleteerror', $readOnlyFile); } }
function translate($value) { // Hack for i18n:attributes in PHPTAL 1.0.0 dev version as of 2004-10-23 $value = preg_replace('/^string:/', '', $value); $value = wfMessage($value)->text(); // interpolate variables $m = []; while (preg_match('/\\$([0-9]*?)/sm', $value, $m)) { list($src, $var) = $m; MediaWiki\suppressWarnings(); $varValue = $this->context[$var]; MediaWiki\restoreWarnings(); $value = str_replace($src, $varValue, $value); } return $value; }
protected function doStoreInternal(array $params) { $status = Status::newGood(); $dst = $this->resolveHashKey($params['dst']); if ($dst === null) { $status->fatal('backend-fail-invalidpath', $params['dst']); return $status; } MediaWiki\suppressWarnings(); $data = file_get_contents($params['src']); MediaWiki\restoreWarnings(); if ($data === false) { // source doesn't exist? $status->fatal('backend-fail-store', $params['src'], $params['dst']); return $status; } $this->files[$dst] = array('data' => $data, 'mtime' => wfTimestamp(TS_MW, time())); return $status; }
public function onSubmit(array $data) { global $wgContLang; if (!$data['Confirm']) { return Status::newFatal('locknoconfirm'); } MediaWiki\suppressWarnings(); $fp = fopen($this->getConfig()->get('ReadOnlyFile'), 'w'); MediaWiki\restoreWarnings(); if (false === $fp) { # This used to show a file not found error, but the likeliest reason for fopen() # to fail at this point is insufficient permission to write to the file...good old # is_writable() is plain wrong in some cases, it seems... return Status::newFatal('lockfilenotwritable'); } fwrite($fp, $data['Reason']); $timestamp = wfTimestampNow(); fwrite($fp, "\n<p>" . $this->msg('lockedbyandtime', $this->getUser()->getName(), $wgContLang->date($timestamp, false, false), $wgContLang->time($timestamp, false, false))->inContentLanguage()->text() . "</p>\n"); fclose($fp); return Status::newGood(); }
/** * Stream a file to the browser, adding all the headings and fun stuff. * Headers sent include: Content-type, Content-Length, Last-Modified, * and Content-Disposition. * * @param string $fname Full name and path of the file to stream * @param array $headers Any additional headers to send * @param bool $sendErrors Send error messages if errors occur (like 404) * @throws MWException * @return bool Success */ public static function stream($fname, $headers = array(), $sendErrors = true) { if (FileBackend::isStoragePath($fname)) { // sanity throw new MWException(__FUNCTION__ . " given storage path '{$fname}'."); } MediaWiki\suppressWarnings(); $stat = stat($fname); MediaWiki\restoreWarnings(); $res = self::prepareForStream($fname, $stat, $headers, $sendErrors); if ($res == self::NOT_MODIFIED) { $ok = true; // use client cache } elseif ($res == self::READY_STREAM) { $ok = readfile($fname); } else { $ok = false; // failed } return $ok; }
protected function __construct() { $this->nodeIdFile = wfTempDir() . '/mw-' . __CLASS__ . '-UID-nodeid'; $nodeId = ''; if (is_file($this->nodeIdFile)) { $nodeId = file_get_contents($this->nodeIdFile); } // Try to get some ID that uniquely identifies this machine (RFC 4122)... if (!preg_match('/^[0-9a-f]{12}$/i', $nodeId)) { MediaWiki\suppressWarnings(); if (wfIsWindows()) { // http://technet.microsoft.com/en-us/library/bb490913.aspx $csv = trim(wfShellExec('getmac /NH /FO CSV')); $line = substr($csv, 0, strcspn($csv, "\n")); $info = str_getcsv($line); $nodeId = isset($info[0]) ? str_replace('-', '', $info[0]) : ''; } elseif (is_executable('/sbin/ifconfig')) { // Linux/BSD/Solaris/OS X // See http://linux.die.net/man/8/ifconfig $m = array(); preg_match('/\\s([0-9a-f]{2}(:[0-9a-f]{2}){5})\\s/', wfShellExec('/sbin/ifconfig -a'), $m); $nodeId = isset($m[1]) ? str_replace(':', '', $m[1]) : ''; } MediaWiki\restoreWarnings(); if (!preg_match('/^[0-9a-f]{12}$/i', $nodeId)) { $nodeId = MWCryptRand::generateHex(12, true); $nodeId[1] = dechex(hexdec($nodeId[1]) | 0x1); // set multicast bit } file_put_contents($this->nodeIdFile, $nodeId); // cache } $this->nodeId32 = Wikimedia\base_convert(substr(sha1($nodeId), 0, 8), 16, 2, 32); $this->nodeId48 = Wikimedia\base_convert($nodeId, 16, 2, 48); // If different processes run as different users, they may have different temp dirs. // This is dealt with by initializing the clock sequence number and counters randomly. $this->lockFile88 = wfTempDir() . '/mw-' . __CLASS__ . '-UID-88'; $this->lockFile128 = wfTempDir() . '/mw-' . __CLASS__ . '-UID-128'; $this->lockFileUUID = wfTempDir() . '/mw-' . __CLASS__ . '-UUID-128'; }
function numRows($res) { if ($res instanceof ResultWrapper) { $res = $res->result; } MediaWiki\suppressWarnings(); $n = pg_num_rows($res); MediaWiki\restoreWarnings(); if (pg_last_error($this->mConn)) { throw new DBUnexpectedError($this, 'SQL error: ' . htmlspecialchars(pg_last_error($this->mConn))); } return $n; }
/** * @return string */ function lastError() { if ($this->mConn) { # Even if it's non-zero, it can still be invalid MediaWiki\suppressWarnings(); $error = $this->mysqlError($this->mConn); if (!$error) { $error = $this->mysqlError(); } MediaWiki\restoreWarnings(); } else { $error = $this->mysqlError(); } if ($error) { $error .= ' (' . $this->mServer . ')'; } return $error; }
/** * Convert metadata version. * * By default just returns $metadata, but can be used to allow * media handlers to convert between metadata versions. * * @param string|array $metadata Metadata array (serialized if string) * @param int $version Target version * @return array Serialized metadata in specified version, or $metadata on fail. */ function convertMetadataVersion($metadata, $version = 1) { if (!is_array($metadata)) { // unserialize to keep return parameter consistent. MediaWiki\suppressWarnings(); $ret = unserialize($metadata); MediaWiki\restoreWarnings(); return $ret; } return $metadata; }
/** * Parses and returns the rc_params attribute * * @since 1.26 * * @return array|null */ public function parseParams() { $rcParams = $this->getAttribute('rc_params'); MediaWiki\suppressWarnings(); $unserializedParams = unserialize($rcParams); MediaWiki\restoreWarnings(); return $unserializedParams; }
function getInfo() { MediaWiki\suppressWarnings(); $file = fopen($this->mFilename, 'rb'); MediaWiki\restoreWarnings(); if ($file === false) { wfDebug(__METHOD__ . ": missing or failed file read\n"); return false; } $header = fread($file, 16); $info = false; if (strlen($header) < 16) { wfDebug(__METHOD__ . ": too short file header\n"); } else { $arr = unpack('a4magic/a4form/NformLength/a4subtype', $header); $subtype = $arr['subtype']; if ($arr['magic'] != 'AT&T') { wfDebug(__METHOD__ . ": not a DjVu file\n"); } elseif ($subtype == 'DJVU') { // Single-page document $info = $this->getPageInfo($file); } elseif ($subtype == 'DJVM') { // Multi-page document $info = $this->getMultiPageInfo($file, $arr['formLength']); } else { wfDebug(__METHOD__ . ": unrecognized DJVU file type '{$arr['subtype']}'\n"); } } fclose($file); return $info; }
/** * checkLastModified tells the client to use the client-cached page if * possible. If successful, the OutputPage is disabled so that * any future call to OutputPage->output() have no effect. * * Side effect: sets mLastModified for Last-Modified header * * @param string $timestamp * * @return bool True if cache-ok headers was sent. */ public function checkLastModified($timestamp) { if (!$timestamp || $timestamp == '19700101000000') { wfDebug(__METHOD__ . ": CACHE DISABLED, NO TIMESTAMP\n"); return false; } $config = $this->getConfig(); if (!$config->get('CachePages')) { wfDebug(__METHOD__ . ": CACHE DISABLED\n"); return false; } $timestamp = wfTimestamp(TS_MW, $timestamp); $modifiedTimes = array('page' => $timestamp, 'user' => $this->getUser()->getTouched(), 'epoch' => $config->get('CacheEpoch')); if ($config->get('UseSquid')) { // bug 44570: the core page itself may not change, but resources might $modifiedTimes['sepoch'] = wfTimestamp(TS_MW, time() - $config->get('SquidMaxage')); } Hooks::run('OutputPageCheckLastModified', array(&$modifiedTimes)); $maxModified = max($modifiedTimes); $this->mLastModified = wfTimestamp(TS_RFC2822, $maxModified); $clientHeader = $this->getRequest()->getHeader('If-Modified-Since'); if ($clientHeader === false) { wfDebug(__METHOD__ . ": client did not send If-Modified-Since header\n", 'log'); return false; } # IE sends sizes after the date like this: # Wed, 20 Aug 2003 06:51:19 GMT; length=5202 # this breaks strtotime(). $clientHeader = preg_replace('/;.*$/', '', $clientHeader); MediaWiki\suppressWarnings(); // E_STRICT system time bitching $clientHeaderTime = strtotime($clientHeader); MediaWiki\restoreWarnings(); if (!$clientHeaderTime) { wfDebug(__METHOD__ . ": unable to parse the client's If-Modified-Since header: {$clientHeader}\n"); return false; } $clientHeaderTime = wfTimestamp(TS_MW, $clientHeaderTime); # Make debug info $info = ''; foreach ($modifiedTimes as $name => $value) { if ($info !== '') { $info .= ', '; } $info .= "{$name}=" . wfTimestamp(TS_ISO_8601, $value); } wfDebug(__METHOD__ . ": client sent If-Modified-Since: " . wfTimestamp(TS_ISO_8601, $clientHeaderTime) . "\n", 'log'); wfDebug(__METHOD__ . ": effective Last-Modified: " . wfTimestamp(TS_ISO_8601, $maxModified) . "\n", 'log'); if ($clientHeaderTime < $maxModified) { wfDebug(__METHOD__ . ": STALE, {$info}\n", 'log'); return false; } # Not modified # Give a 304 Not Modified response code and disable body output wfDebug(__METHOD__ . ": NOT MODIFIED, {$info}\n", 'log'); ini_set('zlib.output_compression', 0); $this->getRequest()->response()->statusHeader(304); $this->sendCacheControl(); $this->disable(); // Don't output a compressed blob when using ob_gzhandler; // it's technically against HTTP spec and seems to confuse // Firefox when the response gets split over two packets. wfClearOutputBuffers(); return true; }
/** * Preprocess some wikitext and return the document tree. * This is the ghost of Parser::replace_variables(). * * @param string $text The text to parse * @param int $flags Bitwise combination of: * Parser::PTD_FOR_INCLUSION Handle "<noinclude>" and "<includeonly>" * as if the text is being included. Default * is to assume a direct page view. * * The generated DOM tree must depend only on the input text and the flags. * The DOM tree must be the same in OT_HTML and OT_WIKI mode, to avoid a regression of bug 4899. * * Any flag added to the $flags parameter here, or any other parameter liable to cause a * change in the DOM tree for a given text, must be passed through the section identifier * in the section edit link and thus back to extractSections(). * * The output of this function is currently only cached in process memory, but a persistent * cache may be implemented at a later date which takes further advantage of these strict * dependency requirements. * * @throws MWException * @return PPNode_DOM */ public function preprocessToObj($text, $flags = 0) { $xml = $this->cacheGetTree($text, $flags); if ($xml === false) { $xml = $this->preprocessToXml($text, $flags); $this->cacheSetTree($text, $flags, $xml); } // Fail if the number of elements exceeds acceptable limits // Do not attempt to generate the DOM $this->parser->mGeneratedPPNodeCount += substr_count($xml, '<'); $max = $this->parser->mOptions->getMaxGeneratedPPNodeCount(); if ($this->parser->mGeneratedPPNodeCount > $max) { // if ( $cacheable ) { ... } throw new MWException(__METHOD__ . ': generated node count limit exceeded'); } $dom = new DOMDocument(); MediaWiki\suppressWarnings(); $result = $dom->loadXML($xml); MediaWiki\restoreWarnings(); if (!$result) { // Try running the XML through UtfNormal to get rid of invalid characters $xml = UtfNormal\Validator::cleanUp($xml); // 1 << 19 == XML_PARSE_HUGE, needed so newer versions of libxml2 // don't barf when the XML is >256 levels deep. $result = $dom->loadXML($xml, 1 << 19); } if ($result) { $obj = new PPNode_DOM($dom->documentElement); } // if ( $cacheable ) { ... } if (!$result) { throw new MWException(__METHOD__ . ' generated invalid XML'); } return $obj; }
/** * Log to a file without getting "file size exceeded" signals. * * Can also log to UDP with the syntax udp://host:port/prefix. This will send * lines to the specified port, prefixed by the specified prefix and a space. * * @param string $text * @param string $file Filename */ public static function emit($text, $file) { if (substr($file, 0, 4) == 'udp:') { $transport = UDPTransport::newFromString($file); $transport->emit($text); } else { \MediaWiki\suppressWarnings(); $exists = file_exists($file); $size = $exists ? filesize($file) : false; if (!$exists || $size !== false && $size + strlen($text) < 0x7fffffff) { file_put_contents($file, $text, FILE_APPEND); } \MediaWiki\restoreWarnings(); } }
/** * @dataProvider importProvider */ public function testImportHandleRevisionXMLTag_hook($xml, $allowImport, $expectedException = null) { // WikiImporter tried to register this protocol every time, so unregister first to avoid errors. \MediaWiki\suppressWarnings(); stream_wrapper_unregister('uploadsource'); \MediaWiki\restoreWarnings(); WikibaseRepo::getDefaultInstance()->getSettings()->setSetting('allowEntityImport', $allowImport); $source = new ImportStringSource($xml); $importer = new WikiImporter($source, ConfigFactory::getDefaultInstance()->makeConfig('main')); $importer->setNoticeCallback(function () { // Do nothing for now. Could collect and compare notices. }); $importer->setPageOutCallback(function () { }); if ($expectedException !== null) { $this->setExpectedException($expectedException); } $importer->doImport(); $this->assertTrue(true); // make PHPUnit happy }
/** * Check selected RFC 7232 precondition headers * * RFC 7232 envisions a particular model where you send your request to "a * resource", and for write requests that you can read "the resource" by * changing the method to GET. When the API receives a GET request, it * works out even though "the resource" from RFC 7232's perspective might * be many resources from MediaWiki's perspective. But it totally fails for * a POST, since what HTTP sees as "the resource" is probably just * "/api.php" with all the interesting bits in the body. * * Therefore, we only support RFC 7232 precondition headers for GET (and * HEAD). That means we don't need to bother with If-Match and * If-Unmodified-Since since they only apply to modification requests. * * And since we don't support Range, If-Range is ignored too. * * @since 1.26 * @param ApiBase $module Api module being used * @return bool True on success, false should exit immediately */ protected function checkConditionalRequestHeaders($module) { if ($this->mInternalMode) { // No headers to check in internal mode return true; } if ($this->getRequest()->getMethod() !== 'GET' && $this->getRequest()->getMethod() !== 'HEAD') { // Don't check POSTs return true; } $return304 = false; $ifNoneMatch = array_diff($this->getRequest()->getHeader('If-None-Match', WebRequest::GETHEADER_LIST) ?: array(), array('')); if ($ifNoneMatch) { if ($ifNoneMatch === array('*')) { // API responses always "exist" $etag = '*'; } else { $etag = $module->getConditionalRequestData('etag'); } } if ($ifNoneMatch && $etag !== null) { $test = substr($etag, 0, 2) === 'W/' ? substr($etag, 2) : $etag; $match = array_map(function ($s) { return substr($s, 0, 2) === 'W/' ? substr($s, 2) : $s; }, $ifNoneMatch); $return304 = in_array($test, $match, true); } else { $value = trim($this->getRequest()->getHeader('If-Modified-Since')); // Some old browsers sends sizes after the date, like this: // Wed, 20 Aug 2003 06:51:19 GMT; length=5202 // Ignore that. $i = strpos($value, ';'); if ($i !== false) { $value = trim(substr($value, 0, $i)); } if ($value !== '') { try { $ts = new MWTimestamp($value); if ($ts->getTimestamp(TS_RFC2822) === $value || $ts->format('l, d-M-y H:i:s') . ' GMT' === $value || $ts->format('D M j H:i:s Y') === $value || $ts->format('D M j H:i:s Y') === $value) { $lastMod = $module->getConditionalRequestData('last-modified'); if ($lastMod !== null) { // Mix in some MediaWiki modification times $modifiedTimes = array('page' => $lastMod, 'user' => $this->getUser()->getTouched(), 'epoch' => $this->getConfig()->get('CacheEpoch')); if ($this->getConfig()->get('UseSquid')) { // T46570: the core page itself may not change, but resources might $modifiedTimes['sepoch'] = wfTimestamp(TS_MW, time() - $this->getConfig()->get('SquidMaxage')); } Hooks::run('OutputPageCheckLastModified', array(&$modifiedTimes)); $lastMod = max($modifiedTimes); $return304 = wfTimestamp(TS_MW, $lastMod) <= $ts->getTimestamp(TS_MW); } } } catch (TimestampException $e) { // Invalid timestamp, ignore it } } } if ($return304) { $this->getRequest()->response()->statusHeader(304); // Avoid outputting the compressed representation of a zero-length body MediaWiki\suppressWarnings(); ini_set('zlib.output_compression', 0); MediaWiki\restoreWarnings(); wfClearOutputBuffers(); return false; } return true; }