spirgmvc+ajaxfileupload上传文件

spirgmvc+ajaxfileupload上传文件

springmvc在上传文件方面有一个MutilpartFile类,这个类中的有直接保存文件的功能。使用的时候首先需要引入commons-fileupload,然后在spirngmvc的配置文件中配置。
 <!-- 上传文件拦截,设置最大上传文件大小   10M=10*1024*1024(B)=10485760 bytes -->
    <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
        <property name="maxUploadSize" value="10485760"/>
    </bean>

之后,需要一个controller进行处理用户上传文件的请求。
package com.xueyou.ssm.controller;


import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.xueyou.ssm.utils.Base;
import com.xueyou.ssm.utils.SysContent;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import sun.misc.BASE64Encoder;

import javax.servlet.http.HttpServletRequest;
import java.io.File;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.HashMap;
import java.util.Map;

/**
 * Created by wuxueyou on 16/10/3.
 */
@RestController
@RequestMapping(value = "/file", method = RequestMethod.POST, produces = "application/json;charset=UTF-8;")
public class FileUploadController {

    @RequestMapping(value = "/upload",produces = "text/html;charset=UTF-8;")
    private String fileUpload(MultipartFile file, Model model) {
        Map<String, Object> resMap = new HashMap<>();
        if (!file.isEmpty()) {
            HttpServletRequest request = SysContent.getRequest();
            String relativePathDir = "/ssmUpload/files";
            String realPathDir = request.getSession().getServletContext().getRealPath(relativePathDir);
            String fileSign = (new SimpleDateFormat("yyyyMMddHHmmssSSS")).format(Calendar.getInstance().getTime());
            String suffix = file.getOriginalFilename().substring(file.getOriginalFilename().lastIndexOf("."));
            String fileName = realPathDir + "/" + file.getName() + fileSign + suffix;
            System.out.println(fileName);
            File myDir = new File(realPathDir);
            if (!myDir.exists()) {
                myDir.mkdirs();
            }
            File uploadFile = new File(fileName);
            try {
                byte[] filebytes = file.getBytes();
                file.transferTo(uploadFile);
                resMap.put("resMsg", Base.MSG_SUCCESS);
                resMap.put("resCode", Base.MSG_CODE_SUCCESS);
                resMap.put("resFile", new BASE64Encoder().encode(filebytes));
                resMap.put("resFilePath",relativePathDir + "/" + file.getName() + fileSign + suffix);
            } catch (IOException e) {
                e.printStackTrace();
            }
        } else {
            resMap.put("resCode", Base.MSG_CODE_ERROR);
            resMap.put("resMsg", Base.MSG_ERROR);
        }
        String resJson = "";
        ObjectMapper mapper = new ObjectMapper();
        try {
            resJson = mapper.writeValueAsString(resMap);
        } catch (JsonProcessingException e) {
            e.printStackTrace();
        }
        return resJson;
    }
}

其中获得HttpServletRequest和HttpServletResponse的方式请看 springmvc 得到HttpServletRequest、HttpServletResponse、HttpSession

下面是前段代码,首先需要的就是ajaxfileupload.js(可以下载,但是可能有bug,推荐用本文中的这个)
/**
 * Created by wuxueyou on 16/10/3.
 */
