netty 文件传输

FileServer

package com.zhaowb.netty.ch13_1;

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

import java.io.File;

public class FileServer {

    public void run(int port) throws Exception {

        EventLoopGroup bossGroup = new NioEventLoopGroup();
        EventLoopGroup workerGroup = new NioEventLoopGroup();
        try {
            ServerBootstrap b = new ServerBootstrap();

            b.group(bossGroup, workerGroup)
                    .channel(NioServerSocketChannel.class)
                    .option(ChannelOption.SO_BACKLOG, 100)
                    .childHandler(new ChannelInitializer<SocketChannel>() {
                        @Override
                        protected void initChannel(SocketChannel ch) throws Exception {
                            ch.pipeline().addLast(
                                    new StringEncoder(CharsetUtil.UTF_8),// 将文件内容编码为字符串

                                    // 这2个解码器一起使用就是文本换行解码器
                                    new LineBasedFrameDecoder(1024),// 根据回车换行符对数据包进行解码
                                    new StringDecoder(CharsetUtil.UTF_8),// 将数据包解码成字符串,

                                    new FileServerHandler()
                            );
                        }
                    });
            ChannelFuture f = b.bind(port).sync();
            System.out.println("Start file server at port : " + port);
            f.channel().closeFuture().sync();

        } finally {
            bossGroup.shutdownGracefully();
            workerGroup.shutdownGracefully();
        }
    }

    public static void main(String[] args)  throws Exception{

        int port = 8080;
        new FileServer().run(port);
    }
}

FileServerHandler

package com.zhaowb.netty.ch13_1;

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

import java.io.File;
import java.io.RandomAccessFile;
import java.sql.SQLOutput;

public class FileServerHandler extends SimpleChannelInboundHandler<String> {

    private static final String CR = System.getProperty("line.separator");

    @Override
    protected void messageReceived(ChannelHandlerContext ctx, String msg) throws Exception {
        File file = new File(msg);
        // 校验文件的合法性,不存在构造异常消息返回。如果存在使用RandomAccessFile 以只读的方式打开文件,然后使用netty的
        //  DefaultFileRegion 进行文件传输,
        //          FileChannel file, 文件通道,用于对文件进行读写操作
        //          long position,文件操作的指针位置,读取或写入的起始点
        //          long count,操作的总字符数
        if (file.exists()){
            if (!file.isFile()){
                ctx.writeAndFlush("Not a file " +  msg);
                return;
            }
            ctx.write(file +" " + file.length() + CR);
            RandomAccessFile randomAccessFile = new RandomAccessFile(msg,"r");
            FileRegion region = new DefaultFileRegion(randomAccessFile.getChannel(),0,randomAccessFile.length());
            ctx.write(region);
            ctx.writeAndFlush(CR); // 写入换行符,告诉CMD控制台,文件传输结束。
            randomAccessFile.close();
        }else {
            ctx.writeAndFlush("File not found " + file + CR);
        }
    }
    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        cause.printStackTrace();
        ctx.close();
    }

    @Override
    public void channelActive(ChannelHandlerContext ctx) throws Exception {
        System.out.println("连接成功!");
    }
}

启动FileServer 之后再CMD控制台 输入 telnet localhost 8080

然后输入文件的绝对路径比如 D:hello.txt ,在操作时,出现了中文乱码的问题,应该是Windows的原因。

原文地址:https://www.cnblogs.com/zwb1234/p/9597918.html