Apache Thrift

维基百科
Thrift是一种接口描述语言和二进制通讯协议,它被用来定义和创建跨语言的服务。它被当作一个远程过程调用(RPC)框架来使用,是由Facebook为“大规模跨语言服务开发”而开发的。

最近用 thrift 做微服务 , 抽空写了通俗易懂 apache thrift 官方java 教程 中文版。

准备

  1. 添加依赖

官网有复杂的安装thrift和编译的过程,复杂多余,最终目的还是要转成jar包,添加maven依赖。不过现在已经有maven依赖的,省去了编译打包jar包过程。一个maven依赖就可以加载进来所有需要的jar包。

1
2
3
4
5
<dependency>
<groupId>org.apache.thrift</groupId>
<artifactId>libthrift</artifactId>
<version>0.10.0</version>
</dependency>
  1. 接口语言 转 java 工具

除了maven依赖,还需要一个从接口描述语言(thrift)转换成 java 的工具,从这里下载.exe文件 http://thrift.apache.org/download

下载thrift-0.10.0.exe文件,把他移到自己喜欢的目录下D:\code\thrift,并改名 thrift.exe,并且把路径添加到环境变量path。

WIN+R , cmd进去输入命令thrift会打印一下则,环境添加成功。
thrift

编写接口

http://thrift.apache.org/tutorial/java , 下载 tutorial.thrift 和 shared.thrift ,控制台 cd 到它俩所在的目录

1
thrift -r --gen java tutorial.thrift

打开目录会多出来以下文件:

1
2
3
4
5
6
7
8
9
10
11
gen-java
├─shared
│ SharedService.java
│ SharedStruct.java

└─tutorial
Calculator.java
InvalidOperation.java
Operation.java
tutorialConstants.java
Work.java

把 shared 和 tutorial 俩文件夹拷到 maven 项目里(我个人用eclipse建的maven,直接拷到了eclipse,src/main/java 下)。

特殊说明 —爬坑

这里可能会出现拷进去的文件的@Override注解报错问题,这是因为什么呢?

原因是我用eclipse建的maven 的jre system libraries 默认使用了 jre1.5 。 这是jdk的问题,@Override是JDK5就已经有了,但是不支持对接口的实现,认为这不是Override而报错。JDK6修正了这个Bug,无论是对父类的方法覆盖还是对接口的实现都可以加上@Override。

解决问题:我把jre system libraries 1.5 删除,并且新添了 jre1.8 就可以了。

实现

先贴出项目整个图:
project.png

这里有一个CalculatorHandler.java 文件, 也是可以从官网找到的 http://thrift.apache.org/

其它client 和 server 都可以下载 http://thrift.apache.org/tutorial/java

官方教程中启动服务器提供了两种方式,一般方式(simple)和TSSL方式(secure)。

simple方式很简单就能运行,但是TSSL方式需要用到安全证书。

官方教程源码,服务端代码里有一段:

1
params.setKeyStore("../../lib/java/test/.keystore", "thrift", null, null);

这里的.keystore是私钥,”thrift”是私钥的口令。

在客户端里有:

1
params.setTrustStore("../../lib/java/test/.truststore", "thrift", "SunX509", "JKS");

这里的.truststore是公钥,”SunX509”是公钥的口令,我们需要通过key-tool工具来生成私钥和公钥。

需要用 java keytool 工具来生成TSSL的私钥和公钥:

这里所有需要输入口令的地方我都输入了 thrift , 其实不合理,由于是测试使用,keytool详情自行“某度” 或 “某狗”。

输入下面的命令生成私钥:

1
keytool -genkeypair -alias certificatekey -keyalg RSA -validity 365 -keystore .keystore

password

输入下面的命令生成server.cer证书:

1
keytool -export -alias certificatekey -keystore .keystore -rfc -file server.cer

输入下面的命令生成.truststore:

1
keytool -import -alias certificatekey -file server.cer -keystore .truststore

pass

最后我生成.keystore和.truststore文件放到了项目根目录下,并把client 和 server 路径改了

1
2
3
4
5
// clinet
params.setTrustStore("./.truststore", "thrift", "SunX509", "JKS");

//server
params.setKeyStore("./.keystore", "thrift", null, null);

运行

这个是client 控制台 :

1
2
3
4
5
6
7
8
9
10
Received 1
ping()
Received 2
1+1=2
Received 3
Invalid operation: Cannot divide by 0
Received 4
15-10=5
Received 5
Check log: 5

这个是server 控制台 :

1
2
3
4
5
6
7
Starting the simple server...
Starting the secure server...
ping()
add(1,1)
calculate(1, {DIVIDE,1,0})
calculate(1, {SUBTRACT,15,10})
getStruct(1)

参考

http://thrift.apache.org/tutorial/java
http://thrift.apache.org/

完结,希望能帮助你!