LIYUANWAI的gravatar头像
LIYUANWAI 2018-12-07 20:19:44

关于springmvc下载大的文件(2G)爆出 溢出 请求帮助

问题描述

客户提出部分地方的资料上传需达到2G的效果,好不容易把内存调大了 结果下载的爆出一下问题  百度了一番说是一次性读取不了多的数据,只能是片面的取出来。

关于springmvc下载大的文件(2G)爆出 溢出 请求帮助

 org.springframework.web.util.NestedServletException: Handler processing failed; nested exception is java.lang.OutOfMemoryError: Java heap space

at org.springframework.web.servlet.DispatcherServlet.triggerAfterCompletionWithError(DispatcherServlet.java:1302)

at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:977)

at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:893)

at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:965)

at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:856)

at javax.servlet.http.HttpServlet.service(HttpServlet.java:617)

at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:841)

at javax.servlet.http.HttpServlet.service(HttpServlet.java:723)

at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)

at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)

at com.opensymphony.sitemesh.webapp.SiteMeshFilter.obtainContent(SiteMeshFilter.java:129)

at com.opensymphony.sitemesh.webapp.SiteMeshFilter.doFilter(SiteMeshFilter.java:77)

at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)

at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)

at org.apache.shiro.web.servlet.ProxiedFilterChain.doFilter(ProxiedFilterChain.java:61)

at org.apache.shiro.web.servlet.AdviceFilter.executeChain(AdviceFilter.java:108)

at org.apache.shiro.web.servlet.AdviceFilter.doFilterInternal(AdviceFilter.java:137)

at org.apache.shiro.web.servlet.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:125)

at org.apache.shiro.web.servlet.ProxiedFilterChain.doFilter(ProxiedFilterChain.java:66)

at org.apache.shiro.web.servlet.AbstractShiroFilter.executeChain(AbstractShiroFilter.java:449)

at org.apache.shiro.web.servlet.AbstractShiroFilter$1.call(AbstractShiroFilter.java:365)

at org.apache.shiro.subject.support.SubjectCallable.doCall(SubjectCallable.java:90)

at org.apache.shiro.subject.support.SubjectCallable.call(SubjectCallable.java:83)

at org.apache.shiro.subject.support.DelegatingSubject.execute(DelegatingSubject.java:383)

at org.apache.shiro.web.servlet.AbstractShiroFilter.doFilterInternal(AbstractShiroFilter.java:362)

at org.apache.shiro.web.servlet.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:125)

at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:344)

at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:261)

at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)

at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)

at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:85)

at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)

at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235)

at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)

at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)

at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)

at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127)

at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:103)

at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:615)

at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)

at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:293)

at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:861)

at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:620)

at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489)

at java.lang.Thread.run(Unknown Source)

 

运行环境

jdk7+tomcat7+mysql+eclipse IDEA+maven

项目技术(必填)

spring+spring mvc+mybatis+bootstrap+jquery

项目截图(必填)

 

运行截图(必填)

 

相关代码片段

//上传资料

public String fileUpload(@RequestParam("file") MultipartFile file, OpaPlanTask opaPlanTask,

HttpServletRequest request,RedirectAttributes redirectAttributes, Model model) {

String itemParentId ="0";

// 获得原始文件名

String fileName = file.getOriginalFilename();

//获取文件后缀

String sufFix = fileName.substring(fileName.lastIndexOf(".") + 1).toLowerCase();

System.out.println("原始文件名:" + fileName);

System.out.println("原始文件后缀名:" + sufFix);

        //临时路径

String basePath = Global.getConfig("upload.attachedBasePath");

StringBuffer fileNameSB = new StringBuffer();

StringBuffer filePathSB = new StringBuffer();

String attachedPath = new String();

String path = new String();

if (!file.isEmpty()) {

try {

if (!Global.getConfig("upload.fileType").contains(sufFix)) {

addMessage(model, "文件上传格式不正确,多个文件请压缩后上传");

return "modules/opa/opaPlanTaskExcuteInputScore";

}

OpaScheme opaScheme = opaSchemeService.get(opaPlanTask.getPlanId());

String opaSchemeName=opaScheme.getName();

//信息录入

String officeName = UserUtils.getUser().getOffice().getName();

path = filePathSB.append(basePath).append(DateUtils.getYear()).append("/").append(opaSchemeName).append("/")

.append(officeName).append("/").toString();

fileName = fileNameSB.append(opaPlanTask.getName()).append(".").append(sufFix).toString();

attachedPath = filePathSB.append(fileName).toString();

File dir = new File(path, fileName);

if (!dir.exists())

dir.mkdirs();

// MultipartFile自带的解析方法

file.transferTo(dir);

} catch (Exception e) {

e.printStackTrace();

}

} else {

addMessage(model, "请选择文件");

return "modules/opa/opaPlanTaskExcuteInputScore";

}

System.out.println("上传文件到:" + attachedPath);

opaPlanTask.setId(request.getParameter("id"));

System.out.println("id="+request.getParameter("id"));

opaPlanTask.setAttachedPath(attachedPath);

opaPlanTask.setStatus(DictUtils.getDictValue("待改动", "opa_planTask_status", ""));

opaPlanTaskDao.update(opaPlanTask);

opaPlanTaskService.save(opaPlanTask);

model.addAttribute("opaPlanTask", opaPlanTask);

addMessage(model, "文件上传成功");

return "modules/opa/opaPlanTaskExcuteInputScore";

}

注意事项

所有回答列表(3)
sourcezero的gravatar头像
sourcezero  LV5 2018年12月24日

看你代码是一次性读取文件,这读取,文件小还好,太大就挂了;一般都是缓存来一片一片读取的哦

 try {   
   File file = new File(session.getServletContext().getRealPath("/")+"attachment/"+filename);
             if (file.exists()) {   
                String dfileName = file.getName();   
                InputStream fis = new BufferedInputStream(new FileInputStream( file));   
                 response.reset();   
                 response.setContentType("application/x-download");
                 response.addHeader("Content-Disposition","attachment;filename="+ new String(dfileName.getBytes(),"iso-8859-1"));
                 response.addHeader("Content-Length", "" + file.length());   
                OutputStream toClient = new BufferedOutputStream(response.getOutputStream());   
               response.setContentType("application/octet-stream");   
                 byte[] buffer = new byte[1024 * 1024 * 4]; //使用缓存慢慢读取,支持大文件下载
                 int i = -1;   
                 while ((i = fis.read(buffer)) != -1) {   
                     toClient.write(buffer, 0, i);  
                 }   
                 fis.close();   
                 toClient.flush();   
                 toClient.close();   
                 try {
                 response.wait();
           } catch (InterruptedException e) {
            e.printStackTrace();
           }  
             } else {   
                PrintWriter out = response.getWriter();   
                out.print("<script>");   
                out.print("alert(\"未找到文件\")");   
                out.print("</script>");   
             }   
         } catch (IOException ex) {   
            PrintWriter out = response.getWriter();   
                out.print("<script>");   
                out.print("alert(\"未找到文件\")");   
                out.print("</script>");   
         }

 

评论(0) 最佳答案
月之氏族的gravatar头像
月之氏族  LV23 2018年12月8日

只有切片了,一般上传大文件的都是切片,把一个文件切成 1M 一片的 , 然后上传,可做断点续传,而且一般大的文件还要验证MD5 , 做秒传

yy1124218793的gravatar头像
yy1124218793  LV9 2018年12月13日

使用腾讯云 阿里云对象存储

顶部 客服 微信二维码 底部
>扫描二维码关注最代码为好友扫描二维码关注最代码为好友