日韩av黄I国产麻豆传媒I国产91av视频在线观看I日韩一区二区三区在线看I美女国产在线I麻豆视频国产在线观看I成人黄色短片

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 >

thrift中TNonblockingServer的简单用法

發布時間:2025/3/15 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 thrift中TNonblockingServer的简单用法 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

最近在項目中需要把客戶端的一些信息發送到服務器上,聽起來是個很簡單的需求,但是實際考慮下,覺得如果自己手工實現,工作量也不小,而且盡是些繁瑣且無聊的事情,遂考慮用現成的庫來實現。對比了protocol buffer與thrift后,本著偷懶到底的原則,選擇了thrift,因為thrift本身提供了RPC框架,而protocol buffer僅是個序列化的庫而已。

? ?首先是編譯thrift,這里參考官方說明,需要先裝boost庫,但是如果要使用nonblocking server的話,還要再把libevent庫也裝上。

? ? thrift提供了三種服務模型,分別是TSimpleServer, TThreadPoolServer和TNonblockingServer,除去第一個一般僅做測試用,后兩個都可以在實際生產中拿來用。在客戶端不多的情況下,可以選用TThreadPoolServer,但是要注意TThreadPoolServer的客戶端只要不從服務器上斷開連接,就會一直占據服務器的一個線程,當服務器線程池所有線程都在被使用時,新到來的客戶端將排在隊列里等待,直到有客戶端斷開連接,使服務器端線程池出現空閑線程方可繼續被提供服務,所以使用這種模型時,一定要注意客戶端不使用時不要長時間連接服務器,如果確實有這種需求,請使用TNonblockingServer。

? ? 說實話,單純從代碼量上來講,使用Nonblocking server并不比ThreadPool server多了多少,誰讓代碼都是由thrift程序生成的,用戶只需填上實際處理的代碼即可。

? ? 下面用一個簡單的例子說明

? ? clientInfo.thrift

[plain]?view plain?copy
  • namespace?cpp?vnmp??
  • ??
  • enum?ClientType?{??
  • ????DOM_MANAGER,??
  • ????DOM_SERVICE??
  • }??
  • ??
  • enum?RegistResult?{??
  • ????SUCCESS,??
  • ????NAME_EXISTED,??
  • ????INVALIE_PARA,??
  • }??
  • ??
  • struct?ClientInfo?{??
  • ????1:?string?name,??
  • ????2:?string?realIP,??
  • ????3:?string?vpnIP,??
  • ????4:?ClientType?type,??
  • ????5:?optional?string?description,??
  • }??
  • ??
  • ??
  • service?Regist?{??
  • ????RegistResult?registClient(1:ClientInfo?clientInfo),??
  • ????bool?heartbeat(1:string?name,?2:ClientType?type)??
  • }??
  • 對這個文件做一個簡單的說明,client需要把自己的信息ClientInfo發送到server上注冊,調用registClient方法,heartbeat方法是用來做心跳的。

    執行 thrift -r --gen cpp clientInfo.thrift

    如果沒有語法錯誤的話,在gen-cpp目錄下會生成 ?

    clientInfo_constants.h clientInfo_constants.cpp?

    clientInfo_types.h clientInfo_types.cpp

    Regist_server.skeleton.cpp

    其中的skeleton文件包含了一個簡單的TSimpleServer實現,是可以直接編譯使用的,這個文件也就是我們要修改的文件,建議另外建一個main文件,并將其中內容拷過來,其他幾個強烈建議不要做修改,一來沒需要,二來如果做了修改,下次執行thrift文件時,也會被新生成的文件覆蓋,這也是我前面建議另外建一個main文件還不是直接修改skeketon文件的原因。

    下面是main文件的主要內容,略去了頭文件的包含和命名空間的使用等等,這里假定讀者已有了一定的boost基礎。

    [cpp]?view plain?copy
  • class?RegistHandler?:?virtual?public?RegistIf?{??
  • public:??
  • ??
  • ????RegistHandler()?{??
  • ????????//?Your?initialization?goes?here??
  • ????}??
  • ??
  • ????RegistResult::type?registClient(const?ClientInfo&?clientInfo)?{??
  • ????????//?Your?implementation?goes?here??
  • ????????printf("registClient\n");??
  • ????}??
  • ??
  • ????void?heartbeat(const?std::string&?name,?const?ClientType::type?type)?{??
  • ????????//?Your?implementation?goes?here??
  • ????????printf("heartbeat\n");??
  • ????}??
  • ??
  • };??
  • ??
  • int?main(int?argc,?char?**argv)?{??
  • ????int?port?=?9090;??
  • ????shared_ptr<RegistHandler>?handler(new?RegistHandler());??
  • ????shared_ptr<TProcessor>?processor(new?RegistProcessor(handler));??
  • ????shared_ptr<TProtocolFactory>?protocolFactory(new?TBinaryProtocolFactory());??
  • ????shared_ptr<ThreadManager>?threadManager?=?ThreadManager::newSimpleThreadManager(15);??
  • ????shared_ptr<PosixThreadFactory>?threadFactory?=?shared_ptr<PosixThreadFactory?>?(new?PosixThreadFactory());??
  • ????threadManager->threadFactory(threadFactory);??
  • ????threadManager->start();??
  • ????TNonblockingServer?server(processor,?protocolFactory,?port,?threadManager);??
  • ????server.serve();??
  • ????return?0;??
  • }??

  • regist service的實際處理方法寫在registHandler對應的方法里。主要是main方法做個簡單說明:

    這里使用了thrift庫自帶的ThreadManager,建立了一個擁有15個線程的線程池,也就是說這個NonblockingServer擁有15個工作線程。

    除了shared_ptr來自boost,其他均是thrift自帶,命名空間是apache::thrift?

    client端

    [cpp]?view plain?copy
  • int?main(int?argc,?char**?argv)?{??
  • ????boost::shared_ptr<TSocket>?socket(new?TSocket("localhost",?9090));??
  • ????boost::shared_ptr<TTransport>?transport(new?TFramedTransport(socket));??
  • ????boost::shared_ptr<TProtocol>?protocol(new?TBinaryProtocol(transport));??
  • ??
  • ????RegistClient?client(protocol);??
  • ??
  • ????transport->open();??
  • ????//insert?your?code?here??
  • ????//??????....??
  • ????transport->close();??
  • ????return?0;??
  • }??

  • 注意對于nonblocking server,client端的TTransport只能選用TFramedTransport;如果通信過程中出現異常,會拋出異常,可以用try catch捕獲并做處理。

    總結

    以上是生活随笔為你收集整理的thrift中TNonblockingServer的简单用法的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。