// JavaScript Document
jQuery.extend({

    createUploadIframe: function (id, uri) {
        //create frame
        var frameId = 'jUploadFrame' + id;

        if (window.ActiveXObject) {
            //var io = document.createElement('<iframe id="' + frameId + '" name="' + frameId + '" />');
            if (jQuery.browser.version == "9.0" || jQuery.browser.version == "10.0") {
                var io = document.createElement('iframe');
                io.id = frameId;
                io.name = frameId;
            } else if (jQuery.browser.version == "6.0" || jQuery.browser.version == "7.0" || jQuery.browser.version == "8.0") {
                var io = document.createElement('<iframe id="' + frameId + '" name="' + frameId + '" />');
                if (typeof uri == 'boolean') {
                    io.src = 'javascript:false';
                }
                else if (typeof uri == 'string') {
                    io.src = uri;
                }
            }
        } else {
            var io = document.createElement('iframe');
            io.id = frameId;
            io.name = frameId;
        }
        io.style.position = 'absolute';
        io.style.top = '-1000px';
        io.style.left = '-1000px';

        document.body.appendChild(io);

        return io;
    },
    createUploadForm: function (id, fileElementId, data) {
        //create form
        var formId = 'jUploadForm' + id;
        var fileId = 'jUploadFile' + id;
        var form = jQuery('<form  action="" method="POST" name="' + formId + '" id="' + formId + '" enctype="multipart/form-data"></form>');
        var oldElement = jQuery('#' + fileElementId);
        var newElement = jQuery(oldElement).clone();
        jQuery(oldElement).attr('id', fileId);
        jQuery(oldElement).before(newElement);
        jQuery(oldElement).appendTo(form);

        //add data
        if (data) {
            for (var i in data) {
                $('<input type="hidden" name="' + i + '" value="' + data[i] + '" />').appendTo(form);
            }
        }
        //set attributes
        jQuery(form).css('position', 'absolute');
        jQuery(form).css('top', '-1200px');
        jQuery(form).css('left', '-1200px');
        jQuery(form).appendTo('body');
        return form;
    },

    ajaxFileUpload: function (s) {
        // TODO introduce global settings, allowing the client to modify them for all requests, not only timeout
        s = jQuery.extend({}, jQuery.ajaxSettings, s);
        var id = s.id;
        //var id = s.fileElementId;
        var form = jQuery.createUploadForm(id, s.fileElementId, s.data);
        var io = jQuery.createUploadIframe(id, s.secureuri);
        var frameId = 'jUploadFrame' + id;
        var formId = 'jUploadForm' + id;

        if (s.global && !jQuery.active++) {
            // Watch for a new set of requests
            jQuery.event.trigger("ajaxStart");
        }
        var requestDone = false;
        // Create the request object
        var xml = {};
        if (s.global) {
            jQuery.event.trigger("ajaxSend", [xml, s]);
        }

        var uploadCallback = function (isTimeout) {
            // Wait for a response to come back
            var io = document.getElementById(frameId);
            try {
                if (io.contentWindow) {
                    xml.responseText = io.contentWindow.document.body ? io.contentWindow.document.body.innerHTML : null;
                    xml.responseXML = io.contentWindow.document.XMLDocument ? io.contentWindow.document.XMLDocument : io.contentWindow.document;
                } else if (io.contentDocument) {
                    xml.responseText = io.contentDocument.document.body ? io.contentDocument.document.body.innerHTML : null;
                    xml.responseXML = io.contentDocument.document.XMLDocument ? io.contentDocument.document.XMLDocument : io.contentDocument.document;
                }
            } catch (e) {
                jQuery.handleError(s, xml, null, e);
            }
            if (xml || isTimeout == "timeout") {
                requestDone = true;
                var status;
                try {
                    status = isTimeout != "timeout" ? "success" : "error";
                    // Make sure that the request was successful or notmodified
                    if (status != "error") {
                        // process the data (runs the xml through httpData regardless of callback)
                        var data = jQuery.uploadHttpData(xml, s.dataType);
                        if (s.success) {
                            // ifa local callback was specified, fire it and pass it the data
                            s.success(data, status);
                        }
                        ;
                        if (s.global) {
                            // Fire the global callback
                            jQuery.event.trigger("ajaxSuccess", [xml, s]);
                        }
                        ;
                    } else {
                        jQuery.handleError(s, xml, status);
                    }

                } catch (e) {
                    status = "error";
                    jQuery.handleError(s, xml, status, e);
                }
                ;
                if (s.global) {
                    // The request was completed
                    jQuery.event.trigger("ajaxComplete", [xml, s]);
                }
                ;

                // Handle the global AJAX counter
                if (s.global && !--jQuery.active) {
                    jQuery.event.trigger("ajaxStop");
                }
                ;
                if (s.complete) {
                    s.complete(xml, status);
                }
                ;

                jQuery(io).unbind();
                setTimeout(function () {
                    try {
                        jQuery(io).remove();
                        jQuery(form).remove();
                    } catch (e) {
                        jQuery.handleError(s, xml, null, e);
                    }
                }, 100);
                xml = null;
            }
            ;
        }
        // Timeout checker
        if (s.timeout > 0) {
            setTimeout(function () {
                if (!requestDone) {
                    uploadCallback("timeout");
                }
            }, s.timeout);
        }
        try {
            var form = jQuery('#' + formId);
            jQuery(form).attr('action', s.url);
            jQuery(form).attr('method', 'POST');
            jQuery(form).attr('target', frameId);
            if (form.encoding) {
                form.encoding = 'multipart/form-data';
            } else {
                form.enctype = 'multipart/form-data';
            }
            jQuery(form).submit();

        } catch (e) {
            jQuery.handleError(s, xml, null, e);
        }
        /*if(window.attachEvent){
         document.getElementById(frameId).attachEvent('onload', uploadCallback);
         }
         else{
         document.getElementById(frameId).addEventListener('load', uploadCallback, false);
         }   */
        jQuery('#' + frameId).load(uploadCallback);
        return {
            abort: function () {
            }
        };

    },

    uploadHttpData: function (r, type) {
        var data = !type;
        data = type == "xml" || data ? r.responseXML : r.responseText;
        // ifthe type is "script", eval it in global context
        if (type == "script") {
            jQuery.globalEval(data);
        }

        // Get the JavaScript object, ifJSON is used.
        if (type == "json") {
            data = r.responseText;
            var start = data.indexOf(">");
            if (start != -1) {
                var end = data.indexOf("<", start + 1);
                if (end != -1) {
                    data = data.substring(start + 1, end);
                }
            }
            eval("data = " + data);
        }

        // evaluate scripts within html
        if (type == "html") {
            jQuery("<div>").html(data).evalScripts();
        }

        return data;
    },
    /*handleError: function( s, xml, status, e ) {
     // If a local callback was specified, fire it
     if ( s.error )
     s.error( xml, status, e );

     // Fire the global callback
     if ( s.global )
     jQuery.event.trigger( "ajaxError", [xml, s, e] );
     }*/
    handleError: function (s, xhr, status, e) {
        // If a local callback was specified, fire it
        if (s.error) {
            s.error.call(s.context || s, xhr, status, e);
        }
        // Fire the global callback
        if (s.global) {
            (s.context ? jQuery(s.context) : jQuery.event).trigger("ajaxError", [xhr, s, e]);
        }
    }
});

