zoukankan      html  css  js  c++  java
  • 关于使用ajax上传图片问题

          今天需要做一个上传图片的功能,由于框架里面没有带,上网搜了下。看到有spring mvc的图片上传,而且有例子,刚好是自己需要的,直接粘贴复制下。参考:

          http://blog.csdn.net/luckey_zh/article/details/46867957# 

        很简单,使用了commons-upload和commons-io包,配置文件位置后,页面form表单这几设置,然后就好了。

         配置完后,自己运行却发现,上传报错了:

         

    org.apache.tomcat.util.http.fileupload.FileUploadException: the request was rejected because no multipart boundary was found
    	org.apache.tomcat.util.http.fileupload.FileUploadBase$FileItemIteratorImpl.<init>(FileUploadBase.java:840)
    	org.apache.tomcat.util.http.fileupload.FileUploadBase.getItemIterator(FileUploadBase.java:259)
    	org.apache.tomcat.util.http.fileupload.FileUploadBase.parseRequest(FileUploadBase.java:283)
    	org.apache.catalina.connector.Request.parseParts(Request.java:2811)
    	org.apache.catalina.connector.Request.getParts(Request.java:2729)
    	org.apache.catalina.connector.RequestFacade.getParts(RequestFacade.java:1075)
    	org.springframework.web.multipart.support.StandardMultipartHttpServletRequest.parseRequest(StandardMultipartHttpServletRequest.java:84)
    	org.springframework.web.multipart.support.StandardMultipartHttpServletRequest.<init>(StandardMultipartHttpServletRequest.java:77)
    	org.springframework.web.multipart.support.StandardServletMultipartResolver.resolveMultipart(StandardServletMultipartResolver.java:76)
    	org.springframework.web.servlet.DispatcherServlet.checkMultipart(DispatcherServlet.java:1073)
    	org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:912)
    	org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:877)
    	org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:966)
    	org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:868)
    	javax.servlet.http.HttpServlet.service(HttpServlet.java:650)
    	org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:842)
    	javax.servlet.http.HttpServlet.service(HttpServlet.java:731)
    	org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
    	com.springapp.mvc.filter.UploadImageInterceptor.doFilter(UploadImageInterceptor.java:27)
    

        上网搜了下,原来是因为自己使用的是ajax提交的,但是ajax默认的content-type是x-www-form-urlencoded,这样提交文件是无法生效的。由于框架的原因,如果改成form提交和其他页面相差太大,而且不一定能解决问题,于是决定继续顺着ajax为何不能提交这个坑继续下去。

       然后上网继续搜,发现需要设置ajax的几个属性为false,这样才能提交:(参考http://www.jianshu.com/p/46e6e03a0d53)

      

     $.ajax({
            	url: "ur",
                contentType: false,  //必须设置 
                processData: false,  //必须设置
                cache: false,   //设置为false
              // data: $(form).serialize(),
                data: new FormData($('#myForm')[0]),
                type: "POST",
    

      刚开始用    data: $(form).serialize(), 结果不行,换成了下面的这种,然而又有问题了。页面的元素通过request.getParameter("")居然获取不到了。。。










    继续搜,为何搜不到。。。然后在一篇文章上面看到了下面的说法:(参考:http://www.chongchonggou.com/g_464425214.html)

    设置提交方式为enctype="multipart/form-data"后,使用request.getParameter(“”)是获取不到页面的formData的数据的。 上面也说了解决办法,就是使用common-smartupload进行获取,我就是

    通过这种方式获取的,不过碰到了几个问题,比如乱码问题、windows/linux 分隔符问题以及文件找不到等小问题,最后总算解决了。另外附上一篇一个大神之前写的一篇文章。

    http://www.cnblogs.com/xdp-gacl/p/4200090.html






    附上自己的代码以及实现:

    前端:
     <link href="#springUrl('/static/css/bootstrap.min.css')" rel="stylesheet">
    <link href="#springUrl('/static/css/style.css')" rel="stylesheet">
    <link href="#springUrl('/static/css/datetimepicker.css')" rel="stylesheet">
    <body class="white-bg">
    <div class="ibox-content" style=" 430px;">
       <form id="myForm" class="form-horizontal" autocomplete="off" data-validator-option="{theme:'default'}" enctype="multipart/form-data" >
       	   <input type="hidden" name="id" value="$!{activity.id}">
           <div class="form-group"><label class="col-sm-2 control-label">xxx</label>
               <div class="col-sm-10">
               		<input type="text" class="form-control" value="$!{activity.title}" name="title" data-rule="xxx:required;title">
               </div>
           </div>
           <div class="hr-line-dashed"></div>
           <div class="form-group"><label class="col-sm-2 control-label">xxx</label>
               <div class="col-sm-10">
                   <textarea class="form-control"   value="$!{activity.content}"  name="content" data-rule="xxx:required;content">$!{activity.content}</textarea>
               </div>
           </div>
    
           <div class="hr-line-dashed"></div>
           <div class="form-group"><label class="col-sm-2 control-label">xxx</label>
    
               #if(${activity.pic} == "null")
               <div class="col-sm-10">
                   <input type="file" name="pic"  id="pic" data-rule="xxx:required;pic"/>
               </div>
               #end
               #if(${activity.pic} != "null")
               <div class="col-sm-10">
                   <input type="file" name="pic"  id="pic" />
               </div>           <img alt="xxx" src="#springUrl('/static/upload/images/f854d8f0186649fcac9a01b4a5da2c8d.jpg')" style="height:100%; 100%">
                 #end
           </div>
    
    
           <div class="hr-line-dashed"></div>
            <div class="form-group"><label class="col-sm-2 control-label">xxx/label>
                <div class="col-sm-10">
                <select class="form-control m-b" name="tag">
                    <option  value="1">xx</option>
                    <option  value="2">xx</option>
                    <option  value="3">xx</option>
                    <option  value="4">xx</option>
                </select>
                </div>
            </div>
           <div class="form-group"><label class="col-sm-2 control-label">xx</label>
               <div class="col-sm-10">
                   <input type="text" class="form-control" value="$!{activity.places}" name="places" data-rule="xx:required;places">
               </div>
           </div>
           <div class="form-group"><label class="col-sm-2 control-label">xx</label>
               <div class="col-sm-10">
                   <input type="text" class="form-control" value="$!{activity.deposit}" name="deposit" data-rule="xx:required;deposit">
               </div>
           </div>
           <div class="form-group"><label class="col-sm-2 control-label">xx</label>
               <div class="col-sm-10">
                   <input type="text" class="form-control" value="$!{activity.fullPrice}" name="fullPrice" data-rule="xx:required;fullPrice">
               </div>
           </div>
           <div class="form-group"><label class="col-sm-2 control-label">xx</label>
               <div class="col-sm-10">
                   <input type="text" class="form-control" value="$!{activity.detailAddress}" name="detailAddress" data-rule="xx:required;detailAddress">
               </div>
           </div>
           <div class="row">
               <div class="col-md-6">
                   <div class="form-group">
                       <label class="control-label">xx:</label>
                       <div class="controls">
                           <input value="$!date.format('yyyy-MM-dd HH:mm:ss ',$!activity.beginTime)"    name="beginTime" id="beginTime">
                       </div>
                   </div>
               </div>
           </div>
    
           <div class="row">
               <div class="col-md-6">
                   <div class="form-group">
                       <label class="control-label">xx:</label>
                       <div class="controls">
                           <input value="$!date.format('yyyy-MM-dd HH:mm:ss ',$!activity.endTime)"    name="endTime" id="endTime">
                       </div>
                   </div>
               </div>
           </div>
    
            <div class="hr-line-dashed"></div>
            <div class="form-group">
                <div class="text-center">
                    <button class="btn btn-primary" type="submit">#if($!{activity})修 改#else提 交#end</button>
                </div>
            </div>
        </form>
    </div>
    <script src="#springUrl('/static/js/jquery-2.1.1.js')"></script>
    <script src="#springUrl('/static/plugins/nice-validator-0.8.1/jquery.validator.js?local=zh-CN')"></script>
    <script src="#springUrl('/static/js/common.js')"></script>
    <script src="#springUrl('/static/js/bootstrap-datetimepicker.js')"></script>
    <script src="#springUrl('/static/js/bootstrap-datetimepicker.zh-CN.js')"></script>
    
    <script type="text/javascript">
        $('#beginTime').datetimepicker({
            format: 'yyyy-mm-dd hh:ii:ss',
            language: 'zh-CN',
            autoclose: true
        });
        $('#endTime').datetimepicker({
            format: 'yyyy-mm-dd hh:ii:ss',
            language: 'zh-CN',
            autoclose: true
        });
       
    
    $("#myForm").validator({
        valid: function(form){
            var me = this;
            // 提交表单之前,hold住表单,防止重复提交
            me.holdSubmit();
            $.ajax({
            	url: "#springUrl('/activities/editActivity')",
                contentType: false,
                processData: false,
                cache: false,
              // data: $(form).serialize(),
                data: new FormData($('#myForm')[0]),
                type: "POST",
                success: function(data){
                	var d = JSON.parse(data);
                    if(d.success && d.data){
                    	window.parent.location.reload();
                    	//当你在iframe页面关闭自身时
                    	//var index = parent.layer.getFrameIndex(window.name); //先得到当前iframe层的索引
                    	//parent.layer.close(index); //再执行关闭   
                    } else {
                    	//失败,提交表单成功后,释放hold,如果不释放hold,就变成了只能提交一次的表单
                        me.holdSubmit(false);
                    }
                }
            });
        }
    });
    </script>
    </body>
    </html>
    

      后端代码以及实现:

      @ResponseBody
        @Permission("5001")
        @RequestMapping(value = "/editActivity")
        public String editActivity(HttpServletRequest request,Activity activity) throws ParseException {
            activity = new Activity();
            boolean rlt = false;
            DiskFileItemFactory factory = new DiskFileItemFactory();
            ServletFileUpload upload = new ServletFileUpload(factory);
            //获得物理路径webapp所在路径
            String pathRoot = request.getSession().getServletContext().getRealPath("");
            String path="";
            upload.setHeaderEncoding("UTF-8");// 解决乱码关键
            Map<String,String>  map = new HashMap<>();
             try {
                List<FileItem> list = upload.parseRequest(request);
                for(FileItem item : list){
                    if(item.isFormField()){
                      //注意此处是没有图片的其他属性
                        String value = null;
                        try {
                            value = new String(item.getString("utf-8"));
                        } catch (UnsupportedEncodingException e) {
                            e.printStackTrace();
                        }
                        map.put(item.getFieldName(),value);
                    }else{
                        //生成uuid作为文件名称
                        String uuid = UUID.randomUUID().toString().replaceAll("-","");
                        //获得文件后缀名称
                        String imageName=item.getName().substring(item.getName().lastIndexOf(".")+1);
                        String fileUrl = Constant.FILE_URL;
                        path = fileUrl + uuid+"."+imageName;
                        map.put(item.getFieldName(),Constant.FILE_URL+uuid+"."+imageName);
                        upload.setHeaderEncoding("UTF-8");
                        try {
                                                //得到上传文件的扩展名
                                                  String fileExtName = imageName.substring(imageName.lastIndexOf(".")+1);
                                                     //如果需要限制上传的文件类型,那么可以通过文件的扩展名来判断上传的文件类型是否合法
                                               System.out.println("上传的文件的扩展名是:"+fileExtName);
                                                //获取item中的上传文件的输入流
                                                     InputStream in = item.getInputStream();
                                                      //得到文件保存的名称
                                                    String saveFilename = path;
                                                     //得到文件的保存目录
                                                      String realSavePath = makePath(pathRoot, fileUrl);
                                                      //创建一个文件输出流
                                                       FileOutputStream out = new FileOutputStream(pathRoot+path);
                                                      //创建一个缓冲区
                                                    byte buffer[] = new byte[1024];
                                                      //判断输入流中的数据是否已经读完的标识
                                                      int len = 0;
                                                     //循环将输入流读入到缓冲区当中,(len=in.read(buffer))>0就表示in里面还有数据
                                                      while((len=in.read(buffer))>0){
                                                            //使用FileOutputStream输出流将缓冲区的数据写入到指定的目录(savePath + "\" + filename)当中
                                                                out.write(buffer, 0, len);
                                                      }
                                                      //关闭输入流
                                                       in.close();
                                                      //关闭输出流
                                                      out.close();
                                                    //删除处理文件上传时生成的临时文件
                                                  item.delete();
                        } catch (IOException e) {
                            e.printStackTrace();
                        }
                    }
                }
            } catch (FileUploadException e) {
                e.printStackTrace();
            }
    
            activity.setBeginTime(DateUtils.toDate(map.get("beginTime"),"yyyy-MM-dd HH:mm:ss") );
            activity.setPlaces(Integer.valueOf(map.get("places")));
            activity.setCity(map.get("city"));
            activity.setContent(map.get("content"));
            activity.setTag(Integer.valueOf(map.get("tag")));
            activity.setDeposit(new BigDecimal(map.get("deposit")));
            activity.setDetailAddress(map.get("detailAddress"));
            activity.setPic(map.get("pic"));
            activity.setEndTime(DateUtils.toDate(map.get("endTime"),"yyyy-MM-dd HH:mm:ss"));
            activity.setTitle(map.get("title"));
            activity.setUpdateTime(new Date());
             if(StringUtils.isNotBlank(map.get("id"))){
                 activity.setId(Long.valueOf(map.get("id")));
                 rlt = activityService.updateById(activity);
             }else {
                 activity.setAddTime(new Date());
                 rlt = activityService.insert(activity);
             }
            return callbackSuccess(rlt);
        }

    配置文件这块,原来的springmvc 是有这样的一段配置的:

      

    <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
       <property name="defaultEncoding" value="utf-8"/>
       <!– 最大内存大小 –>
       <property name="maxInMemorySize" value="10240"/>
       <!– 最大文件大小,-1为不限制大小 –>
       <property name="maxUploadSize" value="-1"/>
    </bean>
    

      

       但是实际做后发现,配置后使用common-fileupload上传不起作用,原因就是因为fileUpload解析过request,所以导致上传为空。



    所以才有了上面的自己写代码来上传。参考:http://zzc1684.iteye.com/blog/2258463
  • 相关阅读:
    java下载url图片链接
    mysql 设计索引的原则
    169. 多数元素
    263. 丑数
    markdown 语法笔记
    70.爬楼梯
    540. 有序数组中的单一元素
    88. 合并两个有序数组
    面试题57
    152. 乘积最大子序列
  • 原文地址:https://www.cnblogs.com/thinkingandworkinghard/p/7075261.html
Copyright © 2011-2022 走看看