2017-02-16 13 views
1

У меня возникает проблема: У меня есть бэкэнд в php на основе codeigniter, где я получу данные о весовых весах от машины-дозатора, которая отправляется из внешнего приложения C# (не может изменять это приложение C#). Я получу весовые данные каждый раз, когда весы будут обновлять значение, так что, например, оно начнется с 0, 100, 300, 400, 1000, 1500, 600, 400, 300, 100 и обратно до 0 (он опустится когда продукт зашкаливает), и все эти значения генерируются одну запись в секунду, так что я буду иметь их быстро, и вставить, что на моей базе данных MySQL с помощью этой функции:Как работать с параллельным процессом в php

public function balance() { 
    $evType = $this->input->post('eventType'); 
    $weight = $this->input->post('balanceWeight'); 

    if ($evType !== false && $weight !== false) { 
     $evType = intval($evType); 
     $weight = intval($weight); 


     switch($this->balance_events->insert($evType, $weight)) { 
      case OpResult::Ok; 
       $this->_issue_success(); 
        if($weight>100){ 
        $insert_id = $this->db->insert_id(); 
        $this->Curlsynologyapi->CURLsaveimage($insert_id); 
        }    
       break; 
      case OpResult::InvalidParameters; 
       $this->_issue_respond_with_reason("Not all parameters were supplied.", HttpResponse::BadRequest); 
       break; 
      case OpResult::Failed: 
       $this->_issue_respond_with_reason("Internal server error occured while inserting the balance entry. Please try again ...", HttpResponse::InternalServerError); 
       break; 
      default: 
       break; 
     } 
    } 
} 

так exaplain это быстрый, $ weight будет удерживать значение веса (игнорируйте $ evType, то есть некоторый масштабный параметр). И это будет необходимо держать и вставлять данные быстро, так как появятся новые значения. Теперь у меня будет условие: if ($ weight> 100), когда это TRUE. Я перехожу к другой функции, которую я перечислю выше, что делает это, чтобы сделать экран печати камеры и сохранить это изображение на моем сервере на выбранную папку и назовите ее с идентификатором значения веса, который был вставлен в mysql. Это то, что я называю, что после моего, если утверждение верно:

public function CURLsaveimage($insert_id) { 
    $datasidget = $this->curl->simple_get('blablabla this is my api login url'); 
    $datasid = json_decode($datasidget,true); 
    $data_sid = $datasid['data']['sid']; 

    $reqUrl = "blabla this is my print screen from a live camera api url"; 
    $imageencode = $this->curl->simple_get($reqUrl); 
    $path = "./images/$insert_id"; 
    write_file($path, $imageencode, $mode = 'wb'); 

} 

Выполнение запросов API из моей последней функции будет принимать как 30-40 сек, и что это много по сравнению со скоростью я получить вес значения (1 вход/сек). И когда if запустит и запустит api-запросы, я пропущу все данные веса до тех пор, пока запросы не будут выполнены. Дело в том, что я могу позволить себе получить 1 экран печати на сеанс шкалы (это означает, что когда кто-то поместит что-то в шкалу, мне нужно сделать 1 экран печати при срабатывании условия, а затем подождать до следующего взвешивающего события, весовой машины не будет генерировать безостановочные данные, но когда он генерирует, я должен быстро его получить).

То, что я думал, - это то, что нужно сделать запрос к процессу api параллельно, чтобы поток событий веса не был затронут, и когда запрос api завершен, снова начните проверять, когда, если это произойдет, и так далее , Мне также хотелось бы, если бы у меня был некоторый контроль над этим параллельным процессом, чтобы использовать какой-то сон с ним или что-то в этом роде.

Я читал немного о работниках и потоках php, я видел redis, german, heroku, но, честно говоря, они кажутся немного трудными для понимания, и документация для этого довольно тонкая, и я тоже думаю, что они тоже много для моей проблемы.

Вопрос: Есть ли что-нибудь вокруг легкого и доступного для кого-то, кто не продвинулся в php?

Большое вам спасибо за ваше время!

ответ

1

Да, вы можете сделать простую очередь задач самостоятельно.

Каждый раз, когда вам нужно запросить API, вы создадите задачу и сохраните ее в своей базе данных в некоторой пользовательской таблице, где хранятся только задачи. Поскольку мы только сохраняем задачу в базе данных и не делаем здесь запросы api, это быстро.

Теперь у нас есть очередь (таблица в базе данных) с задачами для завершения, так что теперь нам нужен какой-то работник php, чтобы получить одну задачу из очереди и выполнить ее.

Создайте простой скрипт php, который получит одну задачу из базы данных (например, "select * from tasks limit 1"), выполняет ее, а затем удаляет эту задачу из базы данных по завершении (или может изменять статус задачи).

Теперь у нас есть только одна проблема, кто запустит этот скрипт и когда? Для этого мы можем использовать cron. Например, мы можем планировать запуск нашего скрипта каждую минуту.

PHP-скрипт может запускаться каждую минуту при помощи cron.

И ваш код будет выглядит следующим образом:

 switch($this->balance_events->insert($evType, $weight)) { 
      case OpResult::Ok; 
       $this->_issue_success(); 
        if($weight>100){ 
         $insert_id = $this->db->insert_id(); 
         $saveCameraImageTask = new SaveCameraImageTask($insert_id); 
         $saveCameraImageTask->save()//save it to database, we are just saving it to our database, no api request, so it is fast. 
        }    
       break; 
      case OpResult::InvalidParameters; 
       $this->_issue_respond_with_reason("Not all parameters were supplied.", HttpResponse::BadRequest); 
       break; 
      case OpResult::Failed: 
       $this->_issue_respond_with_reason("Internal server error occured while inserting the balance entry. Please try again ...", HttpResponse::InternalServerError); 
       break; 
      default: 
       break; 
     } 
+0

Хм, что интересно, спасибо за ваш ответ, мой вопрос заключается в том, что, так как фактические экраны печати, которые я делаю это с живой камеры, и я хочу для обработки так быстро, как задача будет получена в моем db (потому что я хочу сделать экранное изображение для фотоаппарата как можно ближе к триггерам if, хочу проверить, какой продукт (на шкале) есть). Например, есть возможность запустить задачу из моей базы данных, как только там будет вставлена ​​задача? – Bogdan

+0

Ну, это зависит. Если вы хотите запустить задачу на триггере, когда вставлена ​​новая строка, нет простого решения, насколько я знаю. Аналогичный вопрос был здесь http://stackoverflow.com/questions/21019886/how-to-check-in-real-time-if-new-row-was-added-to-mysql-table Однако, если вы хотите проверить новая строка чаще, чем 1 минута, вы можете это сделать. – Clickbeetle

+0

Мое решение более подходит, когда у вас есть какая-то задача, которую вы хотите запустить в ближайшее время, но не в тот же момент. Если вам нужно мгновенное одновременное выполнение, вам действительно нужен редуктор, кролик и т. Д. – Clickbeetle