我在Spring中使用CommonsMultipartResolver库上传10 MB大小的csv文件时出错。我在xml文件中完成了以下设置 Xml文件配置:
<beans:bean id="multipartResolver"
class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<!-- max upload size in bytes -->
<beans:property name="maxUploadSize" value="99971520" /> <!-- 99MB -->
<!-- max size of file in memory (in bytes) -->
<beans:property name="maxInMemorySize" value="1048576" /> <!-- 1MB -->
控制器代码:
@RequestMapping(value="/uploadForm",method = RequestMethod.POST)
public @ResponseBody String uploadForm1(@ModelAttribute("admin") BillingAndRecon billingandrecon,@RequestParam String id,BindingResult result,Principal principal,@RequestParam MultipartFile file,HttpSession session) throws ServiceException, DaoException, IllegalStateException, IOException {
File uploadFile = null;
String msg = "";
if (!file.getOriginalFilename().equals("")) {
logger.info("Before Multipart file get path >> ");
BillingAndReconServiceImpl asi = (BillingAndReconServiceImpl) this.billingAndReconService;// not correct!!
String uploadDirectoryPath = asi.getUploadDirectoryPath(); // not correct!!
uploadFile = new File( uploadDirectoryPath + file.getOriginalFilename());
logger.info("Before Multipart file get path uploadDirectoryPath >> "+uploadDirectoryPath);
file.transferTo(uploadFile);
}
}
表单页面:
<form:form action="./uploadForm" method="post" enctype="multipart/form-data" ModelAttribute=="admin">
<input type="file" name="file" />
<input type="text" name="id" />
</form:form>
但我不明白什么是问题。我尝试设置大小并设置标题enctype="multipart/form-data"
,但尚未解决。
以下是错误:
org.springframework.web.multipart.MultipartException: Could not parse multipart servlet request; nested exception is org.apache.commons.fileupload.FileUploadException: the request was rejected because no multipart boundary was found] with root cause org.apache.commons.fileupload.FileUploadException: the request was rejected because no multipart boundary was found
at org.apache.commons.fileupload.FileUploadBase$FileItemIteratorImpl.<init>(FileUploadBase.java:954)
at org.apache.commons.fileupload.FileUploadBase.getItemIterator(FileUploadBase.java:331)
at org.apache.commons.fileupload.FileUploadBase.parseRequest(FileUploadBase.java:351)
at org.apache.commons.fileupload.servlet.ServletFileUpload.parseRequest(ServletFileUpload.java:126)
at org.springframework.web.multipart.commons.CommonsMultipartResolver.parseRequest(CommonsMultipartResolver.java:156)
at org.springframework.web.multipart.commons.CommonsMultipartResolver.resolveMultipart(CommonsMultipartResolver.java:139)
at org.springframework.web.servlet.DispatcherServlet.checkMultipart(DispatcherServlet.java:1047)
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:892)
at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:856)
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:920)
at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:827)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:647)
at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:801)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:728)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:305)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:222)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:123)
at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:502)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:99)
at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:953)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408)
at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1023)
at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:589)
at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:310)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
at java.lang.Thread.run(Thread.java:744)
答案 0 :(得分:2)
在评论中要求 @ChristianMaioliM ,添加了更多详细信息 您的代码中的问题是不遵循模型对象的BindingResult参数。
错误或BindingResult参数必须遵循立即绑定的模型对象,因为方法签名可能有多个模型对象,Spring将为每个模型对象创建一个单独的BindingResult实例,因此以下示例将不起作用
参考文档Invalid ordering of BindingResult and @ModelAttribute
要解决此问题,请更改控制器方法处理程序签名,以遵循BindingResult和&amp;之间的参数排序。模型对象如:
发件人:强>
@RequestMapping(value="/uploadForm",method = RequestMethod.POST)
public @ResponseBody String uploadForm1(@ModelAttribute("admin") BillingAndRecon billingandrecon,@RequestParam String id,BindingResult result,Principal principal,@RequestParam MultipartFile file,HttpSession session) throws ServiceException, DaoException, IllegalStateException, IOException {
要强>
@RequestMapping(value="/uploadForm",method = RequestMethod.POST)
public String uploadForm1(
@ModelAttribute("admin") BillingAndRecon billingandrecon,
BindingResult result,
Principal principal,
HttpSession session) throws ServiceException, DaoException, IllegalStateException, IOException {
//do file save here
return "some-view-name";
}
并在BillingAndRecon类中添加mulitpart / binding字段,如:
public class BillingAndRecon {
private MultipartFile file;
private String id;
no-arg constructor;
getters;
setters;
}
注意: BindingResult参数应该在@ModelAttrubiute/@RequestBody
之后立即
和jsp形式:
<form:form action="${pageContext.request.contextPath}/uploadForm"
method="post"
enctype="multipart/form-data"
modelAttribute="admin">
<input type="file" name="file" />
<form:input path="id" />
</form:form>
并且不要忘记在GET处理程序中添加绑定实例,如:
@RequestMapping(value="/uploadForm",method = RequestMethod.GET)
public String uploadFormView(Model model){
model.addAttribute("admin", new BillingAndRecon());
return "your-upload-view-name";
}
答案 1 :(得分:0)
org.springframework.web.multipart.MultipartException:无法解析多部分servlet请求;嵌套异常是java.io.IOException:org.apache.tomcat.util.http.fileupload.FileUploadException:流已关闭
在Spring Boot 2.1.12上工作正常,升级到2.2.4后失败(两个版本都运行相同的嵌入式Tomcat 9.0.30)。
根本原因是我们使用了记录请求和响应的logback-access过滤器。过滤器使用缓存包装器包装HttpServletRequest,并在沿过滤器链传递请求之前关闭了输入流。当调用javax.servlet.http.HttpServletRequest#getParts时,这引起了一个问题,因为该调用被委托给原始Tomcat的请求(具有现在关闭的输入流),然后导致“流关闭”异常。 >
引发此问题的Spring更改是hiddenHttpMethodFilter,它不再出现在过滤器链中。以前,此过滤器将是第一个被调用的过滤器,它将调用HttpServletRequest#getParameter,这将使Tomcat的请求实现解析多部分内容并将这些部分存储在对象中(以便以后对#getParts的调用将使用而不尝试再次解析它们。
我将此报告给Logback:https://jira.qos.ch/browse/LOGBACK-1503
解决方法-在将请求传递到logback的过滤器之前调用HttpServletRequest#getParameter(有关代码,请参阅LOGBACK-1503),以强制Tomcat在输入流仍处于打开状态时解析和存储请求部分。