Incremental categorylink updates, mainly to keep the old timestamp.
authorGabriel Wicke <gwicke@users.mediawiki.org>
Fri, 13 May 2005 21:18:45 +0000 (21:18 +0000)
committerGabriel Wicke <gwicke@users.mediawiki.org>
Fri, 13 May 2005 21:18:45 +0000 (21:18 +0000)
Timestamp saved in memcached, to allow checking for updates without contacting the db.
Might be possible to improve further using the linkscache, i tried but didn't succeed.
As-is it should still be faster than the unconditional full deletion/re-addition cycle.

includes/LinksUpdate.php

index c161a33..f57b229 100644 (file)
@@ -145,25 +145,63 @@ class LinksUpdate {
                #------------------------------------------------------------------------------
                # Category links
                if( $wgUseCategoryMagic ) {
-                       $sql = "DELETE FROM $categorylinks WHERE cl_from='{$this->mId}'";
-                       $dbw->query( $sql, $fname );
+                       global $messageMemc, $wgDBname;
                        
                        # Get addition list
                        $add = $wgLinkCache->getCategoryLinks();
                        
-                       # Do the insertion
-                       $sql = '';
-                       if ( 0 != count ( $add ) ) {
+                       # select existing catlinks for this page
+                       $res = $dbw->select( $categorylinks, array( 'cl_to' ), array( 'cl_from' => $this->mId ), 
+                       $fname, 'FOR UPDATE' );
+
+                       $del = array();
+                       if(0 != $dbw->numRows( $res )) {
+                               while ( $row = $dbw->fetchObject( $res ) ) {
+                                       if(!isset($add[$row->cl_to])) {
+                                               // in the db, but no longer in the page -> delete
+                                               $del[] = $row->cl_to;
+                                       } else {
+                                               // remove already existing category memberships
+                                               // from the add array
+                                               unset($add[$row->cl_to]);
+                                       }
+                               }
+                       }
+                       // delete any removed categorylinks
+                       if(count($del) > 0) {
+                               // delete old ones
+                               $sql = "DELETE FROM $categorylinks WHERE cl_from='{$this->mId}' AND cl_to IN('";
+                               $sql .= implode("','", $del) . "')";
+                               $dbw->query( $sql, $fname );
+                               foreach($del as $cname){
+                                       $nt = Title::makeTitle( NS_CATEGORY, $cname );
+                                       $nt->invalidateCache();
+                                       // update the timestamp which indicates when the last article
+                                       // was added or removed to/from this article
+                                       $key = $wgDBname.':Category:'.$nt->getDBkey().':adddeltimestamp';
+                                       $messageMemc->set( $key , wfTimestamp( TS_MW ), 24*3600 );
+                                       #wfDebug( "Linksupdate:Cats:del: ".serialize($nt)." $key \n" );
+                               }
+                       }
+                       // add any new category memberships
+                       if (count($add) > 0) {
                                $arr = array();
                                foreach( $add as $cname => $sortkey ) {
                                        $nt = Title::makeTitle( NS_CATEGORY, $cname );
                                        if( !$nt ) continue;
                                        $nt->invalidateCache();
+                                       // update the timestamp which indicates when the last article
+                                       // was added or removed to/from this article
+                                       $key = $wgDBname.':Category:'.$nt->getDBkey().':adddeltimestamp';
+                                       $messageMemc->set( $key , wfTimestamp( TS_MW ), 24*3600 );
+                                       #wfDebug( "Linksupdate:Cats:add: ".serialize($nt)." $key\n" );
+                                       #wfDebug( "LU-get: ".$messageMemc->get( $key)."\n");
                                        array_push( $arr, array(
                                                'cl_from'    => $this->mId,
                                                'cl_to'      => $cname,
                                                'cl_sortkey' => $sortkey ) );
                                }
+                               // do the actual sql insertion
                                $dbw->insert( 'categorylinks', $arr, $fname, array( 'IGNORE' ) );
                        }
                }
@@ -296,4 +334,4 @@ class LinksUpdate {
                $dbw->delete( 'brokenlinks', array( 'bl_to' => $this->mTitle ), $fname );
        }
 }
-?>
\ No newline at end of file
+?>