前台页面:
<%--
  Created by IntelliJ IDEA.
  User: wuxueyou
  Date: 16/10/1
  Time: 下午2:05
  To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" isELIgnored="false" %>
<%@taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c"%>
<html>
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <title>登录</title>
    <script src="${pageContext.request.contextPath}/Component/angular.min-1.2.19.js"></script>
    <script src="${pageContext.request.contextPath}/Component/angular-route.min-1.2.19.js"></script>
    <script src="${pageContext.request.contextPath}/Component/angular-ui/angular-ui-router.min.js"></script>
    <link href="${pageContext.request.contextPath}/Component/bootstrap/css/bootstrap.min.css" rel="stylesheet">
    <script src="${pageContext.request.contextPath}/Component/bootstrap/js/jquery-1.8.3.min.js"></script>
    <script src="${pageContext.request.contextPath}/Component/ajaxfileupload.js"></script>
    <script src="${pageContext.request.contextPath}/Component/bootstrap/js/bootstrap.min.js"></script>
    <!--[if lte IE 9]>
    <script src="${pageContext.request.contextPath}/Component/bootstrap/js/respond.min.js"></script>
    <script src="${pageContext.request.contextPath}/Component/bootstrap/js/html5.js"></script>
    <![endif]-->
    <script src="${pageContext.request.contextPath}/js/base.js"></script>
    <script src="${pageContext.request.contextPath}/js/common/fileupload.js"></script>
</head>
<body ng-app="fileupload" ng-controller="fileuploadController" class="container">
<h1>fileupload.jsp</h1>
<hr/>
    select a file <input type="file" name="file" id="file">
