[英]grpc Server in background thread c++
我正在嘗試在 MFC 應用程序的線程中運行 grpc 服務器。
我有(直接來自 GRPC 示例的 grpc 部分):
MyAppDlg.h:
#include <thread>
#include <grpcpp\grpcpp.h>
class MyAppDlg : public CDialog
{
public:
MyAppDlg( CString aFileName, CWnd *pParent = NULL );
virtual ~MyAppDlg();
std::unique_ptr<grpc::Server> grpcServer;
std::thread grpcThread;
void RunServer();
MyAppDlg.cpp:
class GreeterServiceImpl final : public Greeter::Service {
Status SayHello(ServerContext* context, const HelloRequest* request,
HelloReply* reply) override {
std::string prefix("Hello ");
reply->set_message(prefix + request->name());
return Status::OK;
}
};
void MyAppDlg::RunServer() {
std::string server_address("0.0.0.0:50051");
GreeterServiceImpl service;
grpc::EnableDefaultHealthCheckService(true);
grpc::reflection::InitProtoReflectionServerBuilderPlugin();
ServerBuilder builder;
builder.AddListeningPort(server_address, grpc::InsecureServerCredentials());
builder.RegisterService(&service);
std::unique_ptr<Server> grpcServer(builder.BuildAndStart());
std::cout << "Server listening on " << server_address << std::endl;
// Wait for the server to shutdown. Note that some other thread must be
// responsible for shutting down the server for this call to ever return.
grpcServer->Wait(); <-- Leaving this out causes the server to close immediately again.
}
MyAppDlg::MyAppDlg( CString aFileName, CWnd* pParent /* =NULL */ )
{
... stuff ...
// RunServer(); <-- using this works but blocks the thread
grpcThread(RunServer); <-- does not work
}
MyAppDlg::~MyAppDlg()
{
grpcServer->Shutdown();
grpcThread.join();
}
沒有線程,它運行良好(客戶端可以連接並調用SayHello
),但由於grpcServer->Wait()
調用而阻塞了RunServer()
處的構造函數。 用線程嘗試它,我得到一個編譯器錯誤: call of an object of a class type without appropriate operator() or conversion functions to pointer-to-function type
不調用grpcServer->Wait()
會導致服務器在RunServer()
退出后立即關閉,盡管只要 class 實例正在運行,變量grpcServer
仍然在 scope 中。
如何正確啟動grpcServer
並將其置於后台?
我認為問題在於MyAppDlg::RunServer()
中的這一行:
std::unique_ptr<Server> grpcServer(builder.BuildAndStart());
您正在定義一個名為grpcServer
的局部變量,而不是分配給同名的 class 數據成員,因此一旦RunServer()
返回,它就會離開 scope 。 我認為應該只是:
grpcServer.reset(builder.BuildAndStart());
如果要在單獨的線程中運行服務器,那就是
grpcThread(Runserver);
您需要將 RunServer 方法與 object 實例相關聯,在本例中為“this”:
grpcTread(std::bind(&MyAppDlg::RunServer, this));
這應該可以修復編譯錯誤。
正如馬克指出的那樣,你有一個 class 成員 grpcServer,但是你在 RunServer 中聲明了一個局部變量 grpcServer,它在 RunServer 退出后退出 scope。
更重要的是,即使您在 RunServer 中執行Wait()
並在單獨的線程上運行它(應該可以正常工作), MyAppDlg::~MyAppDlg()
也不會關閉服務器,因為它會關閉MyAppDlg::grpcServer
,這與 RunServer 內部的局部變量grpcServer
RunServer
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.