springboot带有进度条的上传功能完整实例

网友投稿 425 2022-12-23


springboot带有进度条的上传功能完整实例

本文实例讲述了springboot带有进度条的上传功能。分享给大家供大家参考,具体如下:

一、说明

最近要做文件上传,在网上找了很久都没有一个全面的示例,特此记录下来分享给大家。

1.文件上传接口可按照springboot默认实现,也可用commons-fileupload组件,本示例使用springboot默认文件上传 2.最后也有commons-fileupload组件接口示例

2.重点在前端js实现(也可以使用ajax上传),参考了网上大量上传文件显示进度条博客以及技术方案,在此做了一个统一的总结,方便后续使用

3.这仅仅是一个示例,大家可根据实际需要改进。

二、前端代码

rel="stylesheet">



style="padding-left: 0; padding-right: 0; margin-bottom: 0px;">

role="progressbar" aria-valuemin="0" aria-valuenow="0"

aria-valuemax="100" style="width: 20%">




效果:

三、对上传代码进行组件化封装

UploadCommon.js

/**

* 上传文件公共组件

*

* @param url 上传地址

* @param processBar 进度条 jquery获取的页面组件

* @param speedLab 显示上传速度Label jquery获取的页面组件

* @param uploadBtn 上传按钮 jquery获取的页面组件

* @param cancelBtn 取消上传按钮 jquery获取的页面组件

* @param callBack 上传完成回调函数 上传完成后的回调函数,可以不传

* @author

* @returns

*/

function UploadCommon(url, processBar, speedLab, uploadBtn, cancelBtn, callBack){

function init() {

// 每次回调监测上传开始时间

var startTime = null

// 已上传文件大小

var oloaded = null

var xhr = new XMLHttpRequest()

function setProgress(w) {

processBar.width(w + '%');

processBar.text(w + '%');

}

function progressMonitor(evt){

if (evt.lengthComputable) {

var completePercent = Math.round(evt.loaded / evt.total * 100)

setProgress(completePercent)

var nowTime = new Date().getTime()

// 计算出上次调用该方法时到现在的时间差,单位为s

var pertime = (nowTime - startTime) / 1000

          // 重新赋值时间,用于下次计算

startTime = new Date().getTime()

// 计算该分段上传的文件大小,单位b

var perload = evt.loaded - oloaded

// 重新赋值已上传文件大小,用以下次计算

oloaded = evt.loaded

// 上传速度计算,单位b/s

var speed = perload / pertime

var bspeed = speed

// 单位名称

var units = 'bit/s'if (speed / 1024 > 1) {

speed = speed / 1024

units = 'Kb/s'

}

if (speed / 1024 > 1) {

speed = speed / 1024

units = 'Mb/s'

}

speed = speed.toFixed(1);

// 剩余时间

var resttime = ((evt.total - evt.loaded) / bspeed).toFixed(1)

speedLab.html(speed + units + ',剩余时间:' + resttime + 's')

}

}

// 上传成功后回调

function uploadComplete(evt) {

uploadBtn.attr('disabled', false)

var status = evt.currentTarget.status

if (status == 401) {

alert('请登录后再上传')

return

}

if (status == 403) {

alert('无权限操作')

return

}

if (status != 200) {

alert('上传异常,错误码' + status)

return

}

var response=JSON.parse(evt.currentTarget.response)

if (response.code!='200') {

alert('上传处理异常' + response.msg)

return

}

console.log('上传成功')

if ( callBack != null && typeof callBack != 'undefined') {

callBack()

}

};

// 上传失败回调

function uploadFailed(evt) {

alert('上传处理失败' + evt.target.responseText)

}

// 终止上传

function cancelUpload() {

xhr.abort()

}

// 上传取消后回调

function uploadCanceled(evt) {

alert('文件上传已终止:' + evt.target.responseText)

}

// 添加取消上传事件

cancelBtn.click(function() {

uploadBtn.attr('disabled', false)

cancelUpload();

})

this.uploadFile = function(formData) {

// 上传按钮禁用

uploadBtn.attr('disabled', true);

setProgress(0)

// true为异步处理

xhr.open('post', url, true)

// 上传开始执行方法

xhr.onloadstart = function() {

console.log('开始上传')

// 设置上传开始时间

startTime = new Date().getTime()

// 已上传的文件大小为0

oloaded = 0

}

xhr.upload.addEventListener('progress', progressMonitor, false)

xhr.addEventListener("load", uploadComplete, false)

xhr.addEventListener("error", uploadFailed, false)

xhr.addEventListener("abort", uploadCanceled, false)

xhr.send(formData);

}

this.setProgressValue=function(w){

processBar.width(w + '%')

processBar.text(w + '%')

}

}

return new init()

}

