thrift 0.9.0 tutorial例子

一。thrift 0.9.0的版本的例子编译cpp有好多问题,特此记录一下

1. 在tutorial/cpp下直接make,出现一堆错误,随便截取一下

”/usr/local/include/thrift/protocol/TProtocol.h:312: error: ‘uint32_t’ does not name a type“还有什么ntohl找不到什么的,是由于MakeFile中没有指定

-DHAVE_NETINET_IN_H,导致没有包含#include <arpa/inet.h>头文件

2. 添加-DHAVE_NETINET_IN_H后,出现

/usr/local/include/thrift/concurrency/Thread.h:90: error: ‘pthread_self’ was not declared in this scope等等pthread的函数找不到定义,是没有包含pthread.h头文件

在MakeFile中添加 -DHAVE_PTHREAD_H

3. 编译成功后运行出现

error ' error while loading shared libraries: libthrift-0.9.0.so: cannot open shared object file: No such file or directory'

说找不到libthrift动态链接库,但是在/usr/local/lib下确实存在,还需要在自己的.bashrc问价中添加

export LD_LIBRARY_PATH=/usr/local/lib

然后source .bashrc

终于运行成功。。。


二。对tutorial例子的简单解析

由于tutorial中的例子存在.thrift文件的相互依赖,因此在首先对thrift文件进行编译时,需要首先编译

thrift -gen cpp shared.thrift

shared.thrift内容如下

struct SharedStruct { 1: i32 key 2: string value}service SharedService {  SharedStruct getStruct(1: i32 key)}

此时在gen-cpp目录下生成了

shared_constants.cpp
shared_constants.h
SharedService.cpp
SharedService.h
SharedService_server.skeleton.cpp
shared_types.cpp
shared_types.h

其中*_constants.*文件保存了在thrift文件中定义的常量信息,*_types.*文件保存了thrift文件中定义的类型信息,上述信息供我们编写server和client业务逻辑时参考。

而*Service.*文件,定义了Service的对外接口。skeleton文件则是thrift为我们生成的桩文件,当我们开发Server时,直接将该文件cp到编码的文件夹下添加业务逻辑(实现Service文件中的接口即可)。

然后在 thrift -gen cpp tutorial.thrift

此时可以看到

Calculator.cpp

Calculator.h

Calculator_server.skeleton.cpp

三个文件(忽视掉之前生成的文件以及 constants和types文件),这三个文件中 Calculator.*文件已经帮我们写好了大量的rpc操作,我们此时只需要在skeleton文件中将Calculator.h中定义的但未在Calculator.cpp中实现的接口实现,就好了。(实际上thrift都已经把框架搭建好了,我们只需要修改skeleton文件,实现业务逻辑的接口就好)

仔细对照gen-cpp/下的skeleton文件和cpp/下的CppServer.cpp文件就可以发现,CppServer.cpp不仅仅实现了skeleton文件中的接口,还另外实现了

void getStruct(SharedStruct &ret, const int32_t logid) {
  printf("getStruct(%d)\n", logid);
  ret = log[logid];
}

这是因为在tutorial.thrift文件中include了shared.thrift文件,且继承了shared.SharedService,因此生成的Calculator.h中,我们就看到

class CalculatorIf : virtual public  ::shared::SharedServiceIf
也就是说这个CalculatorIf接口还继承了SharedServiceIf接口,所以实现该接口的类必须要将所有继承的接口全部实现,而getStruct接口就是SharedServiceIf的唯一接口,所以才有了CppServer的实现。


另外,对于Service服务,thrift会直接帮我们生成skeleton文件,简化编码,但是对于client则不行,我们可以把cpp/下的CppClient.cpp文件作为自己的一个模板文件,简化代码编写工作

#include <stdio.h>
#include <unistd.h>
#include <sys/time.h>

#include <thrift/protocol/TBinaryProtocol.h>
#include <thrift/transport/TSocket.h>
#include <thrift/transport/TTransportUtils.h>

#include "../gen-cpp/Calculator.h"

using namespace std;
using namespace apache::thrift;
using namespace apache::thrift::protocol;
using namespace apache::thrift::transport;

using namespace tutorial;
using namespace shared;

using namespace boost;

int main(int argc, char** argv) {
  shared_ptr<TTransport> socket(new TSocket("localhost", 9090));
  shared_ptr<TTransport> transport(new TBufferedTransport(socket));
  shared_ptr<TProtocol> protocol(new TBinaryProtocol(transport));
  CalculatorClient client(protocol);

  try {
    transport->open();
    /* ToDo
    client.ping();
    printf("ping()\n");

    int32_t sum = client.add(1,1);
    printf("1+1=%d\n", sum);

    Work work;
    work.op = Operation::DIVIDE;
    work.num1 = 1;
    work.num2 = 0;

    try {
      int32_t quotient = client.calculate(1, work);
      printf("Whoa? We can divide by zero!\n");
    } catch (InvalidOperation &io) {
      printf("InvalidOperation: %s\n", io.why.c_str());
    }

    work.op = Operation::SUBTRACT;
    work.num1 = 15;
    work.num2 = 10;
    int32_t diff = client.calculate(1, work);
    printf("15-10=%d\n", diff);

    // Note that C++ uses return by reference for complex types to avoid
    // costly copy construction
    SharedStruct ss;
    client.getStruct(ss, 1);
    printf("Check log: %s\n", ss.value.c_str());

    end of ToDo */
    transport->close();
  } catch (TException &tx) {
    printf("ERROR: %s\n", tx.what());
  }

}




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值