`
hbxflihua
  • 浏览: 679365 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

Netty TCP协议简单实现

阅读更多

Netty的强大之处在于它的高度抽象和封装,对于使用者来说不必过多关心内部实现。当需要有新的需求时,只需简单的添加或者修改相关的Handler类即可。

本章将使用Netty 实现TCP协议,以下为具体实现。

 

1、服务端实现

 

TcpServer.java

package emulator.netty5;

import io.netty.bootstrap.ServerBootstrap;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelOption;
import io.netty.channel.ChannelPipeline;
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.LengthFieldBasedFrameDecoder;
import io.netty.handler.codec.LengthFieldPrepender;
import io.netty.handler.codec.string.StringDecoder;
import io.netty.handler.codec.string.StringEncoder;
import io.netty.util.CharsetUtil;


public class TcpServer {

	public void bind(int port)throws Exception{
		
		//配置服务端Nio线程组
		EventLoopGroup bossGroup = new NioEventLoopGroup();
		EventLoopGroup workerGroup = new NioEventLoopGroup();
		try{
			ServerBootstrap b = new ServerBootstrap();
			b.group(bossGroup, workerGroup)
				.channel(NioServerSocketChannel.class)
				.option(ChannelOption.SO_BACKLOG, 1024)
				.childHandler(new ChildChannelHandler());
			//绑定端口,同步等待成功
			ChannelFuture f = b.bind(port).sync();
			//等待服务端监听端口关闭
			f.channel().closeFuture().sync();
			
		}finally{
			//退出时释放资源
			bossGroup.shutdownGracefully();
			workerGroup.shutdownGracefully();
		}		
	}
	

	private class ChildChannelHandler extends ChannelInitializer<SocketChannel>{
		@Override
		protected void initChannel(SocketChannel channel) throws Exception {
			ChannelPipeline pipeline = channel.pipeline();
			pipeline.addLast("frameDecoder", new LengthFieldBasedFrameDecoder(Integer.MAX_VALUE, 0, 4, 0, 4));
			pipeline.addLast("frameEncoder", new LengthFieldPrepender(4));
			pipeline.addLast("decoder", new StringDecoder(CharsetUtil.UTF_8));
			pipeline.addLast("encoder", new StringEncoder(CharsetUtil.UTF_8));
			pipeline.addLast(new TcpServerHandler());
		}		
	}
		
	public static void main(String[] args) throws Exception{
		int port = 8083;
		new TcpServer().bind(port);		
	}
}

 

TcpServerHandler.java

package emulator.netty5;


import java.io.File;
import java.io.IOException;

import org.apache.commons.io.FileUtils;

import emulator.Constants;
import emulator.util.Dom4JUtil;
import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import io.netty.channel.ChannelFutureListener;
import io.netty.channel.ChannelHandlerAdapter;
import io.netty.channel.ChannelHandlerContext;
import io.netty.util.CharsetUtil;

public class TcpServerHandler extends ChannelHandlerAdapter {

	@Override
	public void channelRead(ChannelHandlerContext ctx, Object msg)
			throws Exception {
		String body = (String)msg;
		System.out.println("request content:\n"+ body);
		//响应
		resp(ctx, body);		
	}
	
	
	/**
	 * 
	 * @param xml
	 */
	private void resp(ChannelHandlerContext ctx, String xml){
		String transCode = Dom4JUtil.header(xml, "TransCode");
		String retUrl = "D:\\workspaces\\eclipse-huifu\\emulator\\xml\\error.xml";
		String retCtt = null;
		System.out.println("交易代码:"+transCode);		
		if(equal(transCode, Constants.TC_DZZH)){//电子账户			
			retUrl = "D:\\workspaces\\eclipse-huifu\\emulator\\xml\\account\\manage\\resp.xml";
		}
		try {
			retCtt = FileUtils.readFileToString(new File(retUrl));
		} catch (IOException e) {
			e.printStackTrace();
		}
		ByteBuf resp = Unpooled.copiedBuffer(retCtt.getBytes());
		ctx.writeAndFlush(resp).addListener(ChannelFutureListener.CLOSE);
		
	}
	
	public static boolean equal(String var, String cons){
		return isNotEmpty(var) && cons.equals(var);		
	}
	
	private static boolean isNotEmpty(String s){
		return (null != s && !"".equals(s));
	}

	
	@Override
	public void channelReadComplete(ChannelHandlerContext ctx) throws Exception {
		super.channelReadComplete(ctx);
		//ctx.flush();
	}
	
	@Override
	public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause)
			throws Exception {
		//super.exceptionCaught(ctx, cause);
		ctx.close();
	}
	
}

 

2、客户端实现

 

TcpClient.java

package emulator.netty5;

import io.netty.bootstrap.Bootstrap;
import io.netty.channel.ChannelFuture;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelOption;
import io.netty.channel.ChannelPipeline;
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 io.netty.handler.codec.LengthFieldBasedFrameDecoder;
import io.netty.handler.codec.LengthFieldPrepender;
import io.netty.handler.codec.string.StringDecoder;
import io.netty.handler.codec.string.StringEncoder;
import io.netty.util.CharsetUtil;

public class TcpClient {
	
	public void connect(int port,String host)throws Exception{
		
		//配置客户端NIO线程组
		EventLoopGroup group = new NioEventLoopGroup();
		
		try{
			Bootstrap b = new Bootstrap();
			b.group(group).channel(NioSocketChannel.class)
				.option(ChannelOption.TCP_NODELAY, true)
				.handler(new ChannelInitializer<SocketChannel>() {
					protected void initChannel(SocketChannel ch) throws Exception {
						ChannelPipeline pipeline = ch.pipeline();
						pipeline.addLast("frameDecoder", new LengthFieldBasedFrameDecoder(Integer.MAX_VALUE, 0, 4, 0, 4));
						pipeline.addLast("frameEncoder", new LengthFieldPrepender(4));
						pipeline.addLast("decoder", new StringDecoder(CharsetUtil.UTF_8));
						pipeline.addLast("encoder", new StringEncoder(CharsetUtil.UTF_8));
						pipeline.addLast("handler", new TcpClientHandler());				
					};
				});
			
			//发起异步连接操作
			ChannelFuture f = b.connect(host,port).sync();
			//等待客户端链路关闭
			f.channel().closeFuture().sync();
		}finally{
			//退出,释放资源
			group.shutdownGracefully();
		}
		
	}
	
	public static void main(String[] args)throws Exception {
		int port = 8083;
		new TcpClient().connect(port, "127.0.0.1");		
	}
}

 

TcpClientHandler.java

package emulator.netty5;

import java.io.File;
import java.io.IOException;
import java.util.logging.Logger;

import org.apache.commons.io.FileUtils;

import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import io.netty.channel.ChannelHandlerAdapter;
import io.netty.channel.ChannelHandlerContext;
import io.netty.util.CharsetUtil;

/**
 * 
 * @author lh
 *
 */
public class TcpClientHandler extends ChannelHandlerAdapter {

	private static final Logger logger = Logger.getLogger(TcpClientHandler.class.getName());
	
	
	@Override
	public void channelActive(ChannelHandlerContext ctx) throws Exception {
		String retUrl = "D:\\workspaces\\eclipse-huifu\\emulator\\xml\\account\\manage\\req.xml";
		String ret = null;
		try {
			ret = FileUtils.readFileToString(new File(retUrl));
		} catch (IOException e) {
			e.printStackTrace();
		}
		ctx.writeAndFlush(ret);
	}
	
	@Override
	public void channelRead(ChannelHandlerContext ctx, Object msg)
			throws Exception {
		String body = (String)msg;
		System.out.println("server response :\n"+body);
	}
	
	@Override
	public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause)
			throws Exception {
		logger.warning("unexpected exception from downstream:"+ cause.getMessage());
		ctx.close();
	}
	
}

 

OVER!

分享到:
评论

相关推荐

    Netty HTTP协议简单实现

    总结,Netty HTTP 协议的简单实现涉及了 Netty 的基础架构、HTTP 编解码器的使用以及自定义处理器的编写。通过理解和实践这些步骤,你可以构建出一个高效的、可扩展的 HTTP 服务。在实际开发中,还需要关注性能优化...

    netty搭建TCP、UDP服务

    总的来说,Netty通过其强大的功能和简单易用的API,极大地降低了网络编程的复杂性,是构建高性能网络应用,尤其是TCP和UDP服务的首选框架。无论是在物联网、游戏服务器、大数据传输还是其他分布式系统中,Netty都能...

    Netty一个端口支持tcp和websocket

    Netty 是一个高性能、异步事件驱动...在处理 TCP 和 WebSocket 时,Netty 提供了丰富的工具和组件,使得这一过程变得相对简单。通过深入了解 Netty 的工作原理和最佳实践,开发者能够构建出高性能、低延迟的网络应用。

    java用netty写udp与tcp.pdf

    Netty 是一个基于 NIO 的客户、服务器端编程框架,使用 Netty 可以确保你快速和简单的开发出一个网络应用,例如实现了某种协议的客户、服务端应用。 在 Netty 中,UDP 编程可以通过使用 `DatagramChannel` 实现,...

    Netty4长连接(服务端+客户端)

    Netty4是一款高性能、异步事件驱动的网络应用程序框架,用于快速开发可维护的高性能协议服务器和客户端。本文将深入探讨Netty4在构建长连接、实现断开重连、心跳检测以及Msgpack编码解码方面的知识。 首先,我们要...

    JAVA写的利用ModbusTCP协议控制现场设备

    本项目"JAVA写的利用ModbusTCP协议控制现场设备"就是一个典型的实例,它利用了Modbus协议的TCP/IP变体来实现对设备的远程控制。Modbus是一种广泛应用的通信协议,允许设备间进行简单数据交换,尤其适合于PLC(可编程...

    netty搭建tcp服务,粘拆包解决

    总的来说,Netty通过提供一系列的工具和组件,使得在TCP服务中处理粘包和拆包变得简单且高效。只要正确地配置和使用解码器,就可以确保数据的完整性和一致性,从而保证网络通信的可靠性。在实际项目中,还需要根据...

    Netty-TCP-thymeleaf.zip

    在"Netty-TCP-thymeleaf.zip"项目中,开发者整合了这两个技术,创建了一个系统,使得硬件设备能够通过TCP协议与Netty服务器进行通信,然后将接收到的硬件运行数据实时展示在基于Thymeleaf的Web页面上,实现了硬件...

    netty实现简单的聊天

    消息传递通常基于TCP协议,因为TCP提供了可靠的、面向连接的数据传输服务,能够保证消息的顺序和完整性。然而,这也意味着需要处理TCP粘包和拆包问题,通过自定义的FrameDecoder可以解决这个问题,确保每条消息都能...

    java 通过modbus rtu协议,tcp 协议 通讯源码

    Modbus是一种简单的主从式通信协议,最初设计用于模拟量和数字量的读写操作。它支持多种通信介质,包括串行链路(如RTU模式)和网络(如TCP/IP)。RTU模式通常用于近距离、低速率的串口通信,而TCP模式则适应于更远...

    springboot+netty 实现简单的一对一聊天

    在本文中,我们将深入探讨如何使用Spring Boot和Netty实现一个简单的一对一聊天应用程序。Spring Boot是Java领域中广泛使用的微服务框架,它简化了配置并提供了快速启动的应用程序开发体验。Netty则是一个高性能、...

    整合netty实时通讯

    Netty 提供了对 WebSocket 协议的全面支持,使得开发者可以轻松实现 WebSocket 服务器和客户端。 1. **Netty 框架简介** - Netty 的核心是它的事件驱动模型,基于 NIO(非阻塞 I/O)和 Channel 体系结构。这个模型...

    一个基于Nacos、Netty、Protobuf 实现的简单易懂的RCP框架.zip

    标题中的“一个基于Nacos、Netty、Protobuf 实现的简单易懂的RCP框架”指的是一个使用了阿里巴巴的Nacos服务发现平台、高性能的网络库Netty以及高效的序列化协议Protobuf来构建的远程过程调用(RPC)框架。...

    netty+websocket实现心跳和断线重连

    WebSocket 是一种在单个 TCP 连接上进行全双工通信的协议,它为客户端和服务器提供了低延迟、双向通信的能力,非常适合实时应用。Netty 提供了 WebSocket Server 和 WebSocket Client 的实现,使得构建基于 ...

    netty简单聊天室

    Netty支持多种网络协议,如TCP、UDP等。在这个聊天室中,可能使用了自定义的简单文本协议,或者基于HTTP或WebSocket的协议。Netty通过ChannelHandler来实现协议解析和编码。 5. **客户端与服务器交互**: client....

    Java实现modbus tcp协议数据读写,项目内包含modbus slave仿真软件

    本项目专注于使用Java语言实现Modbus TCP/IP协议的读写功能,提供了两种不同的实现方案:jlibmodbus和modbus4j库。这两种库都是Java社区开发的开源工具,专门用于处理Modbus通信。 首先,我们来看jlibmodbus。...

    Android基于Netty框架实现通信

    Netty是一个高性能、异步事件驱动的网络应用程序框架,适用于多种协议的服务器和客户端应用。本篇文章将详细探讨如何在Android环境中利用Netty来构建通信系统。 首先,我们需要理解Android环境对Netty的特殊性。...

    Netty (netty-netty-5.0.0.Alpha2.tar.gz)

    Netty 是根据从实现许多协议(如 FTP、SMTP、HTTP 以及各种二进制和基于文本的旧协议)中获得的经验精心设计的。因此,Netty 成功地找到了一种方法,可以在不妥协的情况下实现易于开发、性能、稳定性和灵活性。

    netty-netty-3.10.6.Final.tar.gz

    Netty 是根据从实现许多协议(如 FTP、SMTP、HTTP 以及各种二进制和基于文本的旧协议)中获得的经验精心设计的。因此,Netty 成功地找到了一种方法,可以在不妥协的情况下实现易于开发、性能、稳定性和灵活性。

Global site tag (gtag.js) - Google Analytics