调用

$(document).ready(function() {

var addVersionBtn=$('#addVersionBtn') //

var cancelUploadBtn=$('#cancelUploadBtn') //

var fileInput=$("#filewareFile") //

var processBar = $("#progressBar"); //div

var fileNameLab=$("label[name=upfileName]") //

var fileSizeLab=$("label[name=upfileSize]") //...

var fileTypeLab=$("label[name=upfileType]") //...

var speedLab=$("#showSpeed") //

var url='/api/file'

//获取文件上传实例

var upload=UploadCommon(url,processBar,speedLab,addVersionBtn,cancelUploadBtn,initPageInfo)

// 文件选择框变更事件

fileInput.change(function() {

var fileObj = fileInput.get(0).files[0]; // js获取文件对象

if (fileObj) {

var fileSize = getSize(fileObj.size);

fileNameLab.text('文件名:' + fileObj.name);

fileSizeLab.text('文件大小:' + fileSize);

fileTypeLab.text('文件类型:' + fileObj.type);

addVersionBtn.attr('disabled', false);

}

});

// 点击上传固件事件

addVersionBtn.click(function(){

var versionInfo=$('#version').val()

var file = fileInput.get(0).files[0]

var strategyInfo=$('#versionType').val()

if(file==null){

alert("固件文件不能为空")

return

}

if(versionInfo==''){

alert("版本号不能为空")

return

}

if(strategyInfo==''){

alert("升级策略不能为空")

return

}

// 创建提交数据

var formData = new FormData();

formData.append('firmFile', fileInput.get(0).files[0]);

formData.append('version', versionInfo);

formData.append('strategy', strategyInfo);

// 上传文件

upload.uploadFile(formData)

})

});

四,服务端接口

1.springboot默认实现

pom.xml

4.0.0

com.demo

demo

0.0.1-SNAPSHOT

org.springframework.boot

spring-boot-starter-parent

1.5.10.RELEASE

UTF-8

UTF-8

1.8

org.springframework.boot

spring-boot-devtools

true

org.springframework.boot

spring-boot-starter-web

org.springframework.boot

spring-boot-starter-thymeleaf

net.sourceforge.nekohtml

nekohtml

org.springframework.boot

spring-boot-starter-test

test

io.springfox

springfox-swagger2

2.7.0

io.springfox

springfox-swagger-ui

2.7.0

org.springframework.boot

spring-boot-maven-plugin

application.yml

server:

port: 8080

tomcat:

uri-encoding: UTF-8

application:

name: demo

thymeleaf:

encoding: UTF-8

cache: true

mode: LEGACYHTML5

devtools:

restart:

enabled: true

http:

multipart:

maxFileSize: 500Mb

maxRequestSize: 500Mb

location: D:/tmp

debug: false

接口:

@PostMapping("/upload")

public String uploadFile(@RequestParam("file") MultipartFile file) {

if (file == null || file.isEmpty()) {

return "file is empty";

}

// 获取文件名

String fileName = file.getOriginalFilename();

// 文件存储路径

String filePath = "D:/data/" + UUID.randomUUID().toString().replaceAll("-", "") + "_" + fileName;

logger.info("save file to:" + filePath);

File dest = new File(filePath);

if (!dest.getParentFile().exists()) {

dest.getParentFile().mkdirs();

}

try {

file.transferTo(dest);

return "success";

} catch (Exception e) {

e.printStackTrace();

}

return "fail";

}

启动类

import org.springframework.boot.SpringApplication;

import org.springframework.boot.autoconfigure.SpringBootApplication;

import org.springframework.boot.builder.SpringApplicationBuilder;

import org.springframework.boot.web.support.SpringBootServletInitializer;

import org.springframework.transaction.annotation.EnableTransactionManagement;

@SpringBootApplication

@EnableTransactionManagement

public class Application extends SpringBootServletInitializer {

@Override

protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {

return application.sources(Application.class);

}

public static void main(String[] args) {

SpringApplication.run(Application.class, args);

}

}

2.使用commons-fileupload上传组件

application.yml

server:

port: 8080

tomcat:

uri-encoding : UTF-8

spring:

application:

name: svc-demo

thymeleaf:

encoding: UTF-8

cache: false

mode: LEGACYHTML5

debug: false

pom .xml

org.springframework.boot

spring-boot-starter-parent

1.5.10.RELEASE

UTF-8

UTF-8

1.8

org.springframework.boot

spring-boot-devtools

true

org.springframework.boot

spring-boot-starter-web

org.springframework.boot

spring-boot-starter-thymeleaf

