RPC我还是第一次使用,而且Avro更是第一次学习。
1.编写Schema文件
新建user.avsc文件,内容如下,这里的namespace就是生成代码后的类的包路径:
1
2
3
4
5
6
7
8
9{"namespace": "com.example",
"type": "record",
"name": "User",
"fields": [
{"name": "name", "type": "string"},
{"name": "favorite_number", "type": ["int", "null"]},
{"name": "favorite_color", "type": ["string", "null"]}
]
}
2.编写avdl文件,生成接口
新建avdl接口说明文件,内容如下,这里的namespace就是生成代码后的类的包路径:
1
2
3
4
5
6
7
8
9
10@namespace("com.example.protocol")
protocol HelloProtocol {
import schema "user.avsc";
record Message {
string id;
string msg;
}
string hello(com.example.User user);
}
3.下载avro-tools-1.9.1.jar和avro-1.9.1.jar
管网下载,就不说了。
4.命令行执行生成rpc调用方法和序列化类
先执行idl命令,根据avdl文件生成json文件,然后执行compile protocol,生成接口文件。
1
2
3
4## 1.生成协议的json文件
java -jar .\avro-tools-1.9.1.jar idl .\helloprotocol.avdl .\helloprotocol.json
## 2.自动生成接口类
java -jar .\avro-tools-1.9.1.jar compile protocol .\helloprotocol.json .
avro_tool工具将自动生成类文件夹:
文件夹中包括了序列化和反序列的User类:
以及供远程调用的远程接口及远程方法:
注意
执行protocol命令时,最后的点,是表示在当前目录下生成类和方法,否则会出现错误:
5.新建maven工程avro-rpc的服务端
在maven的pom.xml文件中添加如下内容:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71<?xml version="1.0" encoding="UTF-8"?>
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
4.0.0
com.example
AvroRPCServer
1.0-SNAPSHOT
AvroRPCServer
http://www.example.com
UTF-8
1.7
1.7
org.apache.avro
avro
1.9.1
org.apache.avro
avro-ipc
1.9.1
org.apache.avro
avro-ipc-netty
1.9.1
org.apache.avro
avro-maven-plugin
1.9.1
generate-sources
schema
${project.basedir}/src/main/avro/
${project.basedir}/src/main/java/
org.apache.maven.plugins
maven-compiler-plugin
1.6
1.6
注意添加ipc支持,否则idea会报错:
6.实现协议接口
将第四章生成的HelloProtocol.java接口以及数据类User.java复制到工程目录中(注意你的类中包的名字)。然后新建类HelloService,并实现HelloProtocol接口,这里的user.getName()等方法根据自己写的属性进行替换,接口方法也需要适当的调整。
1
2
3
4
5
6
7
8
9
10import org.apache.avro.AvroRemoteException;
public class HelloService implements HelloProtocol{
@Override
public CharSequence hello(User user){
System.out.println(user.getName() + "," + user.getFavoriteNumber() + "," + user.getFavoriteColor());
return "hai i`m from avro service";
}
}
7.发布服务
实现了HelloService,就可以在主程序中发布服务了,监听了端口号65111。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23import org.apache.avro.ipc.Responder;
import org.apache.avro.ipc.Server;
import org.apache.avro.ipc.netty.NettyServer;
import org.apache.avro.ipc.specific.SpecificResponder;
import java.net.InetSocketAddress;
/**
* Hello world!
*
*/
public class App
{
@SuppressWarnings("unused")
private static Server server;
public static void main( String[] args )
{
System.out.println( "Hello World!" );
//服务端协议
Responder responder=new SpecificResponder(HelloProtocol.class, new HelloService());
server=new NettyServer(responder, new InetSocketAddress(65111));
}
}
运行main程序,等待连接:
注意添加NettyServer的maven,否则报错:
8.新建RPC的客户端工程
新建AvroRPCClient的maven工程,pom.xml参考服务端。
9.复制类文件
同服务端一样,将avro-tool生成的User.java和HelloProtocol.java复制到工程目录中,注意包路径。
10.编写Main函数,调用远程接口
在main函数中,添加如下代码:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31package com.proheng;
import org.apache.avro.ipc.netty.NettyTransceiver;
import org.apache.avro.ipc.specific.SpecificRequestor;
import java.net.InetSocketAddress;
/**
* Hello world!
*
*/
public class App
{
public static void main( String[] args )
{
System.out.println( "Hello World!" );
try{
NettyTransceiver client = new NettyTransceiver(new InetSocketAddress(65111));
HelloProtocol proxy = SpecificRequestor.getClient(HelloProtocol.class, client);
User user = new User();
user.setName("xiaofen");
user.setFavoriteNumber(1);
user.setFavoriteColor("dsf");
System.out.println(proxy.hello(user));
}catch (Exception e){
System.out.println(e);
}
}
}
运行客户端main,输出如下:
查看服务端输出:
测试成功!!!