带有进度条的文件上传的小实例

1、文件上传的servlet在工程的web.xml文件中的配置
<servlet>
<servlet-name>ProgressUploadServlet</servlet-name>
<servlet-class>com.servlet.ProgressUploadServlet</servlet-class>
</servlet>

<servlet-mapping>
<servlet-name>ProgressUploadServlet</servlet-name>
<url-pattern>/servlet/ProgressUploadServlet</url-pattern>
</servlet-mapping>

2、文件上传的jsp文件内容如下:
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">

<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
<style type="text/css">
body,td,div {font-size: 12px;}
#progressBar {width: 400px;height: 12px;background: #FFFFFF;border: 1px
solid #000000;padding: 1px}
#progressBarItem {height: 100%;background: #FF0000;}
</style>

<script type="text/javascript">
var _finished = true; //是否上传结束标识符
function $(obj){
return document.getElementById(obj); //返回指定id的HTML元素
}

function showStatus(){
_finished = false; //显示进度条
$('status').style.display = 'block'; //将隐藏的进度条显示
$('progressBarItem').style.width='1%'; //设置进度条初始值为1%
$('btnSubmit').disabled = true; //把提交按钮置灰 防止重复提交

setTimeout("requestStatus()",1000); //1秒后执行requestStatus()方法,更新上传进度
}

function requestStatus(){ //向服务器请求上传进度信息
if(_finished) return; //如果已经结束,则返回
var req = createRequest(); //获取Ajax请求
req.open("GET","servlet/ProgressUploadServlet"); //设置请求路径
req.onreadystatechange=function(){callback(req)} //请求完毕就执行callback(req)
req.send(null); //发送请求
setTimeout("requestStatus()",1000); //1秒后执行requestStatus()方法,更新上传进度
}

function createRequest(){ //返回Ajax请求对象
if(window.XMLHttpRequest){ //Netscape浏览器
return new XMLHttpRequest();
}else{ //IE浏览器
try{
return new ActiveXObject("Msxml2.XMLHTTP");
}catch(e){
return new ActiveXObject("Microsoft.XMLHTTP");
}

}
return null;
}

function callback(req){ //刷新进度条
if(req.readyState == 4){ //请求结束后
if(req.status != 200){ //如果发生错误,则显示错误信息
debug("发生错误。req.status: "+req.status + "");
return;
}
debug("status.jsp 返回值:"+ req.responseText); //显示debug信息
var ss = req.responseText.split("||"); //处理进度条信息。格式格式化:百分比||已完成数(M)||文件总长度(M)||传输速率(K)||已用时间(s)||
//估计总时间(s)||估计剩余时间(s)||正在上传第几个文件
$('progressBarItem').style.width='' + ss[0] + '%';
$('statusInfo').innerHTML = '已完成百分比: '+ ss[0]+'%<br/>已完成数(M):'+ss[1]+'<br/>文件总长度(M): '+ ss[2]+
'<br/>传输速率(K): '+ss[3]+'<br/>已用时间(s): '+ss[4]+'<br/>估计总时间(s): '+ss[5]+'<br/>估计剩余时间(s): '+
ss[6]+'<br/>正在上传第几个文件: '+ ss[7];

if(ss[1] == ss[2]){
_finished = true;
$('statusInfo').innerHTML += "<br/><br/><br/>上传成功。";
$('btnSubmit').disabled = false;
}
}
}

function debug(){
var div = document.createElement("DIV"); //显示提示信息
//div.innerHTML = "[debug]: "+ obj;
document.body.appendChild(div);
}
</script>
</head>
<body>
<iframe name=upload_iframe width=0 height=0></iframe>
<form action="servlet/ProgressUploadServlet" method="post" enctype="multipart/form-data"
target="upload_iframe" οnsubmit="showStatus();">
<input type="file" name="file" style="width: 350px; "><br/>
<input type="submit" value="UPLOAD" name="btnSubmit" id="btnSubmit">
</form>
<br/><br/>
<div id="status" style="display:none;">
上传进度条:
<div id="progressBar">
<div id="progressBarItem"></div>
</div><br/><br/>
<div id="statusInfo"></div>
</div>


</body>
</html>


3、处理文件上传的servlet类的内容如下:
package com.servlet;


import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.util.Iterator;
import java.util.List;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;

import com.beans.UploadStatus;
import com.listener.UploadListener;

