article.php
来自「php 开发的内容管理系统」· PHP 代码 · 共 2,311 行 · 第 1/5 页
PHP
2,311 行
$this->mCounter = 0; } else { $dbr =& wfGetDB( DB_SLAVE ); $this->mCounter = $dbr->selectField( 'page', 'page_counter', array( 'page_id' => $id ), 'Article::getCount', $this->getSelectOptions() ); } } return $this->mCounter; } /** * Determine whether a page would be suitable for being counted as an * article in the site_stats table based on the title & its content * * @param $text String: text to analyze * @return bool */ function isCountable( $text ) { global $wgUseCommaCount, $wgContentNamespaces; $token = $wgUseCommaCount ? ',' : '[['; return array_search( $this->mTitle->getNamespace(), $wgContentNamespaces ) !== false && ! $this->isRedirect( $text ) && in_string( $token, $text ); } /** * Tests if the article text represents a redirect * * @param $text String: FIXME * @return bool */ function isRedirect( $text = false ) { if ( $text === false ) { $this->loadContent(); $titleObj = Title::newFromRedirect( $this->fetchContent() ); } else { $titleObj = Title::newFromRedirect( $text ); } return $titleObj !== NULL; } /** * Returns true if the currently-referenced revision is the current edit * to this page (and it exists). * @return bool */ function isCurrent() { return $this->exists() && isset( $this->mRevision ) && $this->mRevision->isCurrent(); } /** * Loads everything except the text * This isn't necessary for all uses, so it's only done if needed. * @private */ function loadLastEdit() { if ( -1 != $this->mUser ) return; # New or non-existent articles have no user information $id = $this->getID(); if ( 0 == $id ) return; $this->mLastRevision = Revision::loadFromPageId( $this->getDB(), $id ); if( !is_null( $this->mLastRevision ) ) { $this->mUser = $this->mLastRevision->getUser(); $this->mUserText = $this->mLastRevision->getUserText(); $this->mTimestamp = $this->mLastRevision->getTimestamp(); $this->mComment = $this->mLastRevision->getComment(); $this->mMinorEdit = $this->mLastRevision->isMinor(); $this->mRevIdFetched = $this->mLastRevision->getID(); } } function getTimestamp() { // Check if the field has been filled by ParserCache::get() if ( !$this->mTimestamp ) { $this->loadLastEdit(); } return wfTimestamp(TS_MW, $this->mTimestamp); } function getUser() { $this->loadLastEdit(); return $this->mUser; } function getUserText() { $this->loadLastEdit(); return $this->mUserText; } function getComment() { $this->loadLastEdit(); return $this->mComment; } function getMinorEdit() { $this->loadLastEdit(); return $this->mMinorEdit; } function getRevIdFetched() { $this->loadLastEdit(); return $this->mRevIdFetched; } /** * @todo Document, fixme $offset never used. * @param $limit Integer: default 0. * @param $offset Integer: default 0. */ function getContributors($limit = 0, $offset = 0) { # XXX: this is expensive; cache this info somewhere. $title = $this->mTitle; $contribs = array(); $dbr =& wfGetDB( DB_SLAVE ); $revTable = $dbr->tableName( 'revision' ); $userTable = $dbr->tableName( 'user' ); $encDBkey = $dbr->addQuotes( $title->getDBkey() ); $ns = $title->getNamespace(); $user = $this->getUser(); $pageId = $this->getId(); $sql = "SELECT rev_user, rev_user_text, user_real_name, MAX(rev_timestamp) as timestamp FROM $revTable LEFT JOIN $userTable ON rev_user = user_id WHERE rev_page = $pageId AND rev_user != $user GROUP BY rev_user, rev_user_text, user_real_name ORDER BY timestamp DESC"; if ($limit > 0) { $sql .= ' LIMIT '.$limit; } $sql .= ' '. $this->getSelectOptions(); $res = $dbr->query($sql, __METHOD__); while ( $line = $dbr->fetchObject( $res ) ) { $contribs[] = array($line->rev_user, $line->rev_user_text, $line->user_real_name); } $dbr->freeResult($res); return $contribs; } /** * This is the default action of the script: just view the page of * the given title. */ function view() { global $wgUser, $wgOut, $wgRequest, $wgContLang; global $wgEnableParserCache, $wgStylePath, $wgUseRCPatrol, $wgParser; global $wgUseTrackbacks, $wgNamespaceRobotPolicies; $sk = $wgUser->getSkin(); wfProfileIn( __METHOD__ ); $parserCache =& ParserCache::singleton(); $ns = $this->mTitle->getNamespace(); # shortcut # Get variables from query string $oldid = $this->getOldID(); # getOldID may want us to redirect somewhere else if ( $this->mRedirectUrl ) { $wgOut->redirect( $this->mRedirectUrl ); wfProfileOut( __METHOD__ ); return; } $diff = $wgRequest->getVal( 'diff' ); $rcid = $wgRequest->getVal( 'rcid' ); $rdfrom = $wgRequest->getVal( 'rdfrom' ); $wgOut->setArticleFlag( true ); if ( isset( $wgNamespaceRobotPolicies[$ns] ) ) { $policy = $wgNamespaceRobotPolicies[$ns]; } else { $policy = 'index,follow'; } $wgOut->setRobotpolicy( $policy ); # If we got diff and oldid in the query, we want to see a # diff page instead of the article. if ( !is_null( $diff ) ) { require_once( 'DifferenceEngine.php' ); $wgOut->setPageTitle( $this->mTitle->getPrefixedText() ); $de = new DifferenceEngine( $this->mTitle, $oldid, $diff, $rcid ); // DifferenceEngine directly fetched the revision: $this->mRevIdFetched = $de->mNewid; $de->showDiffPage(); if( $diff == 0 ) { # Run view updates for current revision only $this->viewUpdates(); } wfProfileOut( __METHOD__ ); return; } if ( empty( $oldid ) && $this->checkTouched() ) { $wgOut->setETag($parserCache->getETag($this, $wgUser)); if( $wgOut->checkLastModified( $this->mTouched ) ){ wfProfileOut( __METHOD__ ); return; } else if ( $this->tryFileCache() ) { # tell wgOut that output is taken care of $wgOut->disable(); $this->viewUpdates(); wfProfileOut( __METHOD__ ); return; } } # Should the parser cache be used? $pcache = $wgEnableParserCache && intval( $wgUser->getOption( 'stubthreshold' ) ) == 0 && $this->exists() && empty( $oldid ); wfDebug( 'Article::view using parser cache: ' . ($pcache ? 'yes' : 'no' ) . "\n" ); if ( $wgUser->getOption( 'stubthreshold' ) ) { wfIncrStats( 'pcache_miss_stub' ); } $wasRedirected = false; if ( isset( $this->mRedirectedFrom ) ) { // This is an internally redirected page view. // We'll need a backlink to the source page for navigation. if ( wfRunHooks( 'ArticleViewRedirect', array( &$this ) ) ) { $sk = $wgUser->getSkin(); $redir = $sk->makeKnownLinkObj( $this->mRedirectedFrom, '', 'redirect=no' ); $s = wfMsg( 'redirectedfrom', $redir ); $wgOut->setSubtitle( $s ); $wasRedirected = true; } } elseif ( !empty( $rdfrom ) ) { // This is an externally redirected view, from some other wiki. // If it was reported from a trusted site, supply a backlink. global $wgRedirectSources; if( $wgRedirectSources && preg_match( $wgRedirectSources, $rdfrom ) ) { $sk = $wgUser->getSkin(); $redir = $sk->makeExternalLink( $rdfrom, $rdfrom ); $s = wfMsg( 'redirectedfrom', $redir ); $wgOut->setSubtitle( $s ); $wasRedirected = true; } } $outputDone = false; if ( $pcache ) { if ( $wgOut->tryParserCache( $this, $wgUser ) ) { $outputDone = true; } } if ( !$outputDone ) { $text = $this->getContent(); if ( $text === false ) { # Failed to load, replace text with error message $t = $this->mTitle->getPrefixedText(); if( $oldid ) { $t .= ',oldid='.$oldid; $text = wfMsg( 'missingarticle', $t ); } else { $text = wfMsg( 'noarticletext', $t ); } } # Another whitelist check in case oldid is altering the title if ( !$this->mTitle->userCanRead() ) { $wgOut->loginToUse(); $wgOut->output(); exit; } # We're looking at an old revision if ( !empty( $oldid ) ) { $wgOut->setRobotpolicy( 'noindex,nofollow' ); if( is_null( $this->mRevision ) ) { // FIXME: This would be a nice place to load the 'no such page' text. } else { $this->setOldSubtitle( isset($this->mOldId) ? $this->mOldId : $oldid ); if( $this->mRevision->isDeleted( Revision::DELETED_TEXT ) ) { if( !$this->mRevision->userCan( Revision::DELETED_TEXT ) ) { $wgOut->addWikiText( wfMsg( 'rev-deleted-text-permission' ) ); $wgOut->setPageTitle( $this->mTitle->getPrefixedText() ); return; } else { $wgOut->addWikiText( wfMsg( 'rev-deleted-text-view' ) ); // and we are allowed to see... } } } } } if( !$outputDone ) { /** * @fixme: this hook doesn't work most of the time, as it doesn't * trigger when the parser cache is used. */ wfRunHooks( 'ArticleViewHeader', array( &$this ) ) ; $wgOut->setRevisionId( $this->getRevIdFetched() ); # wrap user css and user js in pre and don't parse # XXX: use $this->mTitle->usCssJsSubpage() when php is fixed/ a workaround is found if ( $ns == NS_USER && preg_match('/\\/[\\w]+\\.(css|js)$/', $this->mTitle->getDBkey()) ) { $wgOut->addWikiText( wfMsg('clearyourcache')); $wgOut->addHTML( '<pre>'.htmlspecialchars($this->mContent)."\n</pre>" ); } else if ( $rt = Title::newFromRedirect( $text ) ) { # Display redirect $imageDir = $wgContLang->isRTL() ? 'rtl' : 'ltr'; $imageUrl = $wgStylePath.'/common/images/redirect' . $imageDir . '.png'; # Don't overwrite the subtitle if this was an old revision if( !$wasRedirected && $this->isCurrent() ) { $wgOut->setSubtitle( wfMsgHtml( 'redirectpagesub' ) ); } $targetUrl = $rt->escapeLocalURL(); #聽fixme unused $titleText : $titleText = htmlspecialchars( $rt->getPrefixedText() ); $link = $sk->makeLinkObj( $rt ); $wgOut->addHTML( '<img src="'.$imageUrl.'" alt="#REDIRECT" />' . '<span class="redirectText">'.$link.'</span>' ); $parseout = $wgParser->parse($text, $this->mTitle, ParserOptions::newFromUser($wgUser)); $wgOut->addParserOutputNoText( $parseout ); } else if ( $pcache ) { # Display content and save to parser cache $wgOut->addPrimaryWikiText( $text, $this ); } else { # Display content, don't attempt to save to parser cache # Don't show section-edit links on old revisions... this way lies madness. if( !$this->isCurrent() ) { $oldEditSectionSetting = $wgOut->mParserOptions->setEditSection( false ); } # Display content and don't save to parser cache $wgOut->addPrimaryWikiText( $text, $this, false ); if( !$this->isCurrent() ) { $wgOut->mParserOptions->setEditSection( $oldEditSectionSetting ); } } } /* title may have been set from the cache */ $t = $wgOut->getPageTitle(); if( empty( $t ) ) { $wgOut->setPageTitle( $this->mTitle->getPrefixedText() ); } # check if we're displaying a [[User talk:x.x.x.x]] anonymous talk page if( $ns == NS_USER_TALK && User::isIP( $this->mTitle->getText() ) ) { $wgOut->addWikiText( wfMsg('anontalkpagetext') ); } # If we have been passed an &rcid= parameter, we want to give the user a # chance to mark this new article as patrolled. if ( $wgUseRCPatrol && !is_null( $rcid ) && $rcid != 0 && $wgUser->isAllowed( 'patrol' ) ) { $wgOut->addHTML( "<div class='patrollink'>" . wfMsg ( 'markaspatrolledlink', $sk->makeKnownLinkObj( $this->mTitle, wfMsg('markaspatrolledtext'), "action=markpatrolled&rcid=$rcid" ) ) . '</div>' ); } # Trackbacks if ($wgUseTrackbacks) $this->addTrackbacks(); $this->viewUpdates(); wfProfileOut( __METHOD__ ); } function addTrackbacks() { global $wgOut, $wgUser; $dbr =& wfGetDB(DB_SLAVE); $tbs = $dbr->select( /* FROM */ 'trackbacks', /* SELECT */ array('tb_id', 'tb_title', 'tb_url', 'tb_ex', 'tb_name'), /* WHERE */ array('tb_page' => $this->getID()) ); if (!$dbr->numrows($tbs)) return; $tbtext = ""; while ($o = $dbr->fetchObject($tbs)) { $rmvtxt = ""; if ($wgUser->isAllowed( 'trackback' )) { $delurl = $this->mTitle->getFullURL("action=deletetrackback&tbid=" . $o->tb_id . "&token=" . $wgUser->editToken()); $rmvtxt = wfMsg('trackbackremove', $delurl); } $tbtext .= wfMsg(strlen($o->tb_ex) ? 'trackbackexcerpt' : 'trackback', $o->tb_title, $o->tb_url, $o->tb_ex, $o->tb_name, $rmvtxt); } $wgOut->addWikitext(wfMsg('trackbackbox', $tbtext)); } function deletetrackback() { global $wgUser, $wgRequest, $wgOut, $wgTitle; if (!$wgUser->matchEditToken($wgRequest->getVal('token'))) { $wgOut->addWikitext(wfMsg('sessionfailure')); return; } if ((!$wgUser->isAllowed('delete'))) { $wgOut->sysopRequired(); return; } if (wfReadOnly()) { $wgOut->readOnlyPage(); return; } $db =& wfGetDB(DB_MASTER); $db->delete('trackbacks', array('tb_id' => $wgRequest->getInt('tbid'))); $wgTitle->invalidateCache(); $wgOut->addWikiText(wfMsg('trackbackdeleteok')); } function render() { global $wgOut; $wgOut->setArticleBodyOnly(true); $this->view(); } /** * Handle action=purge */ function purge() { global $wgUser, $wgRequest, $wgOut; if ( $wgUser->isLoggedIn() || $wgRequest->wasPosted() ) { if( wfRunHooks( 'ArticlePurge', array( &$this ) ) ) { $this->doPurge(); } } else { $msg = $wgOut->parse( wfMsg( 'confirm_purge' ) ); $action = $this->mTitle->escapeLocalURL( 'action=purge' ); $button = htmlspecialchars( wfMsg( 'confirm_purge_button' ) ); $msg = str_replace( '$1', "<form method=\"post\" action=\"$action\">\n" .
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?