netty socket相关的一些整理实践

一、Netty概述

    Netty 是由JBOSS提供的一个java开源框架,Netty提供异步的、事件驱动的网络应用程序框架和工具,用以快速开发高性能、高可靠性的网络服务器和客户端程序。
    Netty 是一个基于NIO的客户、服务器端编程框架,Netty相当简化和流线化了网络应用的编程开发过程,例如,TCP和UDP的socket服务开发,同时吸收了多种协议的实现经验,这些协议包括FTP,SMTP,HTTP,各种二进制,文本协议。

    使用Netty可以实现一个Socket通讯,包括客户端和服务端,通过服务端进行监听,客户端发送信息,服务端可进行接收,并进行返回数据,完成一个完整的通讯。

二、基于netty channel的writeAndFlush 客户端发送信息实践,发送并接收反馈信息

    import io.netty.bootstrap.Bootstrap;
    import io.netty.channel.Channel;
import io.netty.channel.ChannelFuture;
import io.netty.channel.EventLoopGroup;
import io.netty.channel.nio.NioEventLoopGroup;
import io.netty.channel.socket.nio.NioSocketChannel;
import java.util.concurrent.CountDownLatch;

public class ClientUtil {
    
    private static final String SOCKET_SERVER_IP = "127.0.0.1";
    private static final int SOCKET_SERVER_PORT = 8899;
    
    public synchronized static String socketRequest(String requestStr) throws Exception{
        EventLoopGroup eventLoopGroup = new NioEventLoopGroup();
        try {
            CountDownLatch lathc = new CountDownLatch(1);
            MyClientInitializer client = new MyClientInitializer(lathc);
            //客户端启动器
            Bootstrap bootstrap = new Bootstrap();
            bootstrap.group(eventLoopGroup).channel(NioSocketChannel.class).handler(client);
            ChannelFuture channelFuture = bootstrap.connect(SOCKET_SERVER_IP, SOCKET_SERVER_PORT).sync();
            if(channelFuture.isSuccess()){
                Channel channel = channelFuture.channel();
                channel.writeAndFlush(requestStr);
                lathc.await();//开启等待会等待服务器返回结果之后再执行下面的代码
                return client.getReturn_msg();
            }
        }catch(Exception e){
            e.printStackTrace();
        }finally{
            eventLoopGroup.shutdownGracefully();
        }
        return null;
    }

}

import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;

import java.time.LocalDateTime;
import java.util.concurrent.CountDownLatch;


public class MyClientHandler extends SimpleChannelInboundHandler {
    
    private String return_msg;
    
    private CountDownLatch lathc;

    public MyClientHandler(CountDownLatch lathc) {
        this.lathc = lathc;
    }

    @Override
    protected void channelRead0(ChannelHandlerContext ctx, String msg) throws Exception {
        System.out.println("client 获取返回信息: " + msg +",ip:"+ctx.channel().remoteAddress());
        this.return_msg = msg;
        lathc.countDown();
       /* Thread.sleep(5000);

        ctx.writeAndFlush("from client: " + LocalDateTime.now());*/
    }

    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        cause.printStackTrace();
        ctx.close();
    }

    /**
     * channel处于活动状态后的回调(链接建立好了过后)
     * @param ctx
     * @throws Exception
     */
    @Override
    public void channelActive(ChannelHandlerContext ctx) throws Exception {
//        ctx.channel().writeAndFlush("来与客户端!");
    }

    public String getReturn_msg() {
        return return_msg;
    }

    public void setReturn_msg(String return_msg) {
        this.return_msg = return_msg;
    }
}

import java.util.concurrent.CountDownLatch;
import io.netty.channel.ChannelInitializer;
import io.netty.channel.ChannelPipeline;
import io.netty.channel.socket.SocketChannel;
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 MyClientInitializer extends ChannelInitializer {
    
    private MyClientHandler myClientHandler;
    
    private CountDownLatch lathc;

    public MyClientInitializer(CountDownLatch lathc) {
        this.lathc = lathc;
    }

    @Override
    protected void initChannel(SocketChannel ch) throws Exception {
        myClientHandler = new MyClientHandler(lathc);
        ChannelPipeline pipeline = ch.pipeline();
        //编解码的处理
        pipeline.addLast(new LengthFieldBasedFrameDecoder(Integer.MAX_VALUE, 0, 4, 0, 4));
        pipeline.addLast(new LengthFieldPrepender(4));
        pipeline.addLast(new StringDecoder(CharsetUtil.UTF_8));
        pipeline.addLast(new StringEncoder(CharsetUtil.UTF_8));
        //自己的处理器
        pipeline.addLast(myClientHandler);
    }
    
    public String getReturn_msg() {
        return myClientHandler.getReturn_msg();
    }
}


你可能感兴趣的:(开发总结,开发总结)