JAVA实现附件分片上传

  1. 项目需求
    由于文件服务器的限制,单次调用文件上传接口上传的附件的大小不能超过500MB,对于超过500MB的附件需要分片上传
  2. 程序示例
    private Boolean uploadFile(File uploadFile, String uploadUrl, List<Object> fileList) {final long CHUNK_SIZE = 500L * 1024 * 1024; // 500MBlong fileSize = uploadFile.length();int totalChunk = (int) Math.ceil((double) fileSize / CHUNK_SIZE);double totalSizeInMB = fileSize / 1024.0 / 1024.0;String md5 = DigestUtils.md5Hex(uploadFile.getName());System.out.printf("开始上传附件:%s,大小:%.2f MB,总分片:%d%n",uploadFile.getName(), totalSizeInMB, totalChunk);long startTime = System.currentTimeMillis(); // ⏱ 开始时间try (RandomAccessFile raf = new RandomAccessFile(uploadFile, "r")) {for (int i = 0; i < totalChunk; i++) {int fileChunk = i + 1;long currentChunkSize = Math.min(CHUNK_SIZE, fileSize - i * CHUNK_SIZE);byte[] chunkData = new byte[(int) currentChunkSize];raf.seek(i * CHUNK_SIZE);raf.readFully(chunkData);try (CloseableHttpClient client = HttpClients.createDefault()) {HttpPost post = new HttpPost(uploadUrl);HttpEntity multipart = MultipartEntityBuilder.create().setCharset(StandardCharsets.UTF_8).setMode(HttpMultipartMode.RFC6532).addTextBody("fileName", uploadFile.getName().replaceFirst("\\.[^.]+$", ""), ContentType.TEXT_PLAIN.withCharset(StandardCharsets.UTF_8)).addTextBody("fileForm", uploadFile.getName().contains(".") ? uploadFile.getName().substring(uploadFile.getName().lastIndexOf('.') + 1) : "", ContentType.TEXT_PLAIN).addTextBody("fileChunk", String.valueOf(fileChunk), ContentType.TEXT_PLAIN).addTextBody("totalChunk", String.valueOf(totalChunk), ContentType.TEXT_PLAIN).addTextBody("md5", md5, ContentType.TEXT_PLAIN).addBinaryBody("file", chunkData, ContentType.DEFAULT_BINARY, uploadFile.getName()).build();post.setEntity(multipart);try (CloseableHttpResponse response = client.execute(post)) {int status = response.getStatusLine().getStatusCode();if (status == 200) {System.out.printf("分片 %d/%d 上传成功,大小:%.2f MB%n",fileChunk, totalChunk, currentChunkSize / 1024.0 / 1024.0);if (fileChunk == totalChunk) {String json = EntityUtils.toString(response.getEntity(), "UTF-8");ObjectMapper mapper = new ObjectMapper();@SuppressWarnings("unchecked")Map<String, Object> result = mapper.readValue(json, Map.class);@SuppressWarnings("unchecked")List<Map<String, Object>> dataArray = (List<Map<String, Object>>) result.get("data");for (Map<String, Object> data : dataArray) {JSONObject file = new JSONObject();file.put("fileName",      data.get("fileName"));file.put("fileSize",      data.get("fileSize"));file.put("fileExtension", data.get("fileExtension"));file.put("fileFullName",  data.get("fileFullName"));file.put("id",            data.get("id"));file.put("fileSizeText",  data.get("fileSizeText"));file.put("url",           data.get("url"));file.put("md5",           data.get("md5"));file.put("shadowLinkCode",data.get("shadowLinkCode"));fileList.add(file);}}} else {System.err.printf("分片上传失败:%d/%d,HTTP Status = %d%n", fileChunk, totalChunk, status);return false;}}}}long endTime = System.currentTimeMillis(); // ⏱ 结束时间double durationSeconds = (endTime - startTime) / 1000.0;double speed = totalSizeInMB / durationSeconds;System.out.printf("附件上传完成:%s,总耗时:%.2f 秒,平均速度:%.2f MB/s%n",uploadFile.getName(), durationSeconds, speed);return true;} catch (IOException e) {e.printStackTrace();return false;}
    }
  3. 日志示例
    开始上传附件:report.zip,大小:1100.00 MB,总分片:3
    分片 1/3 上传成功,大小:500.00 MB
    分片 2/3 上传成功,大小:500.00 MB
    分片 3/3 上传成功,大小:100.00 MB
    附件上传完成:report.zip,总耗时:18.32 秒,平均速度:60.08 MB/s

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/diannao/94733.shtml
繁体地址,请注明出处:http://hk.pswp.cn/diannao/94733.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

