/** * Constructor */ function wfSpecialRecentchanges($par, $specialPage) { global $wgUser, $wgOut, $wgRequest, $wgUseRCPatrol; global $wgRCShowWatchingUsers, $wgShowUpdatedMarker; global $wgAllowCategorizedRecentChanges; $fname = 'wfSpecialRecentchanges'; $userGroups = $wgUser->getGroups(); if (!$wgUser->isAllowed('patrol') || in_array('patrolblock', $userGroups)) { $wgOut->errorpage('nosuchspecialpage', 'nospecialpagetext'); return; } # Get query parameters $feedFormat = $wgRequest->getVal('feed'); /* Checkbox values can't be true by default, because * we cannot differentiate between unset and not set at all */ $defaults = array('days' => $wgUser->getDefaultOption('rcdays'), 'limit' => $wgUser->getDefaultOption('rclimit'), 'hideminor' => false, 'hidebots' => true, 'hideanons' => false, 'hideliu' => false, 'hidepatrolled' => false, 'hidemyself' => false, 'from' => '', 'namespace' => null, 'invert' => false, 'categories_any' => false, 'reverse' => false, 'featured' => false, 'categories_any' => false); extract($defaults); $days = $wgUser->getOption('rcdays', $defaults['days']); $days = $wgRequest->getInt('days', $days); $limit = $wgUser->getOption('rclimit', $defaults['limit']); # list( $limit, $offset ) = wfCheckLimits( 100, 'rclimit' ); $limit = $wgRequest->getInt('limit', $limit); /* order of selection: url > preferences > default */ $hideminor = $wgRequest->getBool('hideminor', $wgUser->getOption('hideminor') ? true : $defaults['hideminor']); # As a feed, use limited settings only if ($feedFormat) { global $wgFeedLimit; if ($limit > $wgFeedLimit) { $limit = $wgFeedLimit; } } else { $namespace = $wgRequest->getIntOrNull('namespace'); $invert = $wgRequest->getBool('invert', $defaults['invert']); //XXADDED $reverse = $wgRequest->getBool('reverse', $defaults['reverse']); $featured = $wgRequest->getBool('featured', $defaults['featured']); $hidebots = $wgRequest->getBool('hidebots', $defaults['hidebots']); $hideanons = $wgRequest->getBool('hideanons', $defaults['hideanons']); $hideliu = $wgRequest->getBool('hideliu', $defaults['hideliu']); $hidepatrolled = $wgRequest->getBool('hidepatrolled', $defaults['hidepatrolled']); $hidemyself = $wgRequest->getBool('hidemyself', $defaults['hidemyself']); $from = $wgRequest->getVal('from', $defaults['from']); # Get query parameters from path if ($par) { $bits = preg_split('/\\s*,\\s*/', trim($par)); foreach ($bits as $bit) { if ('hidebots' == $bit) { $hidebots = 1; } if ('bots' == $bit) { $hidebots = 0; } if ('hideminor' == $bit) { $hideminor = 1; } if ('minor' == $bit) { $hideminor = 0; } if ('hideliu' == $bit) { $hideliu = 1; } if ('hidepatrolled' == $bit) { $hidepatrolled = 1; } if ('hideanons' == $bit) { $hideanons = 1; } if ('hidemyself' == $bit) { $hidemyself = 1; } if (is_numeric($bit)) { $limit = $bit; } $m = array(); if (preg_match('/^limit=(\\d+)$/', $bit, $m)) { $limit = $m[1]; } if (preg_match('/^days=(\\d+)$/', $bit, $m)) { $days = $m[1]; } } } } if ($limit < 0 || $limit > 5000) { $limit = $defaults['limit']; } # Database connection and caching $dbr = wfGetDB(DB_SLAVE); list($recentchanges, $watchlist) = $dbr->tableNamesN('recentchanges', 'watchlist'); $cutoff_unixtime = time() - $days * 86400; $cutoff_unixtime = $cutoff_unixtime - $cutoff_unixtime % 86400; $cutoff = $dbr->timestamp($cutoff_unixtime); if (preg_match('/^[0-9]{14}$/', $from) and $from > wfTimestamp(TS_MW, $cutoff)) { $cutoff = $dbr->timestamp($from); } else { $from = $defaults['from']; } # 10 seconds server-side caching max $wgOut->setSquidMaxage(0); # Get last modified date, for client caching # Don't use this if we are using the patrol feature, patrol changes don't update the timestamp $lastmod = $dbr->selectField('recentchanges', 'MAX(rc_timestamp)', false, $fname); if ($feedFormat || !$wgUseRCPatrol) { if ($lastmod && $wgOut->checkLastModified($lastmod)) { # Client cache fresh and headers sent, nothing more to do. return; } } # It makes no sense to hide both anons and logged-in users # Where this occurs, force anons to be shown if ($hideanons && $hideliu) { $hideanons = false; } # Form WHERE fragments for all the options $hidem = $hideminor ? 'AND rc_minor = 0' : ''; $hidem .= $hidebots ? ' AND rc_bot = 0' : ''; $hidem .= $hideliu ? ' AND rc_user = 0' : ''; $hidem .= $wgUseRCPatrol && $hidepatrolled ? ' AND rc_patrolled = 0' : ''; $hidem .= $hideanons ? ' AND rc_user != 0' : ''; if ($hidemyself) { if ($wgUser->getID()) { $hidem .= ' AND rc_user != ' . $wgUser->getID(); } else { $hidem .= ' AND rc_user_text != ' . $dbr->addQuotes($wgUser->getName()); } } # Namespace filtering $hidem .= is_null($namespace) ? '' : ' AND rc_namespace' . ($invert ? '!=' : '=') . $namespace; //XXADDED $order = $reverse ? " ASC" : "DESC"; $ft = $featured ? " AND page_is_featured = 1 " : ""; // This is the big thing! $uid = $wgUser->getID(); //XXCHANGED // Perform query $forceclause = $dbr->useIndexClause("rc_timestamp"); $sql2 = "SELECT * FROM {$recentchanges} {$forceclause}" . ($uid ? "LEFT OUTER JOIN {$watchlist} ON wl_user={$uid} AND wl_title=rc_title AND wl_namespace=rc_namespace " : "") . " LEFT OUTER JOIN page ON page_title=rc_title AND page_namespace=rc_namespace " . "WHERE rc_timestamp >= '{$cutoff}' {$hidem} {$ft} " . "ORDER BY rc_timestamp {$order} "; $sql2 = $dbr->limitResult($sql2, $limit, 0); $res = $dbr->query($sql2, $fname); // Fetch results, prepare a batch link existence check query $rows = array(); $batch = new LinkBatch(); while ($row = $dbr->fetchObject($res)) { $rows[] = $row; if (!$feedFormat) { // User page and talk links $batch->add(NS_USER, $row->rc_user_text); $batch->add(NS_USER_TALK, $row->rc_user_text); } } $dbr->freeResult($res); if ($feedFormat) { rcOutputFeed($rows, $feedFormat, $limit, $hideminor, $lastmod); } else { # Web output... // Run existence checks $batch->execute(); $any = $wgRequest->getBool('categories_any', $defaults['categories_any']); // Output header if (!$specialPage->including()) { $wgOut->addWikiText('<div class="minor_text">' . wfMsgForContentNoTrans("recentchangestext") . '<br /></div>'); // Dump everything here $nondefaults = array(); wfAppendToArrayIfNotDefault('days', $days, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('limit', $limit, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hideminor', $hideminor, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hidebots', $hidebots, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hideanons', $hideanons, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hideliu', $hideliu, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hidepatrolled', $hidepatrolled, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hidemyself', $hidemyself, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('from', $from, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('namespace', $namespace, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('invert', $invert, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('categories_any', $any, $defaults, $nondefaults); // Add end of the texts $wgOut->addHTML('<div class="rcoptions">' . rcOptionsPanel($defaults, $nondefaults) . "\n"); //XXCHANGED $wgOut->addHTML(rcNamespaceForm($namespace, $invert, $reverse, $featured, $nondefaults, $any) . '</div>' . "\n"); //XXADDED global $wgLanguageCode; if ($wgUser->getID() > 0 && $wgLanguageCode == 'en') { $sk = $wgUser->getSkin(); $url = $wgRequest->getRequestURL(); if ($wgRequest->getVal('refresh', null) != null) { $url = str_replace("&refresh=1", "", $url); $url = str_replace("?refresh=1", "", $url); $wgOut->addHTML("<a href='{$url}' class='button secondary'>" . wfMsg('rc_turn_refresh_off') . "</a>"); } else { if (strpos($url, "?") !== false) { $url .= "&refresh=1"; } else { $url .= "?refresh=1"; } $wgOut->addHTML("<a href='{$url}' class='button secondary'>" . wfMsg('rc_turn_refresh_on') . "</a>"); } $wgOut->addHTML(" <a class='button secondary' href='#' onclick=\"open('/index.php?title=Special:RCBuddy&hidepatrolled=1&limit=200&featured=1', '', 'scrollbars=no,status=no,width=570,height=200,resizable=yes,titlebar=no');\">RC Buddy</a>"); } } // And now for the content $wgOut->setSyndicated(true); $list = ChangesList::newFromUser($wgUser); if ($wgAllowCategorizedRecentChanges) { $categories = trim($wgRequest->getVal('categories', "")); $categories = str_replace("|", "\n", $categories); $categories = explode("\n", $categories); rcFilterByCategories($rows, $categories, $any); } $s = $list->beginRecentChangesList(); $s .= "<div id='recentchanges'>\n"; $counter = 1; $showWatcherCount = $wgRCShowWatchingUsers && $wgUser->getOption('shownumberswatching'); $watcherCache = array(); foreach ($rows as $obj) { if ($limit == 0) { break; } if (!($hideminor && $obj->rc_minor) && !($hidepatrolled && $obj->rc_patrolled)) { $rc = RecentChange::newFromRow($obj); $rc->counter = $counter++; if ($wgShowUpdatedMarker && !empty($obj->wl_notificationtimestamp) && $obj->rc_timestamp >= $obj->wl_notificationtimestamp) { $rc->notificationtimestamp = true; } else { $rc->notificationtimestamp = false; } $rc->numberofWatchingusers = 0; // Default if ($showWatcherCount && $obj->rc_namespace >= 0) { if (!isset($watcherCache[$obj->rc_namespace][$obj->rc_title])) { $watcherCache[$obj->rc_namespace][$obj->rc_title] = $dbr->selectField('watchlist', 'COUNT(*)', array('wl_namespace' => $obj->rc_namespace, 'wl_title' => $obj->rc_title), __METHOD__ . '-watchers'); } $rc->numberofWatchingusers = $watcherCache[$obj->rc_namespace][$obj->rc_title]; } $rc->show_namespace = $namespace; $rc->invert = $invert; $rc->reverse = $reverse; $rc->featured = $featured; $s .= $list->recentChangesLine($rc, !empty($obj->wl_user)); --$limit; } } $s .= $list->endRecentChangesList(); $s .= "</div>\n"; $wgOut->addHTML($s); } }
/** * Constructor */ function wfSpecialRecentchanges($par, $specialPage) { global $wgUser, $wgOut, $wgRequest, $wgUseRCPatrol; global $wgRCShowWatchingUsers, $wgShowUpdatedMarker; global $wgAllowCategorizedRecentChanges; $fname = 'wfSpecialRecentchanges'; # Get query parameters $feedFormat = $wgRequest->getVal('feed'); /* Checkbox values can't be true by default, because * we cannot differentiate between unset and not set at all */ $defaults = array('days' => $wgUser->getDefaultOption('rcdays'), 'limit' => $wgUser->getDefaultOption('rclimit'), 'hideminor' => false, 'hidebots' => true, 'hideanons' => false, 'hideliu' => false, 'hidepatrolled' => false, 'hidemyself' => false, 'from' => '', 'namespace' => null, 'invert' => false, 'categories_any' => false); extract($defaults); $days = $wgUser->getOption('rcdays', $defaults['days']); $days = $wgRequest->getInt('days', $days); $limit = $wgUser->getOption('rclimit', $defaults['limit']); # list( $limit, $offset ) = wfCheckLimits( 100, 'rclimit' ); $limit = $wgRequest->getInt('limit', $limit); /* order of selection: url > preferences > default */ $hideminor = $wgRequest->getBool('hideminor', $wgUser->getOption('hideminor') ? true : $defaults['hideminor']); # As a feed, use limited settings only if ($feedFormat) { global $wgFeedLimit; if ($limit > $wgFeedLimit) { $limit = $wgFeedLimit; } } else { $namespace = $wgRequest->getIntOrNull('namespace'); $invert = $wgRequest->getBool('invert', $defaults['invert']); $hidebots = $wgRequest->getBool('hidebots', $defaults['hidebots']); $hideanons = $wgRequest->getBool('hideanons', $defaults['hideanons']); $hideliu = $wgRequest->getBool('hideliu', $defaults['hideliu']); $hidepatrolled = $wgRequest->getBool('hidepatrolled', $defaults['hidepatrolled']); $hidemyself = $wgRequest->getBool('hidemyself', $defaults['hidemyself']); $from = $wgRequest->getVal('from', $defaults['from']); # Get query parameters from path if ($par) { $bits = preg_split('/\\s*,\\s*/', trim($par)); foreach ($bits as $bit) { if ('hidebots' == $bit) { $hidebots = 1; } if ('bots' == $bit) { $hidebots = 0; } if ('hideminor' == $bit) { $hideminor = 1; } if ('minor' == $bit) { $hideminor = 0; } if ('hideliu' == $bit) { $hideliu = 1; } if ('hidepatrolled' == $bit) { $hidepatrolled = 1; } if ('hideanons' == $bit) { $hideanons = 1; } if ('hidemyself' == $bit) { $hidemyself = 1; } if (is_numeric($bit)) { $limit = $bit; } $m = array(); if (preg_match('/^limit=(\\d+)$/', $bit, $m)) { $limit = $m[1]; } if (preg_match('/^days=(\\d+)$/', $bit, $m)) { $days = $m[1]; } } } } if ($limit < 0 || $limit > 5000) { $limit = $defaults['limit']; } # Database connection and caching $dbr = wfGetDB(DB_SLAVE); list($recentchanges, $watchlist) = $dbr->tableNamesN('recentchanges', 'watchlist'); $cutoff_unixtime = time() - $days * 86400; $cutoff_unixtime = $cutoff_unixtime - $cutoff_unixtime % 86400; $cutoff = $dbr->timestamp($cutoff_unixtime); if (preg_match('/^[0-9]{14}$/', $from) and $from > wfTimestamp(TS_MW, $cutoff)) { $cutoff = $dbr->timestamp($from); } else { $from = $defaults['from']; } # 10 seconds server-side caching max $wgOut->setSquidMaxage(10); # Get last modified date, for client caching # Don't use this if we are using the patrol feature, patrol changes don't update the timestamp $lastmod = $dbr->selectField('recentchanges', 'MAX(rc_timestamp)', false, $fname); if ($feedFormat || !$wgUseRCPatrol) { if ($lastmod && $wgOut->checkLastModified($lastmod)) { # Client cache fresh and headers sent, nothing more to do. return; } } # It makes no sense to hide both anons and logged-in users # Where this occurs, force anons to be shown if ($hideanons && $hideliu) { $hideanons = false; } # Form WHERE fragments for all the options $hidem = $hideminor ? 'AND rc_minor = 0' : ''; $hidem .= $hidebots ? ' AND rc_bot = 0' : ''; $hidem .= $hideliu ? ' AND rc_user = 0' : ''; $hidem .= $wgUseRCPatrol && $hidepatrolled ? ' AND rc_patrolled = 0' : ''; $hidem .= $hideanons ? ' AND rc_user != 0' : ''; if ($hidemyself) { if ($wgUser->getID()) { $hidem .= ' AND rc_user != ' . $wgUser->getID(); } else { $hidem .= ' AND rc_user_text != ' . $dbr->addQuotes($wgUser->getName()); } } # Namespace filtering $hidem .= is_null($namespace) ? '' : ' AND rc_namespace' . ($invert ? '!=' : '=') . $namespace; // This is the big thing! $uid = $wgUser->getID(); // Perform query $forceclause = $dbr->useIndexClause("rc_timestamp"); $sql2 = "SELECT * FROM {$recentchanges} {$forceclause}" . ($uid ? "LEFT OUTER JOIN {$watchlist} ON wl_user={$uid} AND wl_title=rc_title AND wl_namespace=rc_namespace " : "") . "WHERE rc_timestamp >= '{$cutoff}' {$hidem} " . "ORDER BY rc_timestamp DESC"; $sql2 = $dbr->limitResult($sql2, $limit, 0); $res = $dbr->query($sql2, $fname); // Fetch results, prepare a batch link existence check query $rows = array(); $batch = new LinkBatch(); while ($row = $dbr->fetchObject($res)) { $rows[] = $row; if (!$feedFormat) { // User page link $title = Title::makeTitleSafe(NS_USER, $row->rc_user_text); $batch->addObj($title); // User talk $title = Title::makeTitleSafe(NS_USER_TALK, $row->rc_user_text); $batch->addObj($title); } } $dbr->freeResult($res); if ($feedFormat) { rcOutputFeed($rows, $feedFormat, $limit, $hideminor, $lastmod); } else { # Web output... // Run existence checks $batch->execute(); $any = $wgRequest->getBool('categories_any', $defaults['categories_any']); // Output header if (!$specialPage->including()) { $wgOut->addWikiText(wfMsgForContentNoTrans("recentchangestext")); // Dump everything here $nondefaults = array(); wfAppendToArrayIfNotDefault('days', $days, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('limit', $limit, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hideminor', $hideminor, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hidebots', $hidebots, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hideanons', $hideanons, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hideliu', $hideliu, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hidepatrolled', $hidepatrolled, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hidemyself', $hidemyself, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('from', $from, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('namespace', $namespace, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('invert', $invert, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('categories_any', $any, $defaults, $nondefaults); // Add end of the texts $wgOut->addHTML('<div class="rcoptions">' . rcOptionsPanel($defaults, $nondefaults) . "\n"); $wgOut->addHTML(rcNamespaceForm($namespace, $invert, $nondefaults, $any) . '</div>' . "\n"); } // And now for the content $list = ChangesList::newFromUser($wgUser); if ($wgAllowCategorizedRecentChanges) { $categories = trim($wgRequest->getVal('categories', "")); $categories = str_replace("|", "\n", $categories); $categories = explode("\n", $categories); rcFilterByCategories($rows, $categories, $any); } $s = $list->beginRecentChangesList(); $counter = 1; foreach ($rows as $obj) { if ($limit == 0) { break; } if (!($hideminor && $obj->rc_minor) && !($hidepatrolled && $obj->rc_patrolled)) { $rc = RecentChange::newFromRow($obj); $rc->counter = $counter++; if ($wgShowUpdatedMarker && !empty($obj->wl_notificationtimestamp) && $obj->rc_timestamp >= $obj->wl_notificationtimestamp) { $rc->notificationtimestamp = true; } else { $rc->notificationtimestamp = false; } if ($wgRCShowWatchingUsers && $wgUser->getOption('shownumberswatching')) { $sql3 = "SELECT COUNT(*) AS n FROM {$watchlist} WHERE wl_title='" . $dbr->strencode($obj->rc_title) . "' AND wl_namespace={$obj->rc_namespace}"; $res3 = $dbr->query($sql3, 'wfSpecialRecentChanges'); $x = $dbr->fetchObject($res3); $rc->numberofWatchingusers = $x->n; } else { $rc->numberofWatchingusers = 0; } $s .= $list->recentChangesLine($rc, !empty($obj->wl_user)); --$limit; } } $s .= $list->endRecentChangesList(); $wgOut->addHTML($s); } }
/** * Constructor */ function wfSpecialRecentchanges($par, $specialPage) { global $wgUser, $wgOut, $wgLang, $wgContLang, $wgTitle, $wgMemc, $wgDBname; global $wgRequest, $wgSitename, $wgLanguageCode, $wgContLanguageCode; global $wgFeedClasses, $wgUseRCPatrol; global $wgRCShowCurrentRevisionOnly, $wgRCShowWatchingUsers, $wgShowUpdatedMarker; global $wgLinkCache; $fname = 'wfSpecialRecentchanges'; # Get query parameters $feedFormat = $wgRequest->getVal('feed'); $defaults = array('days' => $wgUser->getDefaultOption('rcdays'), 'limit' => $wgUser->getDefaultOption('rclimit'), 'hideminor' => false, 'hidebots' => true, 'hideliu' => false, 'hidepatrolled' => false, 'from' => '', 'namespace' => null, 'invert' => false); extract($defaults); $days = $wgUser->getOption('rcdays'); if (!$days) { $days = $defaults['days']; } $days = $wgRequest->getInt('days', $days); $limit = $wgUser->getOption('rclimit'); if (!$limit) { $limit = $defaults['limit']; } # list( $limit, $offset ) = wfCheckLimits( 100, 'rclimit' ); $limit = $wgRequest->getInt('limit', $limit); /* order of selection: url > preferences > default */ $hideminor = $wgRequest->getBool('hideminor', $wgUser->getOption('hideminor') ? true : $defaults['hideminor']); # As a feed, use limited settings only if ($feedFormat) { global $wgFeedLimit; if ($limit > $wgFeedLimit) { $options['limit'] = $wgFeedLimit; } } else { $namespace = $wgRequest->getIntOrNull('namespace'); $invert = $wgRequest->getBool('invert', $defaults['invert']); $hidebots = $wgRequest->getBool('hidebots', $defaults['hidebots']); $hideliu = $wgRequest->getBool('hideliu', $defaults['hideliu']); $hidepatrolled = $wgRequest->getBool('hidepatrolled', $defaults['hidepatrolled']); $from = $wgRequest->getVal('from', $defaults['from']); # Get query parameters from path if ($par) { $bits = preg_split('/\\s*,\\s*/', trim($par)); foreach ($bits as $bit) { if ('hidebots' == $bit) { $hidebots = 1; } if ('bots' == $bit) { $hidebots = 0; } if ('hideminor' == $bit) { $hideminor = 1; } if ('minor' == $bit) { $hideminor = 0; } if ('hideliu' == $bit) { $hideliu = 1; } if ('hidepatrolled' == $bit) { $hidepatrolled = 1; } if (is_numeric($bit)) { $limit = $bit; } if (preg_match('/^limit=(\\d+)$/', $bit, $m)) { $limit = $m[1]; } if (preg_match('/^days=(\\d+)$/', $bit, $m)) { $days = $m[1]; } } } } if ($limit < 0 || $limit > 5000) { $limit = $defaults['limit']; } # Database connection and caching $dbr =& wfGetDB(DB_SLAVE); extract($dbr->tableNames('recentchanges', 'watchlist', 'page')); $cutoff_unixtime = time() - $days * 86400; $cutoff_unixtime = $cutoff_unixtime - $cutoff_unixtime % 86400; $cutoff = $dbr->timestamp($cutoff_unixtime); if (preg_match('/^[0-9]{14}$/', $from) and $from > wfTimestamp(TS_MW, $cutoff)) { $cutoff = $dbr->timestamp($from); } else { $from = $defaults['from']; } # 10 seconds server-side caching max $wgOut->setSquidMaxage(10); # Get last modified date, for client caching # Don't use this if we are using the patrol feature, patrol changes don't update the timestamp $lastmod = $dbr->selectField('recentchanges', 'MAX(rc_timestamp)', false, $fname); if ($feedFormat || !$wgUseRCPatrol) { if ($lastmod && $wgOut->checkLastModified($lastmod)) { # Client cache fresh and headers sent, nothing more to do. return; } } $hidem = $hideminor ? 'AND rc_minor=0' : ''; $hidem .= $hidebots ? ' AND rc_bot=0' : ''; $hidem .= $hideliu ? ' AND rc_user=0' : ''; $hidem .= $hidepatrolled ? ' AND rc_patrolled=0' : ''; $hidem .= is_null($namespace) ? '' : ' AND rc_namespace' . ($invert ? '!=' : '=') . $namespace; // This is the big thing! $uid = $wgUser->getID(); // Perform query if ($wgRCShowCurrentRevisionOnly && $wgUser->getOption('rccurrevonly')) { $sql2 = "SELECT {$recentchanges}.*" . ($uid ? ",wl_user,wl_notificationtimestamp,wl_lastvisitedrevision" : "") . " FROM {$recentchanges},{$page} " . ($uid ? "LEFT OUTER JOIN {$watchlist} ON wl_user={$uid} AND wl_title=rc_title AND wl_namespace=rc_namespace " : "") . "WHERE rc_timestamp > '{$cutoff}' {$hidem} AND rc_this_oldid=page_latest " . "ORDER BY rc_timestamp DESC LIMIT {$limit}"; } else { $sql2 = "SELECT {$recentchanges}.*" . ($uid ? ",wl_user,wl_notificationtimestamp,wl_lastvisitedrevision" : "") . " FROM {$recentchanges} " . ($uid ? "LEFT OUTER JOIN {$watchlist} ON wl_user={$uid} AND wl_title=rc_title AND wl_namespace=rc_namespace " : "") . "WHERE rc_timestamp > '{$cutoff}' {$hidem} " . "ORDER BY rc_timestamp DESC LIMIT {$limit}"; } $res = $dbr->query($sql2, $fname); // Fetch results, prepare a batch link existence check query $rows = array(); $batch = new LinkBatch(); while ($row = $dbr->fetchObject($res)) { $rows[] = $row; // User page link $title = Title::makeTitleSafe(NS_USER, $row->rc_user_text); $batch->addObj($title); // User talk $title = Title::makeTitleSafe(NS_USER_TALK, $row->rc_user_text); $batch->addObj($title); } $dbr->freeResult($res); // Run existence checks $batch->execute($wgLinkCache); if ($feedFormat) { rcOutputFeed($rows, $feedFormat, $limit, $hideminor, $lastmod); } else { # Web output... // Output header if (!$specialPage->including()) { $wgOut->addWikiText(wfMsgForContent("recentchangestext")); // Dump everything here $nondefaults = array(); wfAppendToArrayIfNotDefault('days', $days, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('limit', $limit, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hideminor', $hideminor, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hidebots', $hidebots, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hideliu', $hideliu, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('hidepatrolled', $hidepatrolled, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('from', $from, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('namespace', $namespace, $defaults, $nondefaults); wfAppendToArrayIfNotDefault('invert', $invert, $defaults, $nondefaults); // Add end of the texts $wgOut->addHTML('<div class="rcoptions">' . rcOptionsPanel($defaults, $nondefaults)); $wgOut->addHTML(rcNamespaceForm($namespace, $invert, $nondefaults) . '</div>'); } // And now for the content $sk = $wgUser->getSkin(); $wgOut->setSyndicated(true); $list =& new ChangesList($sk); $s = $list->beginRecentChangesList(); $counter = 1; foreach ($rows as $obj) { if ($limit == 0) { break; } if (!($hideminor && $obj->rc_minor) && !($hidepatrolled && $obj->rc_patrolled)) { $rc = RecentChange::newFromRow($obj); $rc->counter = $counter++; if ($wgShowUpdatedMarker && $wgUser->getOption('showupdated') && !empty($obj->wl_notificationtimestamp) && $obj->rc_timestamp >= $obj->wl_notificationtimestamp) { $rc->notificationtimestamp = true; } else { $rc->notificationtimestamp = false; } if ($wgRCShowWatchingUsers && $wgUser->getOption('shownumberswatching')) { $sql3 = "SELECT COUNT(*) AS n FROM {$watchlist} WHERE wl_title='" . $dbr->strencode($obj->rc_title) . "' AND wl_namespace={$obj->rc_namespace}"; $res3 = $dbr->query($sql3, 'wfSpecialRecentChanges'); $x = $dbr->fetchObject($res3); $rc->numberofWatchingusers = $x->n; } else { $rc->numberofWatchingusers = 0; } $rc->lastvisitedrevision = $uid ? $obj->wl_lastvisitedrevision : 0; $s .= $list->recentChangesLine($rc, !empty($obj->wl_user)); --$limit; } } $s .= $list->endRecentChangesList(); $wgOut->addHTML($s); } }