需求文档
echo客户端
- 连接到服务器
- 发送一个或多个消息
- 对于每个消息。等待并接受从服务器发回的相同的消息
- 关闭连接
1. 通过channelHandler 实现客户端逻辑
如同服务器,客户端将拥有一个用来处理数据的ChannelInBoundHandler。在这个场景下,你将扩展SimpleChannelInBoundHandler类以处理所有必须的任务,代码如下
- channelActive() –在到服务器的连接已建立之后被调用;
- channelRead0()–当从服务器收到一条信息时被调用
- exceptionCaught()–在处理过程中引发异常时被调用
public class EchoClient extends SimpleChannelInboundHandler<ByteBuf> {
@Override
public void channelActive(ChannelHandlerContext ctx) throws Exception {
ctx.writeAndFlush(Unpooled.copiedBuffer("Netty rocks", CharsetUtil.UTF_8));
}
@Override
protected void channelRead0(ChannelHandlerContext ctx, ByteBuf byteBuf) throws Exception {
//当被通知Channel是活跃当额时候,发送一条消息
System.out.println("--cient received:"+byteBuf.toString(CharsetUtil.UTF_8));
}
@Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
cause.printStackTrace();
ctx.close();
}
}
在客户端,当channelRead0()方法完成时,已经有传入消息,并且已经处理完成它了,当该方返回时,SimpleChannelInBoundHandle负责释放指向保存该消息的ByteBuf的内存引用
在EchoServerHandler中,扔需要将传入的消息回送给发送者,而write()操作是异步的,直到channelRead()
方法返回后可能仍然没有完成,为此,EchoClient扩展了 ChnelInboubdHandlerAdapter,其在这个时间点上不会释放信息
在channelRead-Complete()方法中,当writeAndFlush()方法被调用时被释放
引导客户端
需求
引导客户端类似于引导服务器,不同的是,客户端是使用主机和端口参数来连接远程地址,也就是echo服务器的地址,而不是绑定到一个一直被监听的端口
package org.example;
import io.netty.bootstrap.Bootstrap;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioSocketChannel;
import java.net.InetSocketAddress;
public class EchoClient {
private final String host;
private final int port;
public EchoClient(String host,int port){
this.host = host;
this.port = port;
}
public void start() throws Exception{
EventLoopGroup group = new NioEventLoopGroup();
try {
//创建bootstrap
Bootstrap b = new Bootstrap();
//指定EventLoopGroup 以处理客户端事件,需要适用于NIO的实现
b.group(group).channel(NioSocketChannel.class)
//适用于NIO传输的的channel类型
.remoteAddress(new InetSocketAddress(host,port))
//设置服务器的InetSocketAddress地址
.handler(new ChannelInitializer<SocketChannel>() {
// 在创建Chnannel时向pipLine添加一个EchoClient实例
@Override
protected void initChannel(SocketChannel socketChannel) throws Exception {
socketChannel.pipeline().addLast(new EchoHandler());
}
});
// 连接到远程节点,阻塞直到连接完成
ChannelFuture f = b.connect().sync();
//阻塞,直到Channel关闭
}finally {
group.shutdownGracefully().sync();
}
}
public static void main(String[] args) throws Exception {
new EchoClient("localhost",8002).start();
}
}
转载请注明来源,欢迎对文章中的引用来源进行考证,欢迎指出任何有错误或不够清晰的表达。可以在下面评论区评论,也可以邮件至 ggchzzz@163.com