Ejemplo n.º 1
0
 /**
  * 清理失效的路由
  *
  * @access public static
  * @return void
  */
 public static function clean_invalidated_routes()
 {
     $mysql = \Myfox\Lib\Mysql::instance('default');
     $query = sprintf("SHOW TABLES LIKE '%sroute_info%%'", $mysql->option('prefix'));
     foreach ((array) $mysql->getAll($mysql->query($query)) as $table) {
         $table = end($table);
         $query = sprintf('SELECT autokid,hosts_list,real_table,route_text FROM %s WHERE route_flag IN (%d) AND modtime < %d', $table, Router::FLAG_IS_DELETED, time() - 100000);
         $ids = array();
         foreach ((array) $mysql->getAll($mysql->query($query)) as $row) {
             $hosts = trim($row['hosts_list'], '{}$');
             if (!empty($hosts)) {
                 $where = array();
                 foreach (Router::parse($row['route_text']) as $k => $v) {
                     $where[] = sprintf('%s = %s', $k, $v);
                 }
                 $info = array('host' => $hosts, 'path' => $row['real_table'], 'where' => implode(' AND ', $where));
                 if (!Queque::instance()->insert('delete', $info, 0, array('adduser' => 'cleaner'))) {
                     continue;
                 }
             }
             $ids[] = (int) $row['autokid'];
         }
         $mysql->query(sprintf('DELETE FROM %s WHERE (route_flag = %d AND addtime < %d)%s', $table, Router::FLAG_PRE_IMPORT, time() - 10 * 86400, empty($ids) ? '' : sprintf(' OR (autokid IN (%s))', implode(',', $ids))));
     }
 }
Ejemplo n.º 2
0
 public function execute()
 {
     if (!$this->isReady('thedate', 'priority')) {
         return self::IGNO;
     }
     $date1 = date('Ymd', strtotime(Setting::get('last_date')));
     $date2 = date('Ymd', strtotime($this->option('thedate')));
     if ($date1 >= $date2) {
         return self::IGNO;
     }
     $mysql = \Myfox\Lib\Mysql::instance('default');
     $count = (int) $mysql->getOne($mysql->query(sprintf('SELECT COUNT(*) FROM %stask_queque WHERE autokid < %u AND priority <= %u ' . "AND task_flag NOT IN (%d,%d) AND task_type='import'", $mysql->option('prefix'), $this->id, $this->option('priority'), \Myfox\App\Queque::FLAG_IGNO, \Myfox\App\Queque::FLAG_DONE)));
     if ($count > 0) {
         $this->setError(sprintf('Waiting for %d import task(s)', $count));
         return self::FAIL;
     }
     if (!Router::flush()) {
         $this->setError('flush route failed');
         return self::FAIL;
     }
     Setting::set('last_date', $date2, '', '集群数据最新日期');
     // TODO:
     // CALL nodefox to reload route info info cache
     return self::SUCC;
 }
Ejemplo n.º 3
0
 /**
  * 异步结果返回
  *
  * @access public
  * @return Integer
  */
 public function wait()
 {
     $result = array();
     foreach ((array) $this->pools as $host => $pool) {
         $failed = null;
         $mysql = Server::instance($pool['server'])->getlink();
         $this->setError($mysql->lastError());
         if (false !== $pool['handle'] && false !== $mysql->wait($pool['handle'])) {
             $failed = false;
             foreach ((array) $pool['commit'] as $query) {
                 if (false === $mysql->query($query)) {
                     $failed = true;
                     $this->setError(sprintf('[%s] %s', $pool['server'], $mysql->lastError()));
                     break;
                 }
             }
         }
         if (false === $failed) {
             $result[(int) $host] = true;
         }
     }
     if (!empty($result)) {
         $succes = implode(',', array_keys($result));
         if (false === Router::effect($this->option['table'], $this->route, $this->option['bucket'], $succes)) {
             $this->setError(sprintf('Router effect failed [%s].', $succes));
             $result = array();
         }
     }
     foreach ($this->pools as $host => $pool) {
         if (!empty($result[$host])) {
             unset($this->pools[$host]);
             continue;
         }
         foreach ((array) $pool['rollback'] as $query) {
             $mysql->query($query);
         }
     }
     $this->result = implode(',', array_keys($result));
     return empty($this->pools) ? self::SUCC : self::FAIL;
 }
Ejemplo n.º 4
0
 public function test_should_route_parse_works_fine()
 {
     $this->assertEquals(array(), Router::parse(''));
     $this->assertEquals(array('thedate' => 20110101, 'cid' => 23), Router::parse('thedate:20110101,cid:23'));
 }
Ejemplo n.º 5
0
 /**
  * 计算特定路由的路由值并产生分片规则,外部程序切分文件前调用
  *
  * @access protected
  * @return void
  */
 protected function actionRoute($param, $post)
 {
     if (false === self::priority()) {
         self::output(1100, 'Access Denied.');
         return false;
     }
     foreach (array('table', 'route', 'lines') as $key) {
         if (empty($param[$key])) {
             self::output(1200, sprintf('Param "%s" is required.', $key));
             return false;
         }
     }
     $table = self::vars('table', $param);
     $route = array(array('field' => Router::parse(self::vars('route', $param), $table), 'count' => (int) self::vars('lines', $param)));
     try {
         $routes = Router::set($table, $route);
         if (!is_array($routes)) {
             self::output(1300, 'Route failed.');
             return;
         }
         $output = array();
         foreach ($routes as $key => $shard) {
             foreach ((array) $shard as $split) {
                 $output[] = sprintf("%s\t%s\t%u\t%s\t%s", $param['table'], $key, $split['rows'], $split['hosts'], $split['table']);
             }
         }
         self::output(0, 'OK', implode("\n", $output));
     } catch (\Exception $e) {
         self::output(1400, $e->getMessage());
     }
 }
