TL; DR:あなたがきれいにシャットダウンする(サービスで使用される各完了キュー用)grpc::Server::Shutdown()
とgrpc::CompletionQueue::Shutdown()
の両方を呼び出す必要があります。
あなたがcq_->Shutdown()
を呼び出した場合、唯一の観察可能な効果はService::AsyncService::RequestFoo()
への後続の呼び出し(対応Foo
RPCのための生成方法)は、アサーションで失敗していることです。対応するC APIメソッド(grpc_completion_queue_shutdown()
)のドキュメントを読むと、—という新しい作業を追加すること、つまりRequestFoo()
—を呼び出すことによって、is_shutdown_
というメンバをサービスラッパークラス(mutexによって保護されている)に追加しても、その結果、cq_->Shutdown()
が呼び出された後でエンキューが試みられません。ただし、これを実行した後、完了キューは無期限にブロックcq_->Next()
にブロックされます。エンキューされたタグのいずれも完了しません(エラーなどあります)。
代わりにserver_->Shutdown()
を呼び出すと、すべてのエンキューされたタグはすぐに(ok == false
で)完了します。ただし、完了キューは無制限にブロックされ続けます(cq_->Next()
)。クリーンシャットダウンの両方の(定義された各完了キューの)cq_->Shutdown()
とserver_->Shutdown()
結果を呼び出す
。
1つの警告:あなたは、コールのキャンセル用のタグを登録するgrpc::ServerContext::AsyncNotifyWhenDone()
を使用する場合、最初の要求は、そのコールのために受信される前に、サーバーがシャットダウンした場合、これらはcq_->Next()
によって返されないます。メモリリークを避けたい場合は、対応するタグ構造のメモリ管理に注意する必要があります。