org.springframework.boot

spring-boot-starter-test

test

commons-io

commons-io

2.4

commons-fileupload

commons-fileupload

1.3.1

net.sourceforge.nekohtml

nekohtml

org.springframework.boot

spring-boot-maven-plugin

进程类

public class Progress{

private long bytesRead; //已读取文件的比特数

private long contentLength;//文件总比特数

private long items; //正读的第几个文件

public long getBytesRead(){

return bytesRead;

}

public void setBytesRead(long bytesRead){

this.bytesRead = bytesRead;

}

public long getContentLength() {

return contentLength;

}

public void setContentLength(long contentLength) {

this.contentLength = contentLength;

}

public long getItems() {

return items;

}

public void setItems(long items)\{

this.items = items;

}

}

监听类

@Component

public class FileUploadProgressListener implements ProgressListener{

private HttpSession session;

public void setSession(HttpSession session){

this.session=session;

Progress status = new Progress();//保存上传状态

session.setAttribute("status", status);

}

@Override

public void update(long bytesRead, long contentLength, int items) {

Progress status = (Progress) session.getAttribute("status");

status.setBytesRead(bytesRead);

status.setContentLength(contentLength);

status.setItems(items);

}

}

文件上传处理类

public class CustomMultipartResolver extends CommonsMultipartResolver{

// 注入第二步写的FileUploadProgressListener

@Autowired

private FileUploadProgressListener progressListener;

public void setFileUploadProgressListener(FileUploadProgressListener progressListener){

this.progressListener = progressListener;

}

@Override

public MultipartParsingResult parseRequest(HttpServletRequest request) throws MultipartException{

String encoding = determineEncoding(request);

FileUpload fileUpload = prepareFileUpload(encoding);

     //fileUpload.setFileSizeMax(1024 * 1024 * 500);// 单个文件最大500M

//fileUpload.setSizeMax(1024 * 1024 * 500);// 一次提交总文件最大500M

progressListener.setSession(request.getSession());// 问文件上传进度监听器设置sessihttp://on用于存储上传进度

fileUpload.setProgressListener(progressListener);// 将文件上传进度监听器加入到 fileUpload 中

try{

List fileItems = ((ServletFileUpload) fileUpload).parseRequest(request);

return parseFileItems(fileItems, encoding);

} catch (FileUploadBase.SizeLimitExceededException ex) {

throw new MaxUploadSizeExceededException(fileUpload.getSizeMax(), ex);

} catch (FileUploadException ex){

throw new MultipartException("Could not parse multipart servlet request", ex);

}

}

}

控制器

@RestController

public class FileController{

@PostMapping("/upload")

public String uploadFile(@RequestParam("file") MultipartFile file) {

if (file.isEmpty()) {

return "文件为空";

     }

// 获取文件名

String fileName = file.getOriginalFilename();// 文件上传后的路径

// 文件上传后的路径

String filePath = null;

try{

filePath = new File("").getCanonicalPath() + "/tmp/uploadFile/";

} catch (IOException e){

e.printStackTrace();

}

http:// //存储路径

String tagFilePath = filePath + CommonUtil.getCurrentTime() + fileName;

File dest = new File(tagFilePath);

// 检测是否存在目录

if (!dest.getParentFile().exists()){

dest.getParentFile().mkdirs();

}

try{

file.transferTo(dest);

} catch (IllegalStateException e){

e.printStackTrace();

} catch (IOException e){

e.printStackTrace();

}

return fileName + "上传失败";

}

}

启动类

//注意取消自动Multipart配置,否则可能在上传接口中拿不到file的值

@EnableAutoConfiguration(exclude = { MultipartAutoConfiguration.class })

@SpringBootApplication

public class Application extends SpringBootServletInitializer{

//注入自定义的文件上传处理类

@Bean(name = "multipartResolver")

public MultipartResolver multipartResolver() {

CustomMultipartResolver customMultipartResolver = new CustomMultipartResolver();

return customMultipartResolver;

}

@Override

protected SpringApplicationBuilder configure(SpringApplicationBuilder application){

return application.sources(Application.class);

}

public static void main(String[] args) {

SpringApplication.run(Application.class, args);

}

更多关于java相关内容感兴趣的读者可查看本站专题:《Spring框架入门与进阶教程》、《Java数据结构与算法教程》、《Java操作DOM节点技巧总结》、《Java文件与目录操作技巧汇总》和《Java缓存操作技巧汇总》

希望本文所述对大家java程序设计有所帮助。


版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:spring boot 配置HTTPS代码实例
下一篇:java操作xml的方法汇总及解析
相关文章

 发表评论

暂时没有评论,来抢沙发吧~