Ejemplo n.º 6
0
 /**
  * OPTIONS:
  * ----------------------------------------------------------------------
  * @file    : complete file url, such as "ftp://user:pass@hostname/path"
  * @table   : name of the logic table
  * @route   : route value of the file, ex: thedate=20111001,cid=210
  * @lines   :
  * ---------------------------------------------------------------------
  */
 public function execute()
 {
     if (!$this->isReady('table', 'route', 'lines', 'file', 'priority')) {
         return self::IGNO;
     }
     $table = Table::instance($this->option('table'));
     if (!$table->get('autokid')) {
         $this->setError(sprintf('Undefined table named as "%s".', $this->option('table')));
         return self::IGNO;
     }
     try {
         $routes = Router::set($this->option('table'), array(array('field' => Router::parse($this->option('route'), $this->option('table')), 'count' => (int) $this->option('lines'))));
         if (!is_array($routes)) {
             $this->setError('route failed.');
             return self::FAIL;
         }
         $config = Config::instance('default');
         $fname = Fileset::getfile($this->option('file'), $config->get('path/download'));
         if (empty($fname)) {
             $this->setError(sprintf('getfile:%s', Fileset::lastError()));
             return self::FAIL;
         }
         $splits = array();
         foreach ($routes as $key => $bucket) {
             foreach ($bucket as $item) {
                 $splits[] = $item['rows'];
             }
         }
         $fsplit = new Fsplit($fname, "\n", 16777216);
         $chunks = $fsplit->split($splits, $config->get('path/filesplit'));
         if (empty($chunks)) {
             $this->setError(sprintf('fsplit failed,%s', $fsplit->lastError()));
             return self::FAIL;
         }
         if (preg_match('/^\\w+:/i', $this->option('file'))) {
             @unlink($fname);
         }
         $result = array();
         $queque = Queque::instance();
         foreach ($routes as $key => $bucket) {
             foreach ($bucket as $item) {
                 $fname = array_shift($chunks);
                 if (empty($fname)) {
                     break 2;
                 }
                 $info = array('table' => $this->option('table'), 'route' => $key, 'file' => $fname, 'bucket' => $item['table'], 'hosts' => $item['hosts']);
                 $option = array('openrace' => 0, 'priority' => (int) $this->option('priority'), 'trytimes' => 3, 'task_flag' => Queque::FLAG_WAIT, 'adduser' => 'rsplit');
                 if (!$queque->insert('import', $info, -1, $option)) {
                     $this->setError(sprintf('queque: %s', $queque->lastError()));
                     return self::FAIL;
                 }
                 $result[] = $queque->lastId();
             }
         }
         $this->result = implode(',', $result);
     } catch (\Exception $e) {
         $this->setError($e->getMessage());
         return self::FAIL;
     }
     return self::SUCC;
 }
Ejemplo n.º 7
0
 public function test_should_the_secret_hello_function_works_fine()
 {
     $hello = Router::instance('mirror_v2')->hello(null, $table);
     $this->assertContains('route_info', $table);
     $this->assertEquals(array('route_sign' => 1550635837, 'table_name' => 'mirror_v2', 'route_text' => ''), $hello);
 }
Ejemplo n.º 8
0
 public function test_should_import_mirror_to_ib_works_fine()
 {
     self::cleanTable('default', 'route_info');
     $route = \Myfox\App\Model\Router::set('mirror_v2', array());
     $route = reset($route);
     $route = reset($route);
     $task = new \Myfox\App\Task\Import(10, array('table' => 'mirror_v2', 'route' => '', 'file' => realpath(__DIR__ . '/resource/mirror_import_data_file.txt'), 'bucket' => $route['table'], 'hosts' => '4,5', 'engine' => 'BRIGHTHOUSE'), '999999,-98');
     $this->assertEquals(Task::WAIT, $task->execute());
     $this->assertEquals(Task::SUCC, $task->wait());
     $where = \Myfox\App\Model\Router::instance('mirror_v2')->where(null);
     $route = self::$mysql->getOne(self::$mysql->query(sprintf("SELECT hosts_list FROM %s WHERE table_name='mirror_v2' AND real_table='%s' AND route_flag = %d", $where['table'], $route['table'], \Myfox\App\Model\Router::FLAG_IMPORT_END)));
     $route = array_filter(explode(',', trim($route, '{}$')));
     sort($route);
     $this->assertEquals(array(4, 5), $route);
     $this->assertEquals(true, self::check_table_exists('ibtest_1', 'mirror_v2_0.t_1_0'));
     $this->assertEquals(true, self::check_table_exists('ibtest_1', 'mirror_v2_0.t_1_1'));
     $this->assertEquals(true, self::check_table_exists('ibtest_1', 'mirror_v2_0.t_1_2'));
     $this->assertEquals(true, self::check_table_exists('ibtest_2', 'mirror_v2_0.t_1_0'));
     $this->assertEquals(true, self::check_table_exists('ibtest_2', 'mirror_v2_0.t_1_1'));
     $this->assertEquals(true, self::check_table_exists('ibtest_2', 'mirror_v2_0.t_1_2'));
 }