1. 程式人生 > >ajax實現非同步上傳圖片

ajax實現非同步上傳圖片

圖片上傳並回顯是一個最基本的功能,本文只簡單實現了一個demo,並沒有進行復雜的判斷,簡單記錄下操作流程:
js中用到了Formdata:FormData物件用以將資料編譯成鍵值對,以便用XMLHttpRequest來發送資料。其主要用於傳送表單資料,但亦可用於傳送帶鍵資料(keyed data)。如果表單enctype屬性設為multipart/form-data ,可以用 new formdata物件來模擬submit()方法來發送資料。
前端程式碼實現:

<img width="100" height="100" id="ImgUrl"/>
<form id="formTag" enctype="multipart/form-data">
    <div class="uploadImgBtn" id="uploadImgBtn">
        <input class="uploadImg" type="file" name="file" id="tpfile">
    </div>
</form>

css樣式:

<style>
        .uploadImgBtn {
            width: 100px;
            height: 100px;
            cursor: pointer;
            position: relative;
            background: url("img/add.gif") no-repeat;
            -webkit-background-size: cover;
            background-size: cover;
        }
        .uploadImgBtn .uploadImg {
            position: absolute;
            right: 0;
            top: 0;
            width: 100%;
            height: 100%;
            opacity: 0;
            cursor: pointer;
        } 
    </style>

ajax程式碼實現:

<script>
        $(document).ready(function(){
            $("#tpfile").on("change", upload );
        })
        function upload(){

            var self = this;
            $.ajax({
                url: "/upload/uploadPic.do",
                type: "post",
                dataType: "json",
                cache: false,
                data: new FormData($("#formTag")[0]),
                processData: false,// 不處理資料
                contentType: false, // 不設定內容型別
                success: function(data){
                   $("#ImgUrl").attr("src", data.path);
                   /*
                   圖片顯示路徑出錯,沒解決:反斜槓轉義
                   $(self).parent().css({
                        "background-image": "url("+data.path+")"
                    })*/;
                }
            })
        }
 </script>

後臺程式碼實現:


@RequestMapping("/upload/uploadPic.do")
    public void uploadPic(MultipartFile file, HttpServletRequest request, HttpServletResponse response) throws IllegalStateException, IOException {
        try {
            // 獲取圖片原始檔名
            String originalFilename = file.getOriginalFilename();
            // 檔名使用當前時間
            String name = new SimpleDateFormat("yyyyMMddHHmmssSSS").format(new Date());            
            // 圖片上傳的相對路徑(因為相對路徑放到頁面上就可以顯示圖片)
            String path = File.separator+"img"+File.separator + name + "_" +originalFilename ;
            System.out.println(path);
            // 圖片上傳的絕對路徑
            String url = request.getSession().getServletContext().getRealPath("") + path;
            File dir = new File(url);
            if(!dir.exists()) {
                dir.mkdirs();
            }
            // 上傳圖片
            file.transferTo(new File(url));
            // 將相對路徑寫回(json格式)
            JSONObject jsonObject = new JSONObject();
            jsonObject.put("path",path);
            // 設定響應資料的型別json
            response.setContentType("application/json; charset=utf-8");
            response.getWriter().write(jsonObject.toString());
        } catch (Exception e) {
            //throw new RuntimeException("伺服器繁忙,上傳圖片失敗");
            throw new RuntimeException(e);
        }
    }

測試結果:
image
雖然簡單實現了,但json格式轉義出錯,還沒有解決。

=========================華麗的分割線===========================
實現多檔案同時上傳
檔案上傳有很多的注意細節:
1、為保證伺服器安全,上傳檔案應該放在外界無法直接訪問的目錄下,比如放於WEB-INF目錄下。
2、為防止檔案覆蓋的現象發生,要為上傳檔案產生一個唯一的檔名。
3、為防止一個目錄下面出現太多檔案,要使用hash演算法打散儲存。
4、要限制上傳檔案的最大值。
5、要限制上傳檔案的型別,在收到上傳檔名時,判斷後綴名是否合法。
前端實現:

springmvc 多檔案上傳
<form action="/upload/uploadMulFile.do" enctype="multipart/form-data" method="post" >
    上傳檔案1:<input type="file" name="files"><br/>
    上傳檔案2:<input type="file" name="files"><br/>
    <input type="submit" value="提交"/>
</form>

後端程式碼實現:


   /**
     * 多檔案上傳
     * @param request
     */
    @RequestMapping("/upload/uploadMulFile.do")
    public String uploadMulFile(@RequestParam("files") MultipartFile []multipartFiles, HttpServletRequest request){

        String path = File.separator+"upload"+File.separator ;
        String realPath = request.getSession().getServletContext().getRealPath("") + path;

        File dir = new File(realPath);
        if(!dir.exists()) {
            dir.mkdirs();
        }

        if(multipartFiles == null || multipartFiles.length == 0){
            return null;
        }
        if(multipartFiles.length>0){
            for (MultipartFile file :multipartFiles){
                try {

                    file.transferTo(new File(realPath + file.getOriginalFilename()));
                } catch (Exception e) {
                    throw new RuntimeException(e);
                }
            }
        }
        return "tp";
    }

上傳下載檔案詳細參考部落格3.

參考:
1.https://www.cnblogs.com/kongxc/p/7831837.html
2.https://www.jianshu.com/p/18206a94fee5
3.https://www.cnblogs.com/xdp-gacl/p/4200090.html