JAVA开发web项目 代码的顺序是按照代码执行的顺序写的,以下写的是没有传递id情况下,即是添加文件情况
jsp页面用uploadify插件实现文件上传
//触发上传插件的html页面代码
<span class="chooseNodeSmall" οnclick="fileUpload('')" style="margin-left:10px">文件上传</span>
<!-- 上传开始 上传弹出框 -->
<div id="fileUpload" style=" display: none; position: absolute; left: 20%; top: 30%;width:450px;height:170px;overflow:hidden;border:3px solid #98999D;padding:12px;border-radius:10px;z-index:10;background-color:white">
<br>
<div style="height:130px">
<input id="uploadify" type="file" name="uploadify"/>
<input type="hidden" name="id" id="updateDocId"/>
<span οnclick="closeFileUploadWindow()" style="position:absolute;left:420px;top:10px" class="uploadType">关闭</span>
</div>
<div style="height:30px" >
<a href="javascript:$('#uploadify').uploadify('upload','*')" class="uploadType">开始上传</a>
<a href="javascript:$('#uploadify').uploadify('cancel')" class="uploadType">取消上传</a>
</div>
</div>
<div id="mask" style="display:none"></div>//用于显示弹出框下层的阴影
css代码
<style type="text/css">
.chooseNodeSmall{
cursor:pointer;
background-color:#7F99BE;
border:1px solid #D3D3D3;
padding:4px 7px;
color:white;
font-weight:bold;
font-size:13px;
margin-left:30px;
}
#mask{
width: 100%;
height: 200%;
position: absolute;
background-color: #000;
left: 0;
opacity:0.5;
top: 0;
z-index: 8;
}
</style>
js代码
function fileUpload(id){
$("#mask").show();
$("#fileUpload").css("display","block");
$("#updateDocId").val(id);
}
function closeFileUploadWindow(){
$("#mask").hide();
$("#fileUpload").css("display","none");
}
uploadify插件js代码实现
$(function(){
$("#uploadify").uploadify({
'swf' : "${pageContext.request.contextPath}/static/js/uploadify/uploadify.swf",
'uploader' : "${pageContext.request.contextPath}/document/uploadFile",//文件上传地址
'queueId' : "fileQueue",
'queueSizeLimit' : 1,//限制上传文件的数量
'fileExt' : "*.rar,*.zip",//'fileDesc' : "RAR *.rar",//限制文件类型
'fileTypeDesc' : '压缩文件', //可选择文件类型说明
'auto' : false, //是否直接上传,若为true则不用点击开始上传
'multi' : true,//是否允许多文件上传
'method' :'post',
'width' : '65', //按钮宽度
'height' : '18', //按钮高度
'simUploadLimit': 2,//同时运行上传的进程数量
'scriptData': { "id": $("#updateDocId").val()},//传递其它的参数-----#***************
'buttonText': "选择文件",
'fileObjName' : 'uploadFile',
'onFallback':function(){
alert("您未安装FLASH控件,无法上传图片!请安装FLASH控件后再试。");
},
'onUploadStart' : function(file) {
$("#uploadify").uploadify("settings", "formData", {'id' : $("#updateDocId").val()}); <span style="font-family: Arial, Helvetica, sans-serif;">//传递其它的参数(文件ID值,若有则为更新文件)----#***************</span>
},
'onUploadSuccess' : function(file, data, response){//单个文件上传成功触发
var json = eval('(' + data + ')'); //解析成JSON格式
if(json.flag){
flag += 1;
$.messager.alert("info",json.msg,"success");
$('#uploadify').uploadify('cancel');
closeFileUploadWindow();
}else{
$.messager.alert("info",json.msg,"error");
}
},
});
})
本项目用的是spring+springmvc+jpa开发框架
controller层代码
/**
* 新增文件或更新文件,根据有没有传文件ID值来区分
* @return
*/
@RequestMapping(value = "/uploadFile", method = RequestMethod.POST)
public ResponseEntity<?> uploadFile(@RequestParam("uploadFile") CommonsMultipartFile file,HttpServletResponse response,HttpServletRequest request) {
//文档更新与添加的公共代码
Map<String, String> map = new HashMap<String, String>();
String fileName = file.getOriginalFilename();
String[] split = fileName.split("\\.");
if(split.length >2){
map.put("msg", "压缩文件命名不规范,只能存在一个点");
return new ResponseEntity<Map<String, String>>(map, HttpStatus.OK);
}
File newFile = new File(PropsUtil.getProperty("document.FirstPath")+File.separatorChar+fileName);
if(!new File(PropsUtil.getProperty("document.FirstPath")).exists()){
new File(PropsUtil.getProperty("document.FirstPath")).mkdirs();
}
if(StringUtils.equals(split[1],"zip")){
if(split[0].length() < 50 && StringUtils.isNotBlank(split[0])){
String param_id = request.getParameter("id");
if(StringUtils.isNotBlank(param_id)){
//此时为更新
//首先将该ID的文件全部删除
FileUtil.delete(new File(PropsUtil.getProperty("document.actualPath") + param_id +".zip"));
FileUtil.deltree(new File(PropsUtil.getProperty("document.actualIconPath") + param_id ));
try {
file.transferTo(newFile);
Map<String, String> analyzeResult = analyzeFile(PropsUtil.getProperty("document.FirstPath")+File.separatorChar + fileName,param_id,split[0]);
System.out.println("analyzeResult-------------------------------"+analyzeResult.toString());
Document document = new Document();
document.setId(param_id);
//查找该记录的版本号,在些基础上加1
int oldVersion = documentService.getOldVersionById(param_id);
document.setDocument_version(++oldVersion);
if(!analyzeResult.containsKey("msg")){
map = saveDocInfo(map, split, document, analyzeResult);
System.out.println("map-------------------------------"+map.toString());
if(map.containsKey("flag")){
map.put("msg", "文件更新成功");
}
}else{
map.put("msg", analyzeResult.get("msg"));
}
return new ResponseEntity<Map<String, String>>(map, HttpStatus.OK);
} catch (IllegalStateException | IOException e) {
logger.error("资料uploadFile异常:", e);
//删除原文件
FileUtil.delete(new File(PropsUtil.getProperty("document.FirstPath")+File.separatorChar+fileName));
throw new RestException(messageSourceHelper.getMessage(e.getMessage()));
}
}else{
//此时为添加新文件
try {
//保存文件信息,使最后的修改的文件名为记录的id,这步很重要
Document doc = documentService.saveDoc(split[0]);
file.transferTo(newFile);
Map<String, String> analyzeResult = analyzeFile(PropsUtil.getProperty("document.FirstPath")+File.separatorChar + fileName,doc.getId(),split[0]);
System.out.println("analyzeResult-------------------------------"+analyzeResult.toString());
if(!analyzeResult.containsKey("msg")){
map = saveDocInfo(map, split, doc, analyzeResult);
System.out.println("map-------------------------------"+map.toString());
}else{
map.put("msg", analyzeResult.get("msg"));
}
return new ResponseEntity<Map<String, String>>(map, HttpStatus.OK);
} catch (Exception e) {
logger.error("资料uploadFile异常:", e);
//删除原文件
FileUtil.delete(new File(PropsUtil.getProperty("document.FirstPath")+File.separatorChar+fileName));
throw new RestException(messageSourceHelper.getMessage(e.getMessage()));
}
}
}else{
map.put("msg", "上传压缩文件名不能超过50个字符");
}
}else{
map.put("msg", "请选择zip文件上传");
}
return null;
}
导入ant.jar包,import org.apache.tools.zip.ZipEntry; import org.apache.tools.zip.ZipFile;用util.zip的包会报错,
/**
*
* @param filePath 需要解析的文件路径(zip文件)
* @param id 文件的新名称,若不想改名,可传原文件名
* @param fileName2 解析的文件名
* @return
*/
private Map<String, String> analyzeFile(String filePath, String id, String fileName2) {
Map<String, String> map = new HashMap<String, String>();
//将文件解压缩----------start
ZipFile zipFile;
try {
zipFile = new ZipFile(filePath);
Enumeration<ZipEntry> enu = (Enumeration<ZipEntry>) zipFile.getEntries();
while (enu.hasMoreElements()) {
ZipEntry zipElement = (ZipEntry) enu.nextElement();// 单个文件 对象
InputStream read = zipFile.getInputStream(zipElement); // 单个文件文件的流
String fileName = zipElement.getName(); // 单个文件名字
String outPath = (PropsUtil.getProperty("document.unzipPath")+ File.separator + fileName).replaceAll("\\*", "/");
// 判断路径是否存在,不存在则创建文件路径
File file = new File(outPath.substring(0, outPath.lastIndexOf('/')));
if (!file.exists()) {
file.mkdirs();
}
// 判断文件全路径是否为文件夹,如果是,不需要解压
if (new File(outPath).isDirectory()) {
continue;
}
OutputStream out = new FileOutputStream(outPath);
byte[] buf1 = new byte[1024];
int len;
//将zipFileT中的文件复制到uploadFile文件夹中
while ((len = read.read(buf1)) > 0) {
out.write(buf1, 0, len);
}
read.close();
out.close();
}
zipFile.close();
//将文件解压缩----------end
//删除原文件
FileUtil.delete(filePath);
//读取config.json到MAP中(config.json是上传文件的配置文件,业务需求,要读取里面的内容存储到数据库)
map = readConfigMsgToMap(fileName2);
//文件标题不能重复,若重复提示报错
Boolean flag = documentService.findRepeatTitle(map.get("title"));
if(flag){
//此时说明数据库中已经存在相同的标题,
//删除解压文件夹
FileUtil.deltree(new File(PropsUtil.getProperty("document.unzipPath")+ File.separator + fileName2));
//删除该条记录
documentService.delete(id);
map.put("msg", "上传文件标题已存在,请修改压缩文件里config.json文件的title值");
return map;
}
//更改文件名,为后面压缩文件做准备
File f1 = new File(PropsUtil.getProperty("document.unzipPath")+ File.separator + fileName2);
File f2 = new File(PropsUtil.getProperty("document.unzipPath")+ File.separator + id);
boolean renameTo = f1.renameTo(f2);//这一步有时会报错,那是因为流没有关闭,一定要确保上面用到的流全部关闭
System.out.println("f1---"+f1+"renameTo ---f2"+f2+"---"+renameTo);
boolean fileToZip = fileToZip(PropsUtil.getProperty("document.unzipPath"), PropsUtil.getProperty("document.actualPath"), id);//将解压后的文件重新压缩,重新命名********************
//将文件的icon.png文件复制到目标文件夹
FileUtil.copyFile(PropsUtil.getProperty("document.unzipPath")+ id+ File.separator + map.get("icon"), PropsUtil.getProperty("document.actualIconPath")+ id+ File.separator + "icon.png", true);//这步还没有删除之前解压的文件,取出图片放到目标位置,备用
//如果压缩文件成功,将被压缩的文件删除
if(fileToZip){
FileUtil.deltree(new File(PropsUtil.getProperty("document.unzipPath")+ File.separator + id));
}else{
//删除解压文件夹
FileUtil.deltree(new File(PropsUtil.getProperty("document.unzipPath")+ File.separator + fileName2));
map.put("msg", "文件压缩失败");
}
} catch (IOException e) {
e.printStackTrace();
}
return map;
}
下面是文件夹的压缩,花费了很长时间才解决,有部分代码是转别人的,但他的只能压缩单个文件,不能压缩文件夹,在他的基础上做了修改,实现了压缩文件夹
/**
* 将存放在sourceFilePath目录下的源文件,打包成fileName名称的zip文件,并存放到zipFilePath路径下
* @param sourceFilePath :待压缩的文件路径
* @param zipFilePath :压缩后存放路径
* @param fileName :压缩后文件的名称
* @return
*/
public static boolean fileToZip(String sourceFilePath,String zipFilePath,String fileName){
boolean flag = false;
File sourceFile = new File(sourceFilePath);
FileInputStream fis = null;
BufferedInputStream bis = null;
FileOutputStream fos = null;
ZipOutputStream zos = null;
if(sourceFile.exists() == false){
System.out.println("待压缩的文件目录:"+sourceFilePath+"不存在.");
}else{
try {
File zipFile = new File(zipFilePath + "/" + fileName +".zip");
if(zipFile.exists()){
System.out.println(zipFilePath + "目录下存在名字为:" + fileName +".zip" +"打包文件.");
}else{
File file = new File(zipFilePath);
if (!file.exists()) {
file.mkdirs();
}
File[] sourceFiles = sourceFile.listFiles();
if(null == sourceFiles || sourceFiles.length<1){
System.out.println("待压缩的文件目录:" + sourceFilePath + "里面不存在文件,无需压缩.");
}else{
fos = new FileOutputStream(zipFile);
zos = new ZipOutputStream(new BufferedOutputStream(fos));
byte[] bufs = new byte[1024*10];
for(int i=0;i<sourceFiles.length;i++){
//创建ZIP实体,并添加进压缩包
ZipEntry zipEntry = new ZipEntry(sourceFiles[i].getName());
//读取待压缩的文件并写进压缩包里
if(sourceFiles[i].isDirectory()){
//递归读取文件流中数据
parseFileToZip(sourceFiles[i],"", zos);//实现压缩文件夹关键****************
}else{
zos.putNextEntry(zipEntry);
fis = new FileInputStream(sourceFiles[i]);
bis = new BufferedInputStream(fis, 1024*10);
int read = 0;
while((read=bis.read(bufs, 0, 1024*10)) != -1){
zos.write(bufs,0,read);
}
}
}
}
}
flag = true;
} catch (FileNotFoundException e) {
e.printStackTrace();
throw new RuntimeException(e);
} catch (IOException e) {
e.printStackTrace();
throw new RuntimeException(e);
} finally{
//关闭流
try {
if(null != bis) bis.close();
if(null != zos) zos.close();
} catch (IOException e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
}
return flag;
}
实现压缩文件夹关键
/**
* @param file 输入文件
* @param oppositePath 文件层级(必有,否则压缩后的文件没有层级结构)
* @param zos2 输出流
*/
private static void parseFileToZip(File file,String oppositePath, ZipOutputStream zos2) {
oppositePath = oppositePath +file.getName()+"/";
ZipEntry zipEntry = new ZipEntry(oppositePath);
try {
zos2.putNextEntry(zipEntry);
} catch (IOException e1) {
e1.printStackTrace();
}
FileInputStream fis = null;
BufferedInputStream bis = null;
File[] sf = file.listFiles();
for(int i=0;i<sf.length;i++){
if(sf[i].isDirectory()){
parseFileToZip(sf[i],oppositePath, zos2);
}else{
try {
ZipEntry zipEntryC = new ZipEntry(oppositePath + sf[i].getName());
zos2.putNextEntry(zipEntryC);
byte[] bufs = new byte[1024*10];
fis = new FileInputStream(sf[i]);
bis = new BufferedInputStream(fis, 1024*10);
int read = 0;
while((read=bis.read(bufs, 0, 1024*10)) != -1){
zos2.write(bufs,0,read);
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally{
//关闭流
try {
if(null != fis) fis.close();
if(null != bis) bis.close();
} catch (IOException e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
}
}
}
ps:outputstream(输出流必须到文件夹下重命名的文件,输出目标文件的所在的文件夹必须存在,没有则要先创建,否则会报找一到文件错误),inputstream(输入流必须到文件,否则会报错)**************************
因为更新与添加都用到saveDocInfo,所以提出来了,这一步是将config.json读出的数据保存到数据库中,当然是更新记录,因为id已经存在了
/**
* @param map
* @param split
* @param doc
* @param analyzeResult
*/
private Map<String, String> saveDocInfo(Map<String, String> map, String[] split, Document doc, Map<String, String> analyzeResult) {
if(StringUtils.isNotBlank(analyzeResult.get("icon")) && StringUtils.isNotBlank(analyzeResult.get("path")) && StringUtils.isNotBlank(analyzeResult.get("title"))){
//文件信息保存到数据库
doc.setId(doc.getId());
doc.setDocument_icon(doc.getId() + File.separator +"icon.png");
doc.setDocument_page_count(Integer.parseInt(analyzeResult.get("pages")));
doc.setDocument_md5_sum(getMD5(new File(PropsUtil.getProperty("document.actualPath")+File.separatorChar + doc.getId()+".zip")));
doc.setDocument_name(split[0]);
doc.setDocument_summary(analyzeResult.get("describe"));
doc.setDocument_title(analyzeResult.get("title"));
doc.setUpdate_time(new Date());
doc.setDocument_is_new(0);
doc.setDocument_download_path("zipfiles/"+doc.getId()+".zip");
doc.setDocument_local_path(PropsUtil.getProperty("document.actualPath")+doc.getId()+".zip");
if(doc.getDocument_version()!=null){
doc.setDocument_version(doc.getDocument_version() +1);
}else{
doc.setDocument_version(1);
}
if(StringUtils.isNotBlank(analyzeResult.get("tags"))){
doc.setDocument_keywords(analyzeResult.get("tags"));
}
if(StringUtils.isNotBlank(analyzeResult.get("type"))){
doc.setDocument_type(analyzeResult.get("type"));
}
//获取文件大小
File filed = new File(PropsUtil.getProperty("document.actualPath")+ doc.getId()+".zip" );
if(filed.exists()){
doc.setDocument_size((int)filed.length());
}
documentService.saveEntity(doc);
if(!map.containsKey("msg")){
map.put("msg", "文件上传成功");
map.put("flag", "true");
}
}else{
map.put("msg", "请检查上传文件完整性");
}
return map;
}
到此结束,代码主要都在controller层,其它层就不写了