Index: trunk/phase3/includes/Article.php |
— | — | @@ -305,7 +305,7 @@ |
306 | 306 | |
307 | 307 | $lc =& LinkCache::singleton(); |
308 | 308 | if ( $data ) { |
309 | | - $lc->addGoodLinkObj( $data->page_id, $this->mTitle ); |
| 309 | + $lc->addGoodLinkObj( $data->page_id, $this->mTitle, $data->page_len, $data->page_is_redirect ); |
310 | 310 | |
311 | 311 | $this->mTitle->mArticleID = $data->page_id; |
312 | 312 | |
Index: trunk/phase3/includes/LinkBatch.php |
— | — | @@ -96,7 +96,7 @@ |
97 | 97 | $remaining = $this->data; |
98 | 98 | while ( $row = $res->fetchObject() ) { |
99 | 99 | $title = Title::newFromRow( $row ); |
100 | | - $cache->addGoodLinkObj( $row->page_id, $title ); |
| 100 | + $cache->addGoodLinkObj( $row->page_id, $title, $row->page_len, $row->page_is_redirect ); |
101 | 101 | $ids[$title->getPrefixedDBkey()] = $row->page_id; |
102 | 102 | unset( $remaining[$row->page_namespace][$row->page_title] ); |
103 | 103 | } |
Index: trunk/phase3/includes/Parser.php |
— | — | @@ -4028,7 +4028,7 @@ |
4029 | 4029 | while ( $s = $dbr->fetchObject($res) ) { |
4030 | 4030 | $title = Title::newFromRow( $s ); |
4031 | 4031 | $pdbk = $title->getPrefixedDBkey(); |
4032 | | - $linkCache->addGoodLinkObj( $s->page_id, $title ); |
| 4032 | + $linkCache->addGoodLinkObj( $s->page_id, $title, $s->page_len, $s->page_is_redirect ); |
4033 | 4033 | $this->mOutput->addLink( $title, $s->page_id ); |
4034 | 4034 | $colours[$pdbk] = $sk->getLinkColour( $title, $threshold ); |
4035 | 4035 | //add id to the extension todolist |
— | — | @@ -4110,7 +4110,7 @@ |
4111 | 4111 | $holderKeys = array(); |
4112 | 4112 | if(isset($variantMap[$varPdbk])){ |
4113 | 4113 | $holderKeys = $variantMap[$varPdbk]; |
4114 | | - $linkCache->addGoodLinkObj( $s->page_id, $variantTitle ); |
| 4114 | + $linkCache->addGoodLinkObj( $s->page_id, $variantTitle, $s->page_len, $s->page_is_redirect ); |
4115 | 4115 | $this->mOutput->addLink( $variantTitle, $s->page_id ); |
4116 | 4116 | } |
4117 | 4117 | |
Index: trunk/phase3/includes/WatchlistEditor.php |
— | — | @@ -217,7 +217,7 @@ |
218 | 218 | if( $title instanceof Title ) { |
219 | 219 | // Update the link cache while we're at it |
220 | 220 | if( $row->page_id ) { |
221 | | - $cache->addGoodLinkObj( $row->page_id, $title ); |
| 221 | + $cache->addGoodLinkObj( $row->page_id, $title, $row->page_len, $row->page_is_redirect ); |
222 | 222 | } else { |
223 | 223 | $cache->addBadLinkObj( $title ); |
224 | 224 | } |
Index: trunk/phase3/includes/filerepo/File.php |
— | — | @@ -852,7 +852,7 @@ |
853 | 853 | if ( $db->numRows( $res ) ) { |
854 | 854 | while ( $row = $db->fetchObject( $res ) ) { |
855 | 855 | if ( $titleObj = Title::newFromRow( $row ) ) { |
856 | | - $linkCache->addGoodLinkObj( $row->page_id, $titleObj ); |
| 856 | + $linkCache->addGoodLinkObj( $row->page_id, $titleObj, $row->page_len, $row->page_is_redirect ); |
857 | 857 | $retVal[] = $titleObj; |
858 | 858 | } |
859 | 859 | } |
Index: trunk/phase3/includes/Parser_OldPP.php |
— | — | @@ -4147,7 +4147,7 @@ |
4148 | 4148 | while ( $s = $dbr->fetchObject($res) ) { |
4149 | 4149 | $title = Title::newFromRow( $s ); |
4150 | 4150 | $pdbk = $title->getPrefixedDBkey(); |
4151 | | - $linkCache->addGoodLinkObj( $s->page_id, $title ); |
| 4151 | + $linkCache->addGoodLinkObj( $s->page_id, $title, $s->page_len, $s->page_is_redirect ); |
4152 | 4152 | $this->mOutput->addLink( $title, $s->page_id ); |
4153 | 4153 | |
4154 | 4154 | $colours[$pdbk] = ( $threshold == 0 || ( |
— | — | @@ -4230,7 +4230,7 @@ |
4231 | 4231 | $holderKeys = array(); |
4232 | 4232 | if(isset($variantMap[$varPdbk])){ |
4233 | 4233 | $holderKeys = $variantMap[$varPdbk]; |
4234 | | - $linkCache->addGoodLinkObj( $s->page_id, $variantTitle ); |
| 4234 | + $linkCache->addGoodLinkObj( $s->page_id, $variantTitle, $s->page_len, $s->page_is_redirect ); |
4235 | 4235 | $this->mOutput->addLink( $variantTitle, $s->page_id ); |
4236 | 4236 | } |
4237 | 4237 | |
Index: trunk/phase3/includes/Title.php |
— | — | @@ -86,7 +86,7 @@ |
87 | 87 | $this->mLatestID = false; |
88 | 88 | $this->mOldRestrictions = false; |
89 | 89 | $this->mLength = -1; |
90 | | - $this->mRedirect = null; |
| 90 | + $this->mRedirect = NULL; |
91 | 91 | } |
92 | 92 | |
93 | 93 | /** |
— | — | @@ -231,12 +231,12 @@ |
232 | 232 | */ |
233 | 233 | public static function newFromRow( $row ) { |
234 | 234 | $t = self::makeTitle( $row->page_namespace, $row->page_title ); |
235 | | - |
236 | | - $t->mArticleID = isset($row->page_id) ? $row->page_id : -1; |
237 | | - $t->mLength = isset($row->page_len) ? $row->page_len : -1; |
238 | | - $t->mRedirect = isset($row->page_is_redirect) ? (bool)$row->page_is_redirect : null; |
239 | | - $t->mLatest = isset($row->page_latest) ? $row->page_latest : 0; |
240 | | - |
| 235 | + |
| 236 | + $t->mArticleID = isset($row->page_id) ? intval($row->page_id) : -1; |
| 237 | + $t->mLength = isset($row->page_len) ? intval($row->page_len) : -1; |
| 238 | + $t->mRedirect = isset($row->page_is_redirect) ? intval($row->page_is_redirect) : NULL; |
| 239 | + $t->mLatestID = isset($row->page_latest) ? $row->page_latest : false; |
| 240 | + |
241 | 241 | return $t; |
242 | 242 | } |
243 | 243 | |
— | — | @@ -1482,49 +1482,8 @@ |
1483 | 1483 | public function isTalkPage() { |
1484 | 1484 | return MWNamespace::isTalk( $this->getNamespace() ); |
1485 | 1485 | } |
1486 | | - |
1487 | | - /** |
1488 | | - * Is this an article that is a redirect page? |
1489 | | - * @return bool |
1490 | | - */ |
1491 | | - public function isRedirect() { |
1492 | | - if( $this->mRedirect !== null ) |
1493 | | - return $this->mRedirect; |
1494 | | - # Zero for special pages |
1495 | | - if( $this->getNamespace() == NS_SPECIAL ) |
1496 | | - return 0; |
1497 | 1486 | |
1498 | | - $dbr = wfGetDB( DB_SLAVE ); |
1499 | | - $redir = $dbr->selectField( 'page', 'page_is_redirect', |
1500 | | - array( 'page_id' => $this->getArticleId() ), |
1501 | | - __METHOD__ ); |
1502 | | - |
1503 | | - $this->mRedirect = (bool)$redir; |
1504 | | - |
1505 | | - return $this->mRedirect; |
1506 | | - } |
1507 | | - |
1508 | 1487 | /** |
1509 | | - * What is the length of this page? |
1510 | | - * @return bool |
1511 | | - */ |
1512 | | - public function getLength() { |
1513 | | - if( $this->mLength != -1 || $this->mArticleID == 0 ) |
1514 | | - return $this->mLength; |
1515 | | - # Zero for special pages |
1516 | | - if( $this->getNamespace() == NS_SPECIAL ) |
1517 | | - return 0; |
1518 | | - |
1519 | | - $dbr = wfGetDB( DB_SLAVE ); |
1520 | | - $len = $dbr->selectField( 'page', 'page_len', |
1521 | | - array( 'page_id' => $this->getArticleId() ), |
1522 | | - __METHOD__ ); |
1523 | | - $this->mLength = intval($len); |
1524 | | - |
1525 | | - return $this->mLength; |
1526 | | - } |
1527 | | - |
1528 | | - /** |
1529 | 1488 | * Is this a subpage? |
1530 | 1489 | * @return bool |
1531 | 1490 | */ |
— | — | @@ -1889,7 +1848,43 @@ |
1890 | 1849 | } |
1891 | 1850 | return $this->mArticleID; |
1892 | 1851 | } |
| 1852 | + |
| 1853 | + /** |
| 1854 | + * Is this an article that is a redirect page? |
| 1855 | + * Uses link cache, adding it if necessary |
| 1856 | + * @param int $flags a bit field; may be GAID_FOR_UPDATE to select for update |
| 1857 | + * @return bool |
| 1858 | + */ |
| 1859 | + public function isRedirect( $flags = 0 ) { |
| 1860 | + # Zero for special pages. |
| 1861 | + # Also, calling getArticleID() loads the field from cache! |
| 1862 | + if( !$this->getArticleID($flags) || $this->getNamespace() == NS_SPECIAL ) { |
| 1863 | + return false; |
| 1864 | + } |
| 1865 | + $linkCache =& LinkCache::singleton(); |
| 1866 | + $this->mRedirect = $linkCache->getGoodLinkFieldObj( $this, 'redirect' ); |
1893 | 1867 | |
| 1868 | + return (bool)$this->mRedirect; |
| 1869 | + } |
| 1870 | + |
| 1871 | + /** |
| 1872 | + * What is the length of this page? |
| 1873 | + * Uses link cache, adding it if necessary |
| 1874 | + * @param int $flags a bit field; may be GAID_FOR_UPDATE to select for update |
| 1875 | + * @return bool |
| 1876 | + */ |
| 1877 | + public function getLength( $flags = 0 ) { |
| 1878 | + # Zero for special pages. |
| 1879 | + # Also, calling getArticleID() loads the field from cache! |
| 1880 | + if( !$this->getArticleID($flags) || $this->getNamespace() == NS_SPECIAL ) { |
| 1881 | + return 0; |
| 1882 | + } |
| 1883 | + $linkCache =& LinkCache::singleton(); |
| 1884 | + $this->mLength = $linkCache->getGoodLinkFieldObj( $this, 'length' ); |
| 1885 | + |
| 1886 | + return intval($this->mLength); |
| 1887 | + } |
| 1888 | + |
1894 | 1889 | public function getLatestRevID() { |
1895 | 1890 | if ($this->mLatestID !== false) |
1896 | 1891 | return $this->mLatestID; |
— | — | @@ -2245,7 +2240,7 @@ |
2246 | 2241 | if ( $db->numRows( $res ) ) { |
2247 | 2242 | while ( $row = $db->fetchObject( $res ) ) { |
2248 | 2243 | if ( $titleObj = Title::makeTitle( $row->page_namespace, $row->page_title ) ) { |
2249 | | - $linkCache->addGoodLinkObj( $row->page_id, $titleObj ); |
| 2244 | + $linkCache->addGoodLinkObj( $row->page_id, $titleObj, $row->page_len, $row->page_is_redirect ); |
2250 | 2245 | $retVal[] = $titleObj; |
2251 | 2246 | } |
2252 | 2247 | } |
Index: trunk/phase3/includes/LinkCache.php |
— | — | @@ -7,7 +7,7 @@ |
8 | 8 | class LinkCache { |
9 | 9 | // Increment $mClassVer whenever old serialized versions of this class |
10 | 10 | // becomes incompatible with the new version. |
11 | | - /* private */ var $mClassVer = 3; |
| 11 | + /* private */ var $mClassVer = 4; |
12 | 12 | |
13 | 13 | /* private */ var $mPageLinks; |
14 | 14 | /* private */ var $mGoodLinks, $mBadLinks; |
— | — | @@ -28,6 +28,7 @@ |
29 | 29 | $this->mForUpdate = false; |
30 | 30 | $this->mPageLinks = array(); |
31 | 31 | $this->mGoodLinks = array(); |
| 32 | + $this->mGoodLinkFields = array(); |
32 | 33 | $this->mBadLinks = array(); |
33 | 34 | } |
34 | 35 | |
— | — | @@ -49,14 +50,38 @@ |
50 | 51 | return 0; |
51 | 52 | } |
52 | 53 | } |
| 54 | + |
| 55 | + /** |
| 56 | + * Get a field of a title object from cache. |
| 57 | + * If this link is not good, it will return NULL. |
| 58 | + * @param Title $title |
| 59 | + * @param string $field ('length','redirect') |
| 60 | + * @return mixed |
| 61 | + */ |
| 62 | + function getGoodLinkFieldObj( $title, $field ) { |
| 63 | + $dbkey = $title->getPrefixedDbKey(); |
| 64 | + if ( array_key_exists( $dbkey, $this->mGoodLinkFields ) ) { |
| 65 | + return $this->mGoodLinkFields[$dbkey][$field]; |
| 66 | + } else { |
| 67 | + return NULL; |
| 68 | + } |
| 69 | + } |
53 | 70 | |
54 | 71 | function isBadLink( $title ) { |
55 | 72 | return array_key_exists( $title, $this->mBadLinks ); |
56 | 73 | } |
57 | 74 | |
58 | | - function addGoodLinkObj( $id, $title ) { |
| 75 | + /** |
| 76 | + * Add a link for the title to the link cache |
| 77 | + * @param int $id |
| 78 | + * @param Title $title |
| 79 | + * @param int $len |
| 80 | + * @param int $redir |
| 81 | + */ |
| 82 | + function addGoodLinkObj( $id, $title, $len = -1, $redir = NULL ) { |
59 | 83 | $dbkey = $title->getPrefixedDbKey(); |
60 | 84 | $this->mGoodLinks[$dbkey] = $id; |
| 85 | + $this->mGoodLinkFields[$dbkey] = array( 'length' => $len, 'redirect' => $redir ); |
61 | 86 | $this->mPageLinks[$dbkey] = $title; |
62 | 87 | } |
63 | 88 | |
— | — | @@ -124,11 +149,15 @@ |
125 | 150 | wfProfileOut( $fname ); |
126 | 151 | return 0; |
127 | 152 | } |
128 | | - |
| 153 | + # Some fields heavily used for linking... |
129 | 154 | $id = NULL; |
130 | | - if( $wgLinkCacheMemcached ) |
| 155 | + $len = -1; |
| 156 | + $redirect = NULL; |
| 157 | + |
| 158 | + if( $wgLinkCacheMemcached ) { |
131 | 159 | $id = $wgMemc->get( $key = $this->getKey( $title ) ); |
132 | | - if( ! is_integer( $id ) ) { |
| 160 | + } |
| 161 | + if( !is_integer( $id ) ) { |
133 | 162 | if ( $this->mForUpdate ) { |
134 | 163 | $db = wfGetDB( DB_MASTER ); |
135 | 164 | if ( !( $wgAntiLockFlags & ALF_NO_LINK_LOCK ) ) { |
— | — | @@ -141,20 +170,24 @@ |
142 | 171 | $options = array(); |
143 | 172 | } |
144 | 173 | |
145 | | - $id = $db->selectField( 'page', 'page_id', |
146 | | - array( 'page_namespace' => $ns, 'page_title' => $t ), |
147 | | - $fname, $options ); |
148 | | - if ( !$id ) { |
149 | | - $id = 0; |
| 174 | + $s = $db->selectRow( 'page', |
| 175 | + array( 'page_id', 'page_len', 'page_is_redirect' ), |
| 176 | + array( 'page_namespace' => $ns, 'page_title' => $t ), |
| 177 | + $fname, $options ); |
| 178 | + # Set fields... |
| 179 | + $id = $s ? $s->page_id : 0; |
| 180 | + $len = $s ? $s->page_len : -1; |
| 181 | + $redirect = $s ? $s->page_is_redirect : 0; |
| 182 | + |
| 183 | + if( $wgLinkCacheMemcached ) { |
| 184 | + $wgMemc->add( $key, $id, 3600*24 ); |
150 | 185 | } |
151 | | - if( $wgLinkCacheMemcached ) |
152 | | - $wgMemc->add( $key, $id, 3600*24 ); |
153 | 186 | } |
154 | 187 | |
155 | 188 | if( 0 == $id ) { |
156 | 189 | $this->addBadLinkObj( $nt ); |
157 | 190 | } else { |
158 | | - $this->addGoodLinkObj( $id, $nt ); |
| 191 | + $this->addGoodLinkObj( $id, $nt, $len, $redirect ); |
159 | 192 | } |
160 | 193 | wfProfileOut( $fname ); |
161 | 194 | return $id; |
— | — | @@ -166,6 +199,7 @@ |
167 | 200 | function clear() { |
168 | 201 | $this->mPageLinks = array(); |
169 | 202 | $this->mGoodLinks = array(); |
| 203 | + $this->mGoodLinkFields = array(); |
170 | 204 | $this->mBadLinks = array(); |
171 | 205 | } |
172 | 206 | } |