【问题标题】:Tomcat 6.0 Large File Upload (> 2 GB)Tomcat 6.0 大文件上传 (> 2 GB)
【发布时间】:2012-03-03 03:20:54
【问题描述】:

我在上传文件大于 2GB 的 HTTP 文件时遇到问题。服务器和客户端都是 64 位的,因此从系统角度来看,2GB 必须没有限制。我做了以下事情:

  1. 在阿帕奇 LimitRequestBody = 0 (http://httpd.apache.org/docs/2.0/mod/core.html#LimitRequestBody)
  2. 在 Tomcat 连接器中 maxPostSize = 0 (http://tomcat.apache.org/tomcat-5.5-doc/config/ajp.html)

我正在使用 apache commons 文件上传。我还尝试使用 ServerFileUpload setMaxFileSize 方法设置最大文件大小。

我能够上传小于 2GB 的文件(我成功尝试了 1.88GB 的​​文件)。请指导我,我在这里缺少什么?

更具体地说 ServletFileUpload.parseRequest 方法在上传大文件时返回 0 个 FileItems

这里是sn-p的代码:

if (isMultipartForm()) {
try {
    DiskFileItemFactory factory = new DiskFileItemFactory();
    factory.setSizeThreshold(SIZE_THRESHOLD);//SIZE_THRESHOLD = 4MB
    ServletFileUpload upload = new ServletFileUpload(factory);
        //upload.setFileSizeMax(3000000000L); Tried this too
    upload.setProgressListener(progressListener);
    items = upload.parseRequest(request);
    if(items != null && items.size() == 0)
    return new CommandResultSet(false, "NoItemsFoundInRequest");
    return new CommandResultSet(true, "" + ( (items!=null) ? items.size() : ""));
} catch(FileUploadException e) {
    e.printStackTrace();
    System.out.println("Exception in MultipartFormManager. Can not parse request.");    
    return new CommandResultSet(false, e.getMessage());
    }
}

【问题讨论】:

  • 您究竟是如何使用 apache 库的?向我们展示代码。
  • 您应该使用原始命令行工具(如“wget”)来测试您的服务器,以排除任何服务器问题:文件大小编码为堆栈中某处的整数、文件系统限制...
  • 您的问题有什么症状?传输卡住或停止?任何服务器堆栈跟踪? “在线”活动怎么样 - 用wireshark查看它。
  • 这是个好主意。我现在将使用 wget 运行一些测试。谢谢。
  • 我试过 wget,我认为问题出在 Apache 设置上。我在 Directory 标记下将 LimitRequestBody 设置为 0。我还应该在 apache 中检查什么?

标签: java file-upload


【解决方案1】:

如果您使用的是 common-fileupload 1.1 或旧版本,那么您上传的文件不能超过 (1.9888)~2GB。这里的问题是这个 jar 正在调用一个名为 getContentLength 的方法,它是 int 类型的,因此您的请求只能处理最大为 Integer.MAX_VALUE 的大小。在 1.3 等最新版本的 common-fileupload 中,这个问题得到了解决。 希望这会有所帮助。

【讨论】:

    【解决方案2】:

    我当然可能有新的错误,但我还没有发现即使是 64 位浏览器也能处理大于 2GB 的上传。问题不在于服务器,而在于浏览器。你会很奇怪地发现,大多数现代浏览器都会很乐意从标准服务器下载大于 2GB 的文件,而无需特殊配置。

    【讨论】:

    • 您能否提供任何支持您的答案的链接。我只能找到这个(motobit.com/help/ScptUtl/pa33.htm),但我没有信心。
    • 您好,谢谢参考,不知道。我的 cmets 基于过去几年使用 Apache 2.2、IE 和 Firefox 的经验。很高兴听到有关 Chrome 的消息,我有一段时间没有测试它了。 Flash 也可能对您没有帮助,相对于如此大的文件,您必须以相当小的部分发送数据,并且事情变得更慢。除非您使用他们的客户端软件,否则我所知道的所有商业服务都不支持大于 2GB 的容量。有了正确的标头信息,我看不出 Apache 无法处理这些文件的任何原因。这是浏览器的障碍。
    【解决方案3】:

    如果您希望上传这些大小的文件,我不会依赖直接的浏览器上传。我建议您使用 Java 小程序或什至可能是 Flash 文件(不确定是否可能,不是 Flash 人),因此您可以将文件分成块。如果上传中断,您可以从上次中断的地方继续。

    【讨论】:

    • 我知道它不可靠,但是这种大小的请求较少,所以如果我至少可以处理这样的请求,那就太好了。
    【解决方案4】:
    Jsp code :
    <script src="../lib/app/configurator.data.ajax.js" type="text/javascript"></script>
    <script src="../lib/ui/jquery.fileupload.js"></script>
    <html>
    
    <script language="Javascript">
    var varb = '';
    var test = 0;
    var count = 1;
    $(function () {
    var maxChunkSize = 30000000; //SET CHUNK SIZE HERE
    var your_global_var_for_form_submit = '';
    
    var params = {
            year: threeDSelectedYear,
            series: threeDSelectedSeries
    };
    /*File upload bind with form, 'fileupload' is my form id. As sumit triggers
        for file ulaod will submit my form*/
    /* replaceFileInput: true, */
    $('#fileupload').fileupload({
    maxChunkSize: maxChunkSize,
    url: efccustom.getEfcContext()+'upload/uploadZip?year='+threeDSelectedYear+'&series='+threeDSelectedSeries,             //URL WHERE FILE TO BE UPLOADED
        error: function (jqXHR, textStatus, errorThrown) {
        // Called for each failed chunk upload
            $(".fileupload-loading").html("");
             $('.ANALYZE_DIALOG').dialog("close");       
        },
    
        success: function (data, textStatus, jqXHR) {
        /*This event will be called on success of upload*/
        count = parseInt($('#counter').val()) + 1;
        $('#counter').val(count);
    
        $('#ttk').val(count);
        data.ttk = 7;
        console.log(" count ",count , data);
        },
    
        submit: function (e, data) {
        /*This event will be called on submit here i am
                         adding variable to form*/
        //console.log($('#zip_uploaded_file').val());      
    
        //console.log(data.originalFiles[0].name);            
        test = data.originalFiles[0];
        $('#fname').val(data.originalFiles[0].name);
        $('#trequests').val(Math.ceil(data.originalFiles[0].size/maxChunkSize));
        $('#counter').val('1');
        },
    
        progress: function (e, data) {
        /*PROGRESS BAR CODE WILL BE HERE */
            $(".fileupload-loading").html('<img src="../public/themeroller/images/throbber.gif" alt="Uploading Please Wait..." title="Uploading Please Wait...." />');       
        },
    
        add: function (e, data) {
        $('.browsedFileName').html(data.originalFiles[0].name);
        your_global_var_for_form_submit = data;
        },
    
        done: function (e, data) {
    
            ajaxcall.Data._get('upload/extractZipNCreateJson',params,function(data2) {
                alert("file upload success ");
                 $(".fileupload-loading").html("");
                 $('.ANALYZE_DIALOG').dialog("close");
            });
    
    
        }
    
    });
    /*This is my button click event on which i am submitting my form*/
      $('#button').click(function(){
        your_global_var_for_form_submit.submit();
      });
    });
    </script>
    
    <html>
    
    <body>
    
    
    <form id="fileupload" enctype="multipart/form-data"> 
    <div class="row fileupload-buttonbar">
    <div class="span7">
    <!--<input type="file" name="files" id="file" /> -->
    
    <input type="file" id="zip_uploaded_file"  name="zip_uploaded_file"  />
    <input type="hidden" name="counter" id="counter" value="1" />
    <input type="hidden" name="fname" id="fname" value="" />
    <input type="hidden" name="trequests" id="trequests" value="1" />
    
    <input type="hidden" name="ttk" id="ttk" value="1" />
    <input type="button" id="button" name="button" value="submit" />
     <span class='browsedFileName'></span>
    </div>
    </div>
    <!-- The loading indicator is shown during file processing -->
    <div class="fileupload-loading"></div>
    </form>
    </body>
    
    
    Controller COde :
    @RequestMapping(value = "/uploadZip", method = RequestMethod.POST, consumes = "multipart/form-data")
        @ResponseBody
        public ResponseEntity<String>
         uploadZip(HttpServletRequest request, HttpServletResponse response)
                throws IOException, IllegalArgumentException {
            try {       
            String year = request.getParameter("year");
            String series = request.getParameter("series");
            log.info(" year " + year + " series " + series);
            boolean isMultipart = ServletFileUpload.isMultipartContent(request);
            if (isMultipart) {
    
                FileItemFactory factory = new DiskFileItemFactory();
                ServletFileUpload upload = new ServletFileUpload(factory);
                List items = upload.parseRequest(request);
                Iterator iterator = items.iterator();
    
                HttpSession session = request.getSession();
                UserContext userContext = (UserContext) session
                        .getAttribute(ApplicationConstant.USER_CONTEXT);
                String userName = userContext.getUser();
                String workSpaceInUse = userContext.getCurrentWorkSpace();           
                FileItem item = null;
                boolean fileNotExistFlag;
                String fileExtension;
                while (iterator.hasNext()) {
                    item = (FileItem) iterator.next();
    
                    String content = item.getContentType();
                    log.info(" content "+content);
                    log.info(" File Type Getting Uploaded :"+content);
                    if (!item.isFormField()) {
                /* Here in IOUtils the Third Parameter true tells that the small chunks of data that comes need to be added to the same File */
                IOUtils.copy(fileItem.getInputStream(), new FileOutputStream(new File(threeDPath+"/"+year+"/"+series+"/"+uploadZipFileName),true));               
                    }
                }
                return null;
            }   
            }
            catch(Exception e) {
                return handleError(new RuntimeException("Unexpected error while uploading ZIP", e));
            }
            return null;
        }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-06-30
      • 1970-01-01
      • 2021-08-16
      • 1970-01-01
      • 1970-01-01
      • 2014-12-03
      • 2021-07-30
      • 1970-01-01
      相关资源
      最近更新 更多