* Move lock()/unlock() to DatabaseMysql, declare abstract
authorChad Horohoe <demon@users.mediawiki.org>
Thu, 25 Jun 2009 00:40:12 +0000 (00:40 +0000)
committerChad Horohoe <demon@users.mediawiki.org>
Thu, 25 Jun 2009 00:40:12 +0000 (00:40 +0000)
* Introduce lockTables() and unlockTables(), define in DatabaseMysql
* (bug 19372) updateSearchIndex has MySQLisms.

includes/db/Database.php
includes/db/DatabaseMysql.php
maintenance/updateSearchIndex.inc

index 7d07816..d6789c1 100644 (file)
@@ -2176,7 +2176,7 @@ abstract class DatabaseBase {
        }
        
        /**
-        * Acquire a lock
+        * Acquire a named lock
         * 
         * Abstracted from Filestore::lock() so child classes can implement for
         * their own needs.
@@ -2185,33 +2185,36 @@ abstract class DatabaseBase {
         * @param $method String: Name of method calling us
         * @return bool
         */
-       public function lock( $lockName, $method ) {
-               $lockName = $this->addQuotes( $lockName );
-               $result = $this->query( "SELECT GET_LOCK($lockName, 5) AS lockstatus", $method );
-               $row = $this->fetchObject( $result );
-               $this->freeResult( $result );
+       abstract public function lock( $lockName, $method, $timeout = 5 );
 
-               if( $row->lockstatus == 1 ) {
-                       return true;
-               } else {
-                       wfDebug( __METHOD__." failed to acquire lock\n" );
-                       return false;
-               }
-       }
        /**
         * Release a lock.
         * 
-        * @todo fixme - Figure out a way to return a bool
-        * based on successful lock release.
-        * 
         * @param $lockName String: Name of lock to release
         * @param $method String: Name of method calling us
+        *
+        * FROM MYSQL DOCS: http://dev.mysql.com/doc/refman/5.0/en/miscellaneous-functions.html#function_release-lock
+        * @return Returns 1 if the lock was released, 0 if the lock was not established
+        * by this thread (in which case the lock is not released), and NULL if the named 
+        * lock did not exist
         */
-       public function unlock( $lockName, $method ) {
-               $lockName = $this->addQuotes( $lockName );
-               $result = $this->query( "SELECT RELEASE_LOCK($lockName)", $method );
-               $this->freeResult( $result );
-       }
+       abstract public function unlock( $lockName, $method );
+
+       /**
+        * Lock specific tables
+        *
+        * @param $read Array of tables to lock for read access
+        * @param $write Array of tables to lock for write access
+        * @param $method String name of caller
+        */
+       abstract public function lockTables( $read, $write, $method );
+       
+       /**
+        * Unlock specific tables
+        *
+        * @param $method String the caller
+        */
+       abstract public function unlockTables( $method );
        
        /**
         * Get search engine class. All subclasses of this
index 6508eb2..ecd3485 100644 (file)
@@ -293,6 +293,44 @@ class DatabaseMysql extends DatabaseBase {
                $this->query( "SET net_read_timeout=$timeout" );
                $this->query( "SET net_write_timeout=$timeout" );
        }
+
+       public function lock( $lockName, $method, $timeout = 5 ) {
+               $lockName = $this->addQuotes( $lockName );
+               $result = $this->query( "SELECT GET_LOCK($lockName, $timeout) AS lockstatus", $method );
+               $row = $this->fetchObject( $result );
+               $this->freeResult( $result );
+
+               if( $row->lockstatus == 1 ) {
+                       return true;
+               } else {
+                       wfDebug( __METHOD__." failed to acquire lock\n" );
+                       return false;
+               }
+       }
+
+       public function unlock( $lockName, $method ) {
+               $lockName = $this->addQuotes( $lockName );
+               $result = $this->query( "SELECT RELEASE_LOCK($lockName) as lockstatus", $method );
+               $row = $this->fetchObject( $result );
+               return $row->lockstatus;
+       }
+
+       public function lockTables( $read, $write, $method ) {
+               $items = array();
+
+               foreach( $write as $table ) {
+                       $items[] = $this->tableName( $table ) . ' LOW_PRIORITY WRITE';
+               }
+               foreach( $read as $table ) {
+                       $items[] = $this->tableName( $table ) . ' READ';
+               }
+               $sql = "LOCK TABLES " . implode( ',', $items );
+               $db->query( $sql, $method );
+       }
+
+       public function unlockTables( $method ) {
+               $this->query( "UNLOCK TABLES", $method );
+       }
 }
 
 /**
index 0cac450..21e2df4 100644 (file)
@@ -75,7 +75,7 @@ function updateSearchIndex( $start, $end, $maxLockTime, $quiet ) {
        # Unlock searchindex
        if ( $maxLockTime ) {
                output( "    --- Unlocking --" );
-               unlockSearchindex( $dbw );
+               $dbw->unlockTables( 'updateSearchIndex.inc ' . __METHOD__ );
                output( "\n" );
        }
        output( "Done\n" );
@@ -84,27 +84,14 @@ function updateSearchIndex( $start, $end, $maxLockTime, $quiet ) {
 function lockSearchindex( &$db ) {
        $write = array( 'searchindex' );
        $read = array( 'page', 'revision', 'text', 'interwiki' );
-       $items = array();
-       
-       foreach( $write as $table ) {
-               $items[] = $db->tableName( $table ) . ' LOW_PRIORITY WRITE';
-       }
-       foreach( $read as $table ) {
-               $items[] = $db->tableName( $table ) . ' READ';
-       }
-       $sql = "LOCK TABLES " . implode( ',', $items );
-       $db->query( $sql, 'updateSearchIndex.inc ' . __METHOD__ );
-}
-
-function unlockSearchindex( &$db ) {
-       $db->query( "UNLOCK TABLES", 'updateSearchIndex.inc ' . __METHOD__ );
+       $db->lockTables( $read, $write, 'updateSearchIndex.inc ' . __METHOD__ );
 }
 
 # Unlock and lock again
 # Since the lock is low-priority, queued reads will be able to complete
 function relockSearchindex( &$db ) {
        unlockSearchindex( $db );
-       lockSearchindex( $db );
+       $db->unlockTables( 'updateSearchIndex.inc ' . __METHOD__ );
 }
 
 function output( $text ) {