public class ProgressUploadServlet extends HttpServlet {

/**
*
*/
private static final long serialVersionUID = 1L;

public void doPost(HttpServletRequest request,HttpServletResponse response)
throws ServletException,IOException{

UploadStatus status = new UploadStatus(); //上传状态
UploadListener listener = new UploadListener(status); //监听器
request.getSession(true).setAttribute("uploadStatus", status); //把状态放到Session里

ServletFileUpload upload = new ServletFileUpload(new DiskFileItemFactory()); //解析
upload.setProgressListener(listener); //设置上传listener

try {
List itemList = upload.parseRequest(request); //提交所有的参数
for (Iterator it=itemList.iterator();it.hasNext();) { //遍历所有的参数
FileItem item = (FileItem)it.next();

if (item.isFormField()) { //如果是表单数据
System.out.println("FormField: "+item.getFieldName()+" = "+item.getString());

}else { //否则就是上传文件
System.out.println("File: "+item.getName());
//统一Linux 与 windows 分路径分隔符
// String fileName = item.getName().replace("/", "\\");
// fileName = fileName.substring(fileName.lastIndexOf("\\"));
String fileName = item.getName();

File saved = new File("G:\\upload_test",fileName); //创建文件对象
saved.getParentFile().mkdirs(); //保证路径存在

InputStream ins = item.getInputStream(); //提交的文件内容
OutputStream ous = new FileOutputStream(saved); //输出流

byte[] tmp = new byte[1024]; //缓存
int len = -1; //缓存的实际长度
while ((len = ins.read(tmp))!=-1) {
ous.write(tmp,0,len); //写文件

}
ous.close();
ins.close();
response.getWriter().println("已保存文件: "+ saved);
}

}

} catch (FileUploadException e) {
response.getWriter().println("上传文件发生错误: "+ e.getMessage());
}

}

public void doGet(HttpServletRequest request,HttpServletResponse response)
throws ServletException,IOException{
response.setHeader("Cache-Control", "no-store"); //禁止浏览器缓存
response.setHeader("Pragrma", "no-cache"); //禁止浏览器缓存
response.setDateHeader("Expires", 0); //禁止浏览器缓存
response.setCharacterEncoding("UTF-8");

UploadStatus status = (UploadStatus) request.getSession(true)
.getAttribute("uploadStatus"); //从session中读取上传信息
if (status == null) {
response.getWriter().println("没有上传信息"); return; //没有上传信息,返回
}

long startTime = status.getStartTime(); //上传开始时间
long currentTime = System.currentTimeMillis(); //现在时间
long time = (currentTime - startTime) / 1000 + 1; //已传输的时间 单位: s

double velocity = ((double)status.getBytesRead()) / (double)time; //传输速度 单位: byte/s
double totalTime = status.getContentLength() / velocity; //估计总时间 单位: s
double timeLeft = totalTime - time; //估计剩余时间 单位: s
int percent = (int)(100 * (double)status.getBytesRead() / (double)
status.getContentLength()); //已完成的百分比
double length = ((double)status.getBytesRead())/1024/1024; //已完成数 单位: M
double totalLength = ((double)status.getContentLength())/1024/1024; //总长度 单位: M

//格式化:百分比||已完成数(M)||文件总长度(M)||传输速率(K)||已用时间(s)||
//估计总时间(s)||估计剩余时间(s)||正在上传第几个文件
String value = percent + "||"+ length+"||"+totalLength+"||"+velocity+"||"+ time +
"||"+totalTime +"||"+timeLeft+"||"+status.getItems();
response.getWriter().println(value); //输出给浏览器进度条
}

}


4、用于保存文件上传状态的实体类:
package com.beans;

public class UploadStatus {

private long bytesRead; //已上传的字节数,单位:字节
private long contentLength; //所有文件的总长度,单位:字节
private int items; //正在上传的第几个文件
private long startTime = System.currentTimeMillis(); //开始上传时间,用于计算上传速率、估算上传时间等
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 int getItems() {
return items;
}
public void setItems(int items) {
this.items = items;
}
public long getStartTime() {
return startTime;
}
public void setStartTime(long startTime) {
this.startTime = startTime;
}


}


5、文件上传监听类
package com.listener;

import org.apache.commons.fileupload.ProgressListener;

import com.beans.UploadStatus;

public class UploadListener implements ProgressListener{

private UploadStatus status; //记录上传上传信息的Java Bean

public UploadListener(UploadStatus status){
this.status = status;
}

public void update(long bytesRead, long contentLength, int items) {
status.setBytesRead(bytesRead); //已读取的字节长度
status.setContentLength(contentLength); //文件总长度
status.setItems(items); //正在保存第几个文件

}


}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值