public static function dataCompileLoop($opts)
 {
     self::log("Using database master: " . WH_DATABASE_MASTER . "\n");
     $origToken = self::getToken();
     $numErrors = 0;
     $stopMsg = '';
     $data = new DashboardData();
     // The dashboard is very susceptible to going down when we're doing
     // maintenance on our spare server. Using this flag is a way to hold
     // the stats steady by reading them once from the master DB and not again
     // until the daemon is restarted.
     $fakeStats = isset($opts['f']) || isset($opts['fake-stats']);
     if ($fakeStats) {
         $data->fetchOnFirstCallOnly();
     }
     $staticData = $data->loadStaticGlobalOpts();
     $baselines = (array) json_decode($staticData['cdo_baselines_json']);
     DashboardWidget::setBaselines($baselines);
     // Run the data compilation repeatedly, until token changes
     while (1) {
         $start = microtime(true);
         $success = $data->compileStatsData();
         $end = microtime(true);
         $delta = $end - $start;
         $logMsg = sprintf('data refresh took %.3fs', $delta);
         if ($success) {
             $numErrors = 0;
         } else {
             $logMsg = sprintf('error was detected in data refresh (%.3fs)', $delta);
             $numErrors++;
             if ($numErrors >= self::STOP_AFTER_ERRORS) {
                 $stopMsg = sprintf('there were %d errors in a row. stopping daemon.', self::STOP_AFTER_ERRORS);
             }
         }
         self::log($logMsg);
         if (!empty($stopMsg)) {
             break;
         }
         $until_refresh_seconds = self::REFRESH_SECONDS - $delta;
         if ($until_refresh_seconds >= 0.0) {
             $secs = (int) ceil($until_refresh_seconds);
             sleep($secs);
         }
         $token = self::getToken();
         if ($token != $origToken) {
             $stopMsg = 'stop daemon requested through token change.';
             break;
         }
     }
     if ($stopMsg) {
         self::log($stopMsg);
     }
 }