当前位置: 首页 > news >正文

美的公司网站建设的目的做个网站要钱吗

美的公司网站建设的目的,做个网站要钱吗,嘉兴型网站系统总部,任务网站建设文章目录 什么是断点续传后端实现JAVA实现大文件分片上传断点续传 什么是断点续传 用户上传大文件,网络差点的需要历时数小时#xff0c;万一线路中断#xff0c;不具备断点续传的服务器就只能从头重传#xff0c;而断点续传就是#xff0c;允许用户从上传断线的地方继续传… 文章目录 什么是断点续传后端实现JAVA实现大文件分片上传断点续传 什么是断点续传 用户上传大文件,网络差点的需要历时数小时万一线路中断不具备断点续传的服务器就只能从头重传而断点续传就是允许用户从上传断线的地方继续传送这样大大减少了用户的烦恼。 解决上传大文件服务器内存不够的问题 解决如果因为其他因素导致上传终止的问题,并且刷新浏览器后仍然能够续传重启浏览器关闭浏览器后再打开仍然能够继续上传重启电脑后仍然能够上传 检测上传过程中因网络波动导致文件出现了内容丢失那么需要自动检测并且从新上传 解决方案 前端 需要进行分割上传的文件 需要对上传的分片文件进行指定文件序号 需要监控上传进度,控制进度条 上传完毕后需要发送合并请求 Blob 对象,操作文件 后端 上传分片的接口 合并分片的接口 获取分片的接口 其他工具方法,用于辅助 前端端需要注意的就是: 文件的切割,和进度条 后端需要注意的就是: 分片存储的地方和如何进行合并分片 后端实现 package com.controller.commontools.fIleupload;import com.alibaba.fastjson.JSON; import com.application.Result; import com.container.ArrayByteUtil; import com.encryption.hash.HashUtil; import com.file.FileUtils; import com.file.FileWebUpload; import com.file.ReadWriteFileUtils; import com.function.impl.ExecutorUtils; import com.path.ResourceFileUtil; import com.string.PatternCommon; import org.springframework.web.bind.annotation.*;import javax.servlet.http.HttpServletRequest; import java.io.File; import java.io.FileNotFoundException; import java.io.IOException; import java.io.RandomAccessFile; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.concurrent.Future; import java.util.concurrent.atomic.AtomicBoolean; import java.util.stream.Collectors;RestController RequestMapping(/fileslice) public class FIleSliceUploadController {private final String identification-slice-;private final String uploadslicediruploadsFile.separatorsliceFile.separator;//分片目录private final String uploaddiruploadsFile.separatorrealFile.separator;//实际文件目录//获取分片GetMapping(/testing/{fileName}/{fileSlicSize}/{fileSize})public Result testing(PathVariable String fileName,PathVariable long fileSlicSize,PathVariable long fileSize ) throws Exception {String dir fileNameMd5Dir(fileName,fileSize);String absoluteFilePathAndCreate ResourceFileUtil.getAbsoluteFilePathAndCreate(uploadslicedir)File.separatordir;File file new File(absoluteFilePathAndCreate);if (file.exists()) {ListString filesAll FileUtils.getFilesAll(file.getAbsolutePath());if (filesAll.size()2){//分片缺少 删除全部分片文件 ,从新上传FileUtils.delFilesAllReview(absoluteFilePathAndCreate,true);return Result.Error();}//从小到大文件进行按照序号排序,和判断分片是否损坏ListString collect fileSliceIsbadAndSort(file, fileSlicSize);//获取最后一个分片String fileSliceName collect.get(collect.size() - 1);fileSliceName new File(fileSliceName).getName();int code fileId(fileSliceName);//服务器的分片总大小必须小于或者等于文件的总大小if ((code*fileSlicSize)fileSize) {Result result new Result();String finalFileSliceName fileSliceName;String str PatternCommon.renderString({\code\:\$[code]\,\fileSliceName\:\${fileSliceName}\}, new HashMapString, String() {{put(code, String.valueOf(code));put(fileSliceName, finalFileSliceName);}});result.setData(JSON.parse(str));return result;}else {//分片异常 ,删除全部分片文件,从新上传FileUtils.delFilesAllReview(absoluteFilePathAndCreate,true);return Result.Error();}}//不存在return Result.Error();}PostMapping(value /uploads)public Result uploads(HttpServletRequest request) {String fileSliceName request.getParameter(fileSliceName);long fileSize Long.parseLong(request.getParameter(fileSize)); //文件大小String dir fileSliceMd5Dir(fileSliceName,fileSize);String absoluteFilePathAndCreate ResourceFileUtil.getAbsoluteFilePathAndCreate(uploadslicedirdir);FileWebUpload.fileUpload(absoluteFilePathAndCreate,fileSliceName,request);int i fileId(fileSliceName); //返回上传成功的文件id,用于前端计算进度Result resultnew Result();result.setData(i);return result;}// 合并分片GetMapping(value /merge-file-slice/{fileSlicNamee}/{fileSlicSize}/{fileSize})public Result mergeFileSlice(PathVariable String fileSlicNamee,PathVariable long fileSlicSize,PathVariable long fileSize ) throws Exception {int l (int) Math.ceil((double) fileSize / fileSlicSize); //有多少个分片String dir fileSliceMd5Dir(fileSlicNamee,fileSize); //分片所在的目录String absoluteFilePathAndCreate ResourceFileUtil.getAbsoluteFilePathAndCreate(uploadslicedirdir);File filenew File(absoluteFilePathAndCreate);if (file.exists()){ListString filesAll FileUtils.getFilesAll(file.getAbsolutePath());//阻塞循环判断是否还在上传 ,解决前端进行ajax异步上传的问题int beforeSizefilesAll.size();while (true){Thread.sleep(1000);//之前分片数量和现在分片数据只差,如果大于1那么就在上传,那么继续filesAll FileUtils.getFilesAll(file.getAbsolutePath());if (filesAll.size()-beforeSize1){beforeSizefilesAll.size();//继续检测continue;}//如果是之前分片和现在的分片相等的,那么在阻塞2秒后检测是否发生变化,如果还没变化那么上传全部完成,可以进行合并了//当然这不是绝对的,只能解决网络短暂的波动,因为有可能发生断网很长时间,网络恢复后文件恢复上传, 这个问题是避免不了的,所以我们在下面的代码进行数量的效验// 因为我们不可能一直等着他网好,所以如果1~3秒内没有上传新的内容,那么我们默认判定上传完毕if (beforeSizefilesAll.size()){Thread.sleep(2000);filesAll FileUtils.getFilesAll(file.getAbsolutePath());if (beforeSizefilesAll.size()){break;}}}//分片数量效验if (filesAll.size()!l){//分片缺少 ,删除全部分片文件,从新上传FileUtils.delFilesAllReview(absoluteFilePathAndCreate,true);return Result.Error();}//获取实际的文件名称,组装路径String realFileName realFileName(fileSlicNamee);String realFileNamePath ResourceFileUtil.getAbsoluteFilePathAndCreate(uploaddir realFileName);//从小到大文件进行按照序号排序 ,和检查分片文件是否有问题ListString collect fileSliceIsbadAndSort(file, fileSlicSize);int fileSliceSize collect.size();ListFuture? futures new ArrayList();// 将文件按照序号进行合并 ,算出Runtime.getRuntime().availableProcessors()个线程 ,每个线程需要读取多少分片, 和每个线程需要读取多少字节大小//有人会说一个分片一个线程不行吗,你想想如果上千或者上万分片的话,你创建这么多的线程需要多少时间,以及线程切换上下文切换和销毁需要多少时间? // 就算使用线程池,也顶不住啊,你内存又有多大,能存下多少队列?,并发高的话直接怼爆int availableProcessors Runtime.getRuntime().availableProcessors();//每个线程读取多少文件int readFileSize (int)Math.ceil((double)fileSliceSize / availableProcessors);//每个线程需要读取的文件大小long readSliceSize readFileSize * fileSlicSize;for (int i 0; i availableProcessors; i) {int finalI i;Future? future ExecutorUtils.createFuture(FIleSliceUploadController,()-{//每个线程需要读取多少字节byte[] bytesnew byte[(int) readSliceSize];int index0;for (int i1 finalI *readFileSize,i2 readFileSize*(finalI1)fileSliceSize?fileSliceSize:readFileSize*(finalI1); i1 i2; i1) {try ( RandomAccessFile r new RandomAccessFile(collect.get(i1), r);){r.read(bytes, (int)(index*fileSlicSize),(int)fileSlicSize);} catch (IOException e) {e.printStackTrace();}index;}if(finalIavailableProcessors-1){//需要调整数组bytes ArrayByteUtil.getActualBytes(bytes);}try ( RandomAccessFile w new RandomAccessFile(realFileNamePath, rw);){//当前文件写入的位置w.seek(finalI*readSliceSize);w.write(bytes);} catch (IOException e) {e.printStackTrace();}});futures.add(future);}//阻塞到全部线程执行完毕后ExecutorUtils.waitComplete(futures);//删除全部分片文件FileUtils.delFilesAllReview(absoluteFilePathAndCreate,true);}else {//没有这个分片相关的的目录return Result.Error();}return Result.Ok();}//获取分片文件的目录private String fileSliceMd5Dir(String fileSliceName,long fileSize){int i fileSliceName.indexOf(identification) ;String substring fileSliceName.substring(0, i);String dir HashUtil.md5(substringfileSize);return dir;}//通过文件名称获取文件目录private String fileNameMd5Dir(String fileName,long fileSize){return HashUtil.md5(fileNamefileSize);}//获取分片的实际文件名private String realFileName(String fileSliceName){int i fileSliceName.indexOf(identification) ;String substring fileSliceName.substring(0, i);return substring;}//获取文件序号private int fileId(String fileSliceName){int i fileSliceName.indexOf(identification)identification.length() ;String fileId fileSliceName.substring(i);return Integer.parseInt(fileId);}//判断是否损坏private ListString fileSliceIsbadAndSort(File file,long fileSlicSize) throws Exception {String absolutePath file.getAbsolutePath();ListString filesAll FileUtils.getFilesAll(absolutePath);if (filesAll.size()1){//分片缺少,删除全部分片文件 ,从新上传FileUtils.delFilesAllReview(absolutePath,true);throw new Exception(分片损坏);}//从小到大文件进行按照序号排序ListString collect filesAll.stream().sorted((a, b) - fileId(a) - fileId(b)).collect(Collectors.toList());//判断文件是否损坏,将文件排序后,进行前后序号相差大于1那么就代表少分片了for (int i 0; i collect.size()-1; i) {//检测分片的连续度if (fileId(collect.get(i)) - fileId(collect.get(i1))!-1) {//分片损坏 删除全部分片文件 ,从新上传FileUtils.delFilesAllReview(absolutePath,true);throw new Exception(分片损坏);}//检测分片的完整度if (new File(collect.get(i)).length()!fileSlicSize) {//分片损坏 删除全部分片文件 ,从新上传FileUtils.delFilesAllReview(absolutePath,true);throw new Exception(分片损坏);}}return collect;} }JAVA实现大文件分片上传断点续传 import org.springframework.web.multipart.MultipartFile; import java.util.concurrent.CompletableFuture; import org.apache.commons.lang3.StringUtils; import lombok.extern.slf4j.Slf4j; import java.text.DecimalFormat; import java.io.*;Slf4j public class FileSliceUpload {// 文件上传地址 private final String uploadPath /data/upload/;/** * description: 文件分片上传 * date: 2024/3/12 15:25 * param fileSliceDTO * return boolean */public boolean fileUpload(FileSliceDTO fileSliceDTO) {// 当前分片序号Integer chunkNumber fileSliceDTO.getChunkNumber();// 当前分片大小 Long currentChunkSize fileSliceDTO.getCurrentChunkSize();// 总分片数 Integer totalChunks fileSliceDTO.getTotalChunks();// 原文件md5 String fileMd5 fileSliceDTO.getFileMd5();// 文件名称 String fileName fileSliceDTO.getFileName();// 用户账号 String userAccount fileSliceDTO.getUserAccount();// 文件总大小 Long totalSize fileSliceDTO.getTotalSize();// 当前分片文件流 MultipartFile mFile fileSliceDTO.getFile();log.info(接收到文件{}总大小{} 总分片{} 当前分片{}, fileName, this.readableFileSize(totalSize), totalChunks, chunkNumber);String path uploadPath fileMd5 _ userAccount File.separator;File dirfile new File(path);if (!dirfile.exists()) {dirfile.mkdirs();}String currentChunkFileName path fileMd5 _ chunkNumber .tmp;File file new File(currentChunkFileName);boolean uploadFlag this.fileUpload(mFile, file);if (uploadFlag) {if (chunkNumber totalChunks) {return true;} else {// 如果是最后一个分片上传成功后就进行文件合并String mergeFileName null;try {mergeFileName this.fileMerge(fileMd5, totalChunks, fileName, totalSize, userAccount);} catch (IOException e) {log.info(文件合并发生异常{}, {}, fileName, e.toString());}if (StringUtils.isBlank(mergeFileName)) {// 合并失败后异步删除文件夹CompletableFuture.runAsync(() - { delFile(new File(path)); });return false;}log.info(文件合并成功{}, 总大小: {}, fileName, this.readableFileSize(totalSize)); // 合并成功后异步删除文件夹CompletableFuture.runAsync(() - {delFile(new File(path)); });return true;}}return false;}/** * description: 文件上传私有方法* date: 2024/3/12 15:25 * param multipartFile 分片文件* param file 目标文件* return boolean */private boolean fileUpload(MultipartFile multipartFile, File file) {boolean flag false;try {if (!file.exists()) {file.createNewFile();multipartFile.transferTo(file);} else {log.info(当前分片文件已存在:{}, file.getName());}flag true;} catch (Exception e) {log.info(文件上传失败{}, {}, multipartFile.getOriginalFilename(), e.toString());}return flag;} /** * description: 合并文件 * date: 2024/3/12 15:21 * param fileMd5 * param chunks * param fileName * param totalSize * param userAccount * return java.lang.String */private String fileMerge(String fileMd5, Integer chunks, String fileName, long totalSize, String userAccount) throws IOException {String fileType this.getFileSuffix(fileName);String mergePath uploadPath UUIDUtil.uuid32() . fileType;FileOutputStream fileOutputStream new FileOutputStream(mergePath);String mergeFileName null;long fileSize 0 L;try {byte[] buf new byte[1024 * 4];for (int i 1; i chunks; i) {String chunkFile i .tmp;File file new File(uploadPath fileMd5 _ userAccount File.separator fileMd5 _ chunkFile);fileSize fileSize file.length();InputStream inputStream new FileInputStream(file);int len;while ((len inputStream.read(buf)) ! -1) {fileOutputStream.write(buf, 0, len);}inputStream.close();}mergeFileName mergePath;} catch (Exception e) {log.info(合并文件失败{},{}, fileName, e.toString());} finally {fileOutputStream.close();}if (fileSize ! totalSize) {log.info(文件总大小不一致:{}, fileName);return null;}return mergeFileName;} /*** description: 删除文件/文件夹 * date: 2024/3/12 15:19* param file * return boolean*/private boolean delFile(File file) {if (file null || !file.exists()) {return true;}if (!file.isDirectory()) {file.delete();return true;} else {File[] files file.listFiles();for (File f: files) {if (f.isDirectory()) {delFile(f);} else {f.delete();}}file.delete();return true;}} /** * description: 文件大小可读化转换* date: 2024/3/12 15:18 * param size* return java.lang.String */private String readableFileSize(long size) {if (size 0) {return 0;}final String[] units new String[] {B, KB, MB, GB, TB};int digitGroups (int)(Math.log10(size) / Math.log10(1024));return new DecimalFormat(#,###.##).format(size / Math.pow(1024, digitGroups)) units[digitGroups];} /** * description: 获取文件的拓展名 支持形式 abc.jpg or D:/data/abc.txt; * date: 2024/3/12 15:16 * param fileName * return java.lang.String */private String getFileSuffix(String fileName) {String newFileName fileName;      if(fileName.contains(/) || fileName.contains(\\)){         String replaceFileName fileName.replaceAll(\\\\, /);         int lastIndexOf replaceFileName.lastIndexOf(/);         if(lastIndexOf 0) {           newFileName replaceFileName.substring(lastIndexOf);         }      }     int lastIndexOf newFileName.lastIndexOf(.);String fileSuffix lastIndexOf 0 ? newFileName.substring(lastIndexOf 1).toLowerCase() : ;fileSuffix newFileName.toLowerCase().endsWith(.tar.gz) ? tar.gz : fileSuffix;return fileSuffix;} }
http://www.w-s-a.com/news/917235/