<div id="resPath"></div>
<div id="fileimg"><img src="" style="width: 200px;height: 200px;border: solid #cccccc 1px;"/></div>
<button class="btn btn-primary" id="ajaxUpload">ajax上传</button>
</body>
</html>

前台js
/**
 * Created by wuxueyou on 16/10/1.
 */
var fileuploadapp = angular.module('fileupload', [], function ($httpProvider) {
    baseRequest($httpProvider);
});

fileuploadapp.controller('fileuploadController', function ($scope) {
    $scope.test = "aabbcc";
    $('#resPath').text(' ');
    $('#ajaxUpload').click(function () {
        $.ajaxFileUpload({
            url:BASE_URL + '/file/upload',
            securityuri:false,
            fileElementId:'file',
            dataType:'json',
            success:function(data,status){
                if(data != null){
                    if(data.resCode == 1){
                        alert('上传成功!');
                        $('#resPath').text(data.resFilePath);
                        $('#fileimg').empty();
                        $('#fileimg').append('<img src="data:image/png;base64,'+ data.resFile + '" style="width: 200px;height: 200px;border: solid #cccccc 1px;"/>');
                        //$('#fileimg').attr("src","data:image/png;base64," + data.resFile);
                    }else{
                        alert('上传失败!');
                        $('#resPath').text(' ');
                        $('#fileimg').empty();
                        $('#fileimg').append('<img src="data:image/png;base64,'+ 'error' + '" style="width: 200px;height: 200px;border: solid #cccccc 1px;"/>');
                        //$('#fileimg').attr("src","data:image/png;base64,--");
                    }
                }
            },
            error: function (data, status) {
                alert('error');
            }
        })
    });
});

下面是运行效果,还有一点问题,就是IE8,上传图片完成后,图片不能显示出来。
需要注意的是ie8 ajaxfileupload支持的jquery最高不能超过1.9。如果超过,会报错。如果不考虑ie8那么无所谓了。


附:下面是解决IE8下不显示图片的问题。首先是上传后,能够在浏览器中访问图片资源,然后是在ie中加载图片的时候,不要使用base64编码的方式,因为图片过大的话,会出现错误。下面是代码:
/**
 * Created by wuxueyou on 16/10/1.
 */
var fileuploadapp = angular.module('fileupload', [], function ($httpProvider) {
    baseRequest($httpProvider);
});

fileuploadapp.controller('fileuploadController', function ($scope) {
    $scope.test = "aabbcc";
    $('#resPath').text(' ');
    $('#ajaxUpload').click(function () {
        $.ajaxFileUpload({
            url: BASE_URL + '/file/upload',
            securityuri: false,
            fileElementId: 'file',
            dataType: 'json',
            timeout:30000,
            success: function (data, status) {
                if (data != null) {
                    if (data.resCode == 1) {
                        var path = BASE_URL + data.resFilePath;
                        $('#img').attr("src",path);
                        //ie8下,上传如果文件过大,渲染不出来
                        //$('#img').attr("src","data:image/jpg;base64," + data.resFile);
                        alert('上传成功!');
                        $('#resPath').text(data.resFilePath);
                    } else {
                        var errorPath = BASE_URL + '/img/404.jpg';
                        $('#img').attr("src",errorPath);
                        alert('上传失败!');
                        $('#resPath').text(' ');
                    }
                }
            },
            error: function (data, status) {
                alert('error');
            }
        });
    });
});

效果如下:


附2:
最近在做项目的时候发现,一个界面中很多个上传控件,这个时候以为需要些好多后台,后来发现,只需要写一个后台。ajaxfileupload和后台中的代码对应是这样的:
界面上name属性和后台中Mutilpartfile file这个参数对应。也就是说前台是可以这样写的:
<input type="file" id="ccc" name="file"/>
然后在js中使用的时候
$ajaxFileUpload的时候,需要把fileElementId改为“ccc”即可。
这样就解决了单个页面中有多个文件上传控件,进行上传任务的问题了。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值