gRPC: как обработчики RPC могут правильно определить, был ли `Server` выключен () - PullRequest
0 голосов
/ 05 июля 2018

Текущий, я использую хакерский способ - глобальную переменную - чтобы обработчики RPC могли обнаружить, что Server был (должен быть) назван Shutdown().

bool g_ServerIsNotDead = true;   // Hack!

Status StreamServiceImpl::GetCurrentTemperature(ServerContext *context_,
                                                const UpdateInterval *request_,
                                                ServerWriter<Temperature> *stream_)
{
  auto currentTemp = 100.0f;
  while(g_ServerIsNotDead)   // Hack!!!
  {
    qDebug() << QThread::currentThreadId() << currentTemp << "farenheit.";

    Temperature message;
    message.set_temperature(currentTemp);
    stream_->Write(message);

    QThread::sleep(2);

    currentTemp += 1.0f;
  }

  return Status::OK;
}

void insideSomeFunction() {
   // Testing shutdown 5 seconds later
   QTimer::singleShot(std::chrono::seconds(5), this, [=]() {
      qDebug() << "Shuting down!";

      g_ServerIsNotDead = false;   // Hack!!

      this->server->Shutdown();    // This method actually blocks until all RPC handlers have exited, believe it or not!

      emit shutdown();

      qDebug() << "All dead.";
  });
}

Ссылка: https://github.com/C0D1UM/grpc-qt-example/blob/master/rpc_server/hellostream_server.cpp

Было бы очень хорошо, если бы я мог как-то проверить, что Server было Shutdown() из grpc::ServerContext, но я не видел подходящих методов для достижения этого.

Еще лучше, если кто-то может предложить способ полного удаления цикла while (?). Я использую Qt, поэтому все управляется событиями.

1 Ответ

0 голосов
/ 14 июля 2018

Итак, я думаю, стоит пояснить, что делает Shutdown. Существует подробный комментарий об этом , но в основном сервер Shutdown не завершает работу, не отменяет или не завершает ваши текущие текущие вызовы (если вы не используете аргумент deadline и gRPC C ++ async API).

Скорее, он прекращает прослушивание новых подключений, прекращает прием новых вызовов, отказывает в запросе, но еще не принятом вызове. Если вы хотите прервать или прервать ваши вызовы при завершении работы, вы можете сделать это с помощью кода уровня приложения, как вы делали выше.

Я бы просто рекомендовал вместо использования глобальной переменной использовать функцию-член вашего класса StreamServiceImpl, чтобы вы могли поддерживать несколько служб, работающих в одном процессе, если вы выберете.

...