PyTorch环境安装

pytorch安装 建议&#xff08;非常强烈的那种&#xff09;用Anaconda创建一个虚拟环境&#xff0c;用于运行安装你的PyTorch conda create -n universal python3.9 1. 基础认知 cuDNN&#xff08;CUDA Deep Neural Network library&#xff09;是 NVIDIA 开发的用于深度学习…

机场风云:AI 云厂商的暗战,广告大战一触即发

文 | 大力财经机场广告牌背后&#xff0c;一场决定云计算未来格局的隐形战争已悄然打响。当你匆匆走过首都机场T3航站楼的通道&#xff0c;巨幅屏幕上“阿里云&#xff1a;开源的力量”与不远处“百度智能云&#xff1a;AI落地领导者”的广告交相辉映。它们精准锁定着日均10万的…

MLE-STAR:谷歌AI推出的机器学习工程新范式,一种搜索驱动、精准优化的智能代理

最近看到 Google AI 发布了一个叫 MLE-STAR&#xff08;Machine Learning Engineering via Search and Targeted Refinement&#xff09;的新系统&#xff0c;说实话&#xff0c;第一眼看完论文和相关介绍后&#xff0c;我是有点震撼的。这不只是一次简单的“LLM 自动化”拼凑…

3-防火墙

防火墙 一 防火墙概述防火墙概述防火墙是一个位于内部网络与外部网络之间的安全系统&#xff08;网络中不同区域之间&#xff09;&#xff0c;是按照一定的安全策略建立起来的硬件或软件系统&#xff0c;用于流量控制的系统&#xff08;隔离&#xff09;&#xff0c;保护内部网…

python opencv 调用 海康威视工业相机(又全又细又简洁)

1.准备工作 准备一个海康相机 下载MVS 和SDK 海康机器人-机器视觉-下载中心 2.python MVS示例 &#xff08;说明&#xff1a;MVS里有很多python示例&#xff0c;可以直接运行&#xff0c;但没有用opencv&#xff09; 下载完MVS后&#xff0c;我们打开路径安装路径 我的&#…

计算机基础·linux系统

Finalshell 用于远程操控vmware中的linux系统 获取虚拟机的IP地址 ifconfig命令&#xff0c;重启系统后IP地址可能会变化&#xff01;问题&#xff1a;vmware子系统没有网络连接 winRservices.msc启动这些服务问题&#xff1a;配置正确但是finalshell连接失败 更新子系统中的ss…

8.结构健康监测选自动化:实时数据 + 智能分析,远超人工

第一次接触结构健康自动化监测系统&#xff0c;感觉成本很高&#xff0c;比人工好在哪里&#xff1f; 人工检测是依靠目测检查或借助于便携式仪器测量得到的信息&#xff0c;但是随着整个行业的发展&#xff0c;传统的人工检测方法已经不能满足检测需求&#xff0c;从人工检测到…

【慕伏白】Android Studio 配置国内镜像源

文章目录配置HTTP代理修改 gradle 镜像地址修改 maven 镜像源重新同步配置HTTP代理 进入File --> Settings --> Appearance & Behavior --> System Settings --> HTTP Proxy 勾选 Auto-detect proxy settings --> Automatic proxy configuration URL &…

Spring Cloud系列—LoadBalance负载均衡

上篇文章&#xff1a; Spring Cloud系列—Eureka服务注册/发现https://blog.csdn.net/sniper_fandc/article/details/149937589?fromshareblogdetail&sharetypeblogdetail&sharerId149937589&sharereferPC&sharesourcesniper_fandc&sharefromfrom_link …

如何使用 pnpm创建Vue 3 项目

✅ 一、什么是 pnpm&#xff1f; pnpm 是一种更快、更高效的 Node 包管理工具&#xff0c;替代 npm 或 yarn&#xff0c;具有&#xff1a; 更快的安装速度更节省磁盘空间&#xff08;包复用&#xff09;严格的依赖管理二、使用 pnpm 创建 Vue 项目的完整流程 ✅ 第一步&#xf…

Vite vs. vue-cli 创建 Vue 3 项目的区别与使用场景

Vite vs. vue-cli 创建 Vue 3 项目的区别与使用场景 Vite 和 vue-cli 都是 Vue 官方推荐的脚手架工具&#xff0c;但它们的架构、构建方式和适用场景有所不同。以下是它们的对比&#xff1a;1. 核心区别对比项Vite (推荐&#x1f525;)vue-cli (传统)构建工具基于 ESM Rollup基…

VC6800智能相机:赋能智能制造,开启AI视觉新纪元

在工业自动化与智能化浪潮奔涌的今天&#xff0c;精准、高效、智能的视觉检测已成为提升生产力和品质的关键核心。VC6800智能相机应运而生&#xff0c;它不仅仅是一部相机&#xff0c;更是一个集强大视觉硬件与前沿AI算法于一身的 “工业智眼”&#xff0c;正深刻改变着各个领域…

(Python)Python爬虫入门教程:从零开始学习网页抓取(爬虫教学)(Python教学)

一、爬虫基础概念 什么是爬虫&#xff1f; 网络爬虫&#xff08;Web Crawler&#xff09;是一种自动获取网页内容的程序&#xff0c;它像蜘蛛一样在互联网上"爬行"&#xff0c;收集和提取数据。 爬虫应用场景&#xff1a; 搜索引擎&#xff08;Google、百度&#…

dify前端源码部署详细教程

这两天突发奇想&#xff0c;能不能dify源码部署我只部署个前端&#xff0c;后端、数据库什么的还是原来docker部署dify的本地部署和遇到的问题。按逻辑来说应该是行得通的&#xff0c;我就亲自操作了下试下。 我这边就以我以前使用docker部署好的1.3.1版本为例。docker安装参考…

Web地图服务规范,WMS服务是什么

Web地图服务规范&#xff0c;WMS服务是什么&#xff1f; WMS&#xff0c;全称 Web Map Service (网络地图服务)&#xff0c;是有OGC(开放地理空间信息联盟)制定的一项标准化协议。他的核心功能是允许客户端&#xff08;比如网页浏览器或者GIS桌面软件&#xff09;通过互联网或者…

北京手机基站数据分享:9.3万点位+双格式,解锁城市通信「基础设施地图」

今天分享的是——​​2023年7月北京市手机基站数据&#xff08;shpcsv双格式&#xff09;​​。92,785个基站点位&#xff08;覆盖全市16区&#xff09;&#xff0c;WGS84坐标系直接能用&#xff0c;shp格式适配GIS软件&#xff0c;csv格式方便Excel/Pandas分析&#xff01;文末…

Druid学习笔记 01、快速了解Druid中SqlParser实现

文章目录前言介绍Druid代码目录介绍模块一&#xff1a;Parser模块二&#xff1a;Druid_SQL_AST在Druid SQL Parser中有哪些AST节点类型?熟悉常用的AST节点组成常用的SQLExpr有哪些&#xff1f;常用的SQLStatemment&#xff1f;SQLTableSourceSQLSelect & SQLSelectQuerySQ…

Rust中生命周期的理解与应用

在学习Rust编程语言时,理解生命周期(Lifetime)是非常关键的,因为它直接影响到代码的安全性和性能。今天我们来深入探讨Rust中的一个常见问题——生命周期的误解和正确应用,结合实际代码实例来说明。 生命周期的基本概念 Rust中的生命周期是用来确保引用(Reference)在其…

智慧感知新体验:英飞凌雷达在智能家居的创新应用

随着智慧家居快速发展&#xff0c;感知技术成为实现高效、便捷生活的关键。雷达作为非接触、高精度的感测方案&#xff0c;正在家居应用中展现出巨大潜力。 本次研讨会将由英飞凌大中华区雷达应用产品经理 Tommy Wan主讲&#xff0c;分享他在智能门铃、门锁与安防摄像头等应用…

AI:新书预告—从机器学习避坑指南(分类/回归/聚类/可解释性)到大语言模型落地手记(RAG/Agent/MCP),一场耗时5+3年的技术沉淀—“代码可跑,经验可抄”—【一个处女座的程序猿】携两本AI

AI&#xff1a;新书预告—从机器学习避坑指南(分类/回归/聚类/可解释性)到大语言模型落地手记(RAG/Agent/MCP)&#xff0c;一场耗时53年的技术沉淀—“代码可跑&#xff0c;经验可抄”—【一个处女座的程序猿】携两本AI实战书终于正式来了&#xff01; 导读&#xff1a;大家好&…