Provide a default "max lag" value for LoadBalancer
[lhc/web/wiklou.git] / includes / db / loadbalancer / LoadBalancer.php
index cdd3d4c..fbc8c8c 100644 (file)
@@ -63,6 +63,8 @@ class LoadBalancer {
 
        /** @var integer Warn when this many connection are held */
        const CONN_HELD_WARN_THRESHOLD = 10;
+       /** @var integer Default 'max lag' when unspecified */
+       const MAX_LAG = 30;
 
        /**
         * @param array $params Array with keys:
@@ -155,7 +157,7 @@ class LoadBalancer {
         * @param float $maxLag Restrict the maximum allowed lag to this many seconds
         * @return bool|int|string
         */
-       private function getRandomNonLagged( array $loads, $wiki = false, $maxLag = INF ) {
+       private function getRandomNonLagged( array $loads, $wiki = false, $maxLag = self::MAX_LAG ) {
                $lags = $this->getLagTimes( $wiki );
 
                # Unset excessively lagged servers
@@ -250,6 +252,7 @@ class LoadBalancer {
 
                # No server found yet
                $i = false;
+               $conn = false;
                # First try quickly looking through the available servers for a server that
                # meets our criteria
                $currentLoads = $nonErrorLoads;
@@ -545,6 +548,14 @@ class LoadBalancer {
                        $trxProf->recordConnection( $host, $dbname, $masterOnly );
                }
 
+               # Make master connections read only if in lagged slave mode
+               if ( $masterOnly && $this->getServerCount() > 1 && $this->getLaggedSlaveMode() ) {
+                       $conn->setLBInfo( 'readOnlyReason',
+                               'The database has been automatically locked ' .
+                               'while the slave database servers catch up to the master'
+                       );
+               }
+
                return $conn;
        }
 
@@ -803,12 +814,6 @@ class LoadBalancer {
                }
 
                $db->setLBInfo( $server );
-               if ( isset( $server['fakeSlaveLag'] ) ) {
-                       $db->setFakeSlaveLag( $server['fakeSlaveLag'] );
-               }
-               if ( isset( $server['fakeMaster'] ) ) {
-                       $db->setFakeMaster( true );
-               }
 
                return $db;
        }
@@ -839,7 +844,9 @@ class LoadBalancer {
                                "Connection error: {last_error} ({db_server})",
                                $context
                        );
-                       $conn->reportConnectionError( "{$this->mLastError} ({$context['db_server']})" ); // throws DBConnectionError
+
+                       // throws DBConnectionError
+                       $conn->reportConnectionError( "{$this->mLastError} ({$context['db_server']})" );
                }
 
                return false; /* not reached */
@@ -1134,6 +1141,7 @@ class LoadBalancer {
        }
 
        /**
+        * @note This method will trigger a DB connection if not yet done
         * @return bool Whether the generic connection for reads is highly "lagged"
         */
        public function getLaggedSlaveMode() {
@@ -1143,6 +1151,15 @@ class LoadBalancer {
                return $this->mLaggedSlaveMode;
        }
 
+       /**
+        * @note This method will never cause a new DB connection
+        * @return bool Whether any generic connection used for reads was highly "lagged"
+        * @since 1.27
+        */
+       public function laggedSlaveUsed() {
+               return $this->mLaggedSlaveMode;
+       }
+
        /**
         * Disables/enables lag checks
         * @param null|bool $mode
@@ -1224,12 +1241,14 @@ class LoadBalancer {
        }
 
        /**
-        * Get lag time for each server
+        * Get an estimate of replication lag (in seconds) for each server
         *
         * Results are cached for a short time in memcached/process cache
         *
+        * Values may be "false" if replication is too broken to estimate
+        *
         * @param string|bool $wiki
-        * @return int[] Map of (server index => seconds)
+        * @return int[] Map of (server index => float|int|bool)
         */
        public function getLagTimes( $wiki = false ) {
                if ( $this->getServerCount() <= 1 ) {