相关文章:

  • 和县建设局网站孟州网站建设
  • 网站与规划设计思路竞价培训课程
  • 网站建设设计视频专业设计企业网站
  • 湖南省建设工程网站cerntos wordpress
  • 主机屋的免费空间怎么上传网站广告公司的经营范围有哪些
  • 门户网站建设公司案例门户建设是什么意思
  • 深圳seo专家东莞网站关键词优化排名
  • 套用别人产品图片做网站如何在阿里云自主建网站
  • 网站开发需要用哪些东西wordpress页面参数
  • 大连模板网站制作哪家好wordpress 安装不上
  • 宝塔搭建网站首页图片点击率如何提高
  • 长沙找人做网站wordpress如何安装模板
  • 比较好的国外网站建设公司wordpress短代码可视化
  • 做新的网站网站个性化
  • 吉安做网站的英文网站 字体大小
  • 外贸网站服务商wordpress主题handsome
  • 云主机多个网站如何优化网站图片
  • 松江移动网站建设成都app开发制作公司
  • 锦州做网站的公司百度seo搜索营销新视角
  • 做画册找什么网站海南建设工程股份有限公司网站
  • 网站机房建设有助于网站备案
  • 北辰苏州网站建设抖音代运营投诉平台
  • 安徽住房与城乡建设部网站如何新建站点
  • 企业网站开发的感想网站开发公司所需投入资源
  • 如何拿网站后台账号wordpress 电影下载站源码
  • 公司网站建设方案书安卓应用市场免费下载安装
  • phpmysql网站设计建设好一个网站需要
  • 自己做的网站能被别人看到吗idea怎么做网页
  • 燕莎网站建设互联网排名前十的公司2021
  • 微软云怎么做网站微商城和小程序区别