一、需求
公司电脑不让使用U盘,又不想通过公司聊天软件传输,怕被监控。但是通过QQ、微信传输文件对文件大小又有限制。基于种种原因,自己简单写了个服务端、客户端进行文件传输,大文件最好在局域网内进行数据传输。
二、pom依赖
三、定义服务端
服务端用于接收文件
@Slf4j
public class FileServer {
/**
* 设置服务端端口
*/
public static final int PORT = 9999;
/**
* 指定保存文件地址 例如要把公司文件A,传输到家里电脑上,存为B文件,这里就是B文件的地址
*/
public static final String PATH = "/Users/admin/Downloads/yinyue31.zip";
public static void main(String[] args) {
FileChannel fileChannel = null;
SocketChannel socketChannel = null;
try {
// 1. 创建并配置 服务器套接字通道 ServerSocketChannel
ServerSocketChannel serverSocketChannel = ServerSocketChannel.open();
//设置端口
serverSocketChannel.socket().bind(new InetSocketAddress(PORT));
// 注意这里使用阻塞模式, 不调用该代码
// serverSocketChannel.configureBlocking(false);
// 2. 获取文件通道
fileChannel = new FileOutputStream(PATH).getChannel();
log.info("服务端启动完毕******等待接收文件");
// 3. 阻塞等待
socketChannel = serverSocketChannel.accept();
log.info("服务端开始接收文件******");
long startTime = System.currentTimeMillis();
// 4. 零拷贝核心操作
fileChannel.transferFrom(socketChannel, 0, Long.MAX_VALUE);
log.info("服务端接收文件结束,耗时{}ms", System.currentTimeMillis() - startTime);
} catch (IOException e) {
log.error("服务端接收异常{}", e);
} finally {
// 5. 释放资源
if (null != socketChannel) {
try {
socketChannel.close();
} catch (IOException e) {
log.error("服务端关闭流socketChannel异常{}", e);
}
}
if (null != fileChannel) {
try {
fileChannel.close();
} catch (IOException e) {
log.error("服务端关闭流socketChannel异常{}", e);
}
}
}
}
}
四、定义客户端
客户端用于发送文件
@Slf4j
public class FileClient {
/**
* 设置需要访问的服务端IP
*/
public static final String IP = "127.0.0.1";
/**
* 设置需要访问的服务端端口
*/
public static final int PORT = 9999;
/**
* 指定读取的文件地址(要被传输的文件) 例如要把文件A传输到家里电脑上,这里就是A文件的地址
*/
public static final String PATH = "/Users/admin/Downloads/ioa.zip";
public static void main(String[] args) {
FileChannel fileChannel = null;
SocketChannel socketChannel = null;
try {
// 1. 创建并配置 服务器套接字通道 ServerSocketChannel
socketChannel = SocketChannel.open();
socketChannel.connect(new InetSocketAddress(IP, PORT));
//socketChannel.configureBlocking(false);
// 2. 从文件输入流中获取文件通道 ( FileChannel )
fileChannel = new FileInputStream(PATH).getChannel();
long startTime = System.currentTimeMillis();
// 3. 零拷贝传输数据, 注意记录每次拷贝的起始位置
long transferLen;
long totalCount = 0;
log.info("文件开始传输******");
// 使用零拷贝将文件数据传到服务器, 循环终止条件是传输结果小于等于 0
while ((transferLen = fileChannel.transferTo(totalCount, Long.MAX_VALUE, socketChannel)) > 0) {
totalCount += transferLen;
log.info("文件大小:{}", transferLen);
}
log.info("文件传输完毕, 用时:{}ms", System.currentTimeMillis() - startTime);
} catch (IOException e) {
log.error("客户端传输异常{}", e);
} finally {
// 5. 释放资源
if (null != socketChannel) {
try {
socketChannel.close();
} catch (IOException e) {
log.error("客户端关闭流socketChannel异常{}", e);
}
}
if (null != fileChannel) {
try {
fileChannel.close();
} catch (IOException e) {
log.error("客户端关闭流fileChannel异常{}", e);
}
}
}
}
}
五、修改重要参数
FileClient
这个类是客户端,要把文件传输到服务端。公司电脑启动这个类。
1、设置需要访问的服务端IP public static final String IP = “127.0.0.1”; 2、设置需要访问的服务端端口 public static final int PORT = 9999; 3、指定读取的文件地址(要被传输的文件) 例如要把文件A传输到家里电脑上,这里就是A文件的地址 public static final String PATH = “/Users/admin/Downloads/ioa.zip”;
FileServer
这个类是服务端,要接收文件的服务。家里电脑启动这个类。
1、设置服务端端口 public static final int PORT = 9999; 2、指定保存文件地址 例如要把公司文件A,传输到家里电脑上,存为B文件,这里就是B文件的地址 public static final String PATH = “/Users/admin/Downloads/yinyue31.zip”;
六、测试
需要在一个局域网下,台式机可能不方便。最好有一台电脑是笔记本。 1、公司电脑和家里电脑都用idea打开这个工程 2、家里电脑运行FileServer类中的main方法 3、公司电脑运行FileClient类中的main方法
七、完整代码
GitHub地址:https://github.com/9925dev/netty-transmission-file
相关文章
发表评论