多线程分片文件上传报FileNotFoundException异常
发布日期:2022-04-11 08:52:54
浏览次数:15
分类:技术文章
本文共 5752 字,大约阅读时间需要 19 分钟。
问题描述
出现java.io.IOException:java.io.FileNotFoundException:/home/admin/appName/.default/temp/tomcat.4504264197870423949.7001/work/Tomcat/Localhost/ROOT/upLoad_ff92855a_13c6_49d9_bbdf_1c062fb9bfd9_00000004.tmp(没有那个文件或目录)的错误。
错误部分代码:
// 写入分片的数据accessFile.write(bytes);//这里如果使用multipartFile.getBytes();则会出现FileNotFoundException异常。
这里如果使用multipartFile.getBytes();则会出现FileNotFoundException异常。
全部代码
package com.operative.core.d3DicomFile.controller;import com.aliyun.oss.model.PartETag;import com.aliyuncs.auth.sts.AssumeRoleResponse;import com.operative.base.annotation.OperationLogAnnotation;import com.operative.base.annotation.UnLogin;import com.operative.base.constants.SysLogConstants;import com.operative.base.http.ResponseData;import com.operative.base.http.ResponseStatus;import com.operative.base.http.Result;import com.operative.base.utils.OSSUtils;import com.operative.core.d3DicomFile.entity.D3DicomFile;import com.operative.core.d3DicomFile.service.D3DicomFileService;import com.operative.core.sysLog.entity.SysLog;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.beans.factory.annotation.Value;import org.springframework.scheduling.annotation.Async;import org.springframework.web.bind.annotation.*;import org.springframework.web.multipart.MultipartFile;import java.io.*;import java.util.List;import java.util.Map;import java.util.UUID;import java.util.concurrent.*;import java.util.concurrent.atomic.AtomicInteger;/** ** 前端控制器 *
* * @author cst * @since 2021-09-06 */@CrossOrigin@RestController@RequestMapping("/d3DicomFile")public class D3DicomFileController { @Autowired private D3DicomFileService d3DicomFileService; @Value("${path.static}") private String staticPath; private static final ConcurrentMapTAP_BYTE = new ConcurrentHashMap<>(); // 文件MD5的缓存容器 private static final ConcurrentMap MD5_CACHE = new ConcurrentHashMap<>(); private static final File tempFilePath = new File(""); static AtomicInteger c = new AtomicInteger(1); static ArrayBlockingQueue queue = new ArrayBlockingQueue<>(2000); static ThreadPoolExecutor treadPool = new ThreadPoolExecutor( 6,//核心线程数 6,//最大线程数 0,//针对急救线程的生存时间,0的意思是没任务了直接释放 TimeUnit.MILLISECONDS,//针对急救线程的生存时间,0的意思是没任务了直接释放 queue,//工作队列,设置成了2,队列中最多两个线程排队 r -> new Thread(r,"myThread"+c.getAndIncrement()) ); /** * 大文件分片上传 * @param name 文件名 唯一不变 * @param md5 文件MD5值 * @param size 文件大小 总的大小 * @param chunks 总的分片数 * @param chunk 当前分片数 * @param multipartFile 分片流 * @throws IOException */// @PostMapping("/test") @PostMapping @UnLogin @Async public void chunkUpload1(String name, String md5, Long size, Integer chunks, Integer chunk, String fileName, @RequestParam("file") MultipartFile multipartFile) throws IOException { final byte[] bytes = multipartFile.getBytes(); treadPool.submit(()->{ try { chunkUpload(name, md5, size, chunks, chunk, fileName,bytes, multipartFile); } catch (IOException e) { e.printStackTrace(); } }); } /** * 大文件分片上传 * @param name 文件名 唯一不变 * @param md5 文件MD5值 * @param size 文件大小 总的大小 * @param chunks 总的分片数 * @param chunk 当前分片数 * @param multipartFile 分片流 * @throws IOException */// @PostMapping("/test")// @PostMapping @UnLogin// @Async public void chunkUpload(String name, String md5, Long size, Integer chunks, Integer chunk, String fileName, byte[] bytes, @RequestParam("file") MultipartFile multipartFile) throws IOException { File targetFile = MD5_CACHE.get(md5); //如果map中没有这个file文件路径 if (targetFile == null) { // 没有生成的话就生成一个新的文件,没有做并发控制,多线程上传会出问题 targetFile = new File(System.getProperty("user.dir") + System.getProperty("file.separator") + staticPath + System.getProperty("file.separator"), name); //生成新文件 targetFile.getParentFile().mkdirs(); //放入map中进行标记,表示已经生成文件 MD5_CACHE.put(md5, targetFile); } System.out.println("targetFile"+targetFile); File newFile = new File(System.getProperty("user.dir") + System.getProperty("file.separator") + staticPath +System.getProperty("file.separator"), name); System.out.println("newFile"+newFile); // 可以对文件的任意位置进行读写 RandomAccessFile accessFile = new RandomAccessFile(newFile, "rw"); boolean finished = (chunk.equals(chunks));//是否最后一片 if (finished) { //如果是最后一片 // 移动指针(光标)到指定位置 accessFile.seek(size - multipartFile.getSize()); }else { accessFile.seek((chunk - 1) * multipartFile.getSize()); } // 写入分片的数据 accessFile.write(bytes);//这里如果使用multipartFile.getBytes();则会出现FileNotFoundException异常。 accessFile.close(); if (finished) { System.out.println("success."); // 上传成功 MD5_CACHE.remove(md5); } }}
同一个文件上传时间对比
直接上传
分片上传
可用线程池对线程进行管理
转载地址:https://blog.csdn.net/LJWWD/article/details/123561561 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!
发表评论
最新留言
路过按个爪印,很不错,赞一个!
[***.219.124.196]2024年04月05日 19时37分42秒
关于作者
喝酒易醉,品茶养心,人生如梦,品茶悟道,何以解忧?唯有杜康!
-- 愿君每日到此一游!
推荐文章
Unity可视化编程插件: Bolt,可以像UE4的蓝图那样啦
2019-04-27
Android的.dex、.odex与.oat文件扫盲
2019-04-27
Unity移动应用如何在Bugly上查看崩溃堆栈
2019-04-27
一分钟搞明白Android的.so文件、ABI和CPU的关系
2019-04-27
UGUI的Text描边Outline拓展
2019-04-27
游戏性能指标参考,游戏质量白皮书下载
2019-04-27
游戏帧同步学习笔记
2019-04-27
Mac苹果电脑分辨率不够用,安装SwitchResX这个软件完美解决
2019-04-27
iOS Info.plist知多少
2019-04-27
XCode9之后命令打包需要使用OptionExport.plist
2019-04-27
关于iOS XCode的entitlements文件
2019-04-27
Airtest自动化测试神器,教你实现Unity自动化测试
2019-04-27
模拟器连接端口汇总和常用ADB命令
2019-04-27
ShaderGraph使用教程与各种特效案例:Unity2020(持续更新)
2019-04-27
Unity爆炸、闪电、火焰、雷雨特效Demo
2019-04-27
使用python登录和访问Confluence
2019-04-27