您的位置:首页 > 其它

Netty——简单创建服务器、客户端通讯

2017-11-10 10:58 204 查看

       Netty 是一个基于NIO的客户、服务器端编程框架,使用Netty 可以确保你快速和简单的开发出一个网络应用,例如实现了某种协议的客户,服务端应用。Netty相当简化和流线化了网络应用的编程开发过程,例如,TCP和UDP的socket服务开发。

  Netty简单来说就是socket通讯,支持多协议的通讯

 对 创建 netty 的过程作了详细的解析

1、简单创建一个Netty服务器

package com.netty.test;

import java.net.InetAddress;

import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelOption;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.SocketChannel;
import io.netty.channel.socket.nio.NioServerSocketChannel;
import io.netty.handler.codec.DelimiterBasedFrameDecoder;
import io.netty.handler.codec.Delimiters;
import io.netty.handler.codec.string.StringDecoder;
import io.netty.handler.codec.string.StringEncoder;

/**
* Netty4 服务端代码
*
*/
public class HelloWorldServer {

public static void main(String[] args) {
// EventLoop 代替原来的 ChannelFactory
EventLoopGroup bossGroup = new NioEventLoopGroup();
EventLoopGroup workerGroup = new NioEventLoopGroup();

try {
ServerBootstrap serverBootstrap = new ServerBootstrap();        //创建 一个netty 服务器 // server端采用简洁的连写方式,client端才用分段普通写法。 serverBootstrap.group(bossGroup, workerGroup) .channel(NioServerSocketChannel.class)              // 指定channel[通道]类型 .childHandler(new ChannelInitializer<SocketChannel>() {    // 指定Handler [操纵者]
@Override public void initChannel(SocketChannel ch) throws Exception { // 以("\n")为结尾分割的 解码器 ch.pipeline().addLast("framer", new DelimiterBasedFrameDecoder(8192, Delimiters.lineDelimiter())); // 字符串 解码 和 编码 默认的 StringDecoder 字符串形式输出 ch.pipeline().addLast("decoder", new StringDecoder()); ch.pipeline().addLast("encoder", new StringEncoder()); ch.pipeline().addLast(new HelloServerHandler());     // 添加自己的对 上传数据的处理 }
}).option(ChannelOption.SO_KEEPALIVE, true);
       ChannelFuture f = serverBootstrap.bind(8000).sync();           // 绑定 8000 端口 f.channel().closeFuture().sync(); } catch (InterruptedException e) { } finally { workerGroup.shutdownGracefully(); // 销毁 netty bossGroup.shutdownGracefully(); } } /** * 自己对 处理数据 * * @author flm * 2017年11月10日 */ private static class HelloServerHandler extends ChannelInboundHandlerAdapter { @Override public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception { // 收到消息直接打印输出 System.out.println(ctx.channel().remoteAddress() + " Say : " + msg); // 返回客户端消息 - 我已经接收到了你的消息 ctx.writeAndFlush("server Received your message !\n"); } /* * * 覆盖 channelActive 方法 在channel被启用的时候触发 (在建立连接的时候) * * channelActive 和 channelInActive 在后面的内容中讲述,这里先不做详细的描述 */ @Override public void channelActive(ChannelHandlerContext ctx) throws Exception { System.out.println("RamoteAddress : " + ctx.channel().remoteAddress() + " active !"); ctx.writeAndFlush("Welcome to " + InetAddress.getLocalHost().getHostName() + " service!\n"); //回复 super.channelActive(ctx); } }

 

 

2、netty 客户端 创建

package com.netty.test;

import java.net.InetSocketAddress;
import java.util.Date;

import io.netty.bootstrap.Bootstrap;
import io.netty.channel.Channel;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelPipeline;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioSocketChannel;
import io.netty.handler.codec.DelimiterBasedFrameDecoder;
import io.netty.handler.codec.Delimiters;
import io.netty.handler.codec.string.StringDecoder;
import io.netty.handler.codec.string.StringEncoder;

/**
* Netty4 客户端代码
*
*/
public class HelloWorldClient {

public static void main(String args[]) {

// Bootstrap,且构造函数变化很大,这里用无参构造。
Bootstrap bootstrap = new Bootstrap();
// 指定channel[通道]类型
bootstrap.channel(NioSocketChannel.class);
// 指定Handler [操纵者]
bootstrap.handler(new ChannelInitializer<Channel>() {

@Override
protected void initChannel(Channel ch) throws Exception {
ChannelPipeline pipeline = ch.pipeline();

/*
* 这个地方的 必须和服务端对应上。否则无法正常解码和编码
*
*/
pipeline.addLast("framer", new DelimiterBasedFrameDecoder(8192, Delimiters.lineDelimiter()));
pipeline.addLast("decoder", new StringDecoder());
pipeline.addLast("encoder", new StringEncoder());

// 客户端的逻辑,自己对数据处理
pipeline.addLast(new HelloClientHandler());
}
});
// 指定EventLoopGroup [事件 组]
bootstrap.group(new NioEventLoopGroup());

// 连接到本地的8000端口的服务端
bootstrap.connect(new InetSocketAddress("127.0.0.1", 8000));

}

/**
* 客户端的逻辑,自己对数据处理
*
* @author flm
* 2017年11月10日
*/
private static class HelloClientHandler extends ChannelInboundHandlerAdapter {

/*
* 监听 服务器 发送来的数据
*/
@Override
public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception {

System.out.println("Server say : " + msg.toString());

}

/*
* 启动客户端 时触发
*/
@Override
public void channelActive(ChannelHandlerContext ctx) throws Exception {
System.out.println("Client active ");
ctx.writeAndFlush("我是 client " + new Date() + "\n");
super.channelActive(ctx);
}

/*
* 关闭 客户端 触发
*/
@Override
public void channelInactive(ChannelHandlerContext ctx) throws Exception {
System.out.println("Client close ");
super.channelInactive(ctx);
}
}
}

 

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: