一、原理
自动配置原理
文件上传自动配置类-MultipartAutoConfiguration-MultipartProperties
- 自动配置好了 StandardServletMultipartResolver 【文件上传解析器】
- 原理步骤
- 1、请求进来使用文件上传解析器判断(isMultipart)并封装(resolveMultipart,返回MultipartHttpServletRequest)文件上传请求
- 2、参数解析器来解析请求中的文件内容封装成MultipartFile
- 3、将request中文件信息封装为一个Map;MultiValueMap<String, MultipartFile>
FileCopyUtils。实现文件流的拷贝
二、使用篇
表单
文件上传:form中一定要加 enctype="multipart/form-data"表示文件上传
多文件上传 一定要在input中加multiple
如:input type="file" id="exampleInputFile1" name="images" multiple> 表示多文件上传
<header class="panel-heading">
文件上传
</header>
<div class="panel-body">
<form role="form" enctype="multipart/form-data" method="post" th:action="@{/multipart}">
<div class="form-group">
<label for="exampleInputEmail1">用户名</label>
<input type="email" class="form-control" name="username" id="exampleInputEmail1" placeholder="Enter email">
</div>
<div class="form-group">
<label for="exampleInputPassword1">密码</label>
<input type="password" name="password" class="form-control" id="exampleInputPassword1" placeholder="Password">
</div>
<div class="form-group">
<label for="exampleInputFile">最喜欢的图片</label>
<input type="file" id="exampleInputFile" name="img">
</div>
<div class="form-group">
<label for="exampleInputFile1">最喜欢的图片</label>
<input type="file" id="exampleInputFile1" name="images" multiple>
</div>
<div class="checkbox">
<label>
<input type="checkbox"> Check me out
</label>
</div>
<button type="submit" class="btn btn-primary">Submit</button>
</form>
设置控制器进行文件上传
package com.example.controller;
import lombok.extern.slf4j.Slf4j;
import org.springframework.http.HttpRequest;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RequestPart;
import org.springframework.web.multipart.MultipartFile;
import javax.servlet.ServletRequest;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpSession;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.net.URI;
import java.util.UUID;
/**
* @author 谭铖
* 文件上传
*/
@Slf4j
@Controller
public class multipartFile {
@GetMapping("/form_layouts")
public String flot_chart(){
return "MultipartFile/form_layouts";
}
@PostMapping("/multipart")
public String multipart(@RequestParam(value = "username",required = false) String username,
@RequestParam(value = "password",required = false) String password,
@RequestPart("img") MultipartFile img,
@RequestPart("images") MultipartFile [] images,
HttpServletRequest request,
HttpSession session) throws IOException {
log.info("上传的信息:username={},password={} ,Img={},photos={}"
,username,password,img.getSize(),images.length);
// String path = request.getSession().getServletContext().getRealPath("/upload/");
// System.out.println(path);
判断该路径是否存在
// File file = new File(path);
// // 若不存在则创建该文件夹
// if(!file.exists()){
// file.mkdirs();
// }
if (!img.isEmpty()) {
String originalFilename = img.getOriginalFilename();
img.transferTo(new File("D:\\"+originalFilename));
}
if (images.length > 0) {
for (MultipartFile mult:images
) {
String originalFilename1 = mult.getOriginalFilename();
mult.transferTo(new File("D:\\"+originalFilename1));
}
}
log.info(request.getRequestURI());
return "index";
}
}
即可实现文件上传因为springboot都是auto配置好的非常方便
当然如果你要设置你的文件大小配置可以修改application.properties文件
#单个文件最大限制
spring.servlet.multipart.max-file-size=100MB
#提交的全部文件最大限制
spring.servlet.multipart.max-request-size=100MB
为什么能修改呢我们看源码上传配置文件写了
然后看源码中配置好好多默认设置因为自动配置我就可以在配置文件中调用spring.servlet.multipart修改他的配置进行操作了
/*
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springframework.boot.autoconfigure.web.servlet;
import javax.servlet.MultipartConfigElement;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.context.properties.PropertyMapper;
import org.springframework.boot.web.servlet.MultipartConfigFactory;
import org.springframework.util.unit.DataSize;
/**
* Properties to be used in configuring a {@link MultipartConfigElement}.
* <ul>
* <li>{@link #getLocation() location} specifies the directory where uploaded files will
* be stored. When not specified, a temporary directory will be used.</li>
* <li>{@link #getMaxFileSize() max-file-size} specifies the maximum size permitted for
* uploaded files. The default is 1MB</li>
* <li>{@link #getMaxRequestSize() max-request-size} specifies the maximum size allowed
* for {@literal multipart/form-data} requests. The default is 10MB.</li>
* <li>{@link #getFileSizeThreshold() file-size-threshold} specifies the size threshold
* after which files will be written to disk. The default is 0.</li>
* </ul>
* <p>
* These properties are ultimately passed to {@link MultipartConfigFactory} which means
* you may specify numeric values using {@literal long} values or using more readable
* {@link DataSize} variants.
*
* @author Josh Long
* @author Toshiaki Maki
* @author Stephane Nicoll
* @since 2.0.0
*/
@ConfigurationProperties(prefix = "spring.servlet.multipart", ignoreUnknownFields = false)
public class MultipartProperties {
/**
* Whether to enable support of multipart uploads.
*/
private boolean enabled = true;
/**
* Intermediate location of uploaded files.
*/
private String location;
/**
* Max file size.
*/
private DataSize maxFileSize = DataSize.ofMegabytes(1);
/**
* Max request size.
*/
private DataSize maxRequestSize = DataSize.ofMegabytes(10);
/**
* Threshold after which files are written to disk.
*/
private DataSize fileSizeThreshold = DataSize.ofBytes(0);
/**
* Whether to resolve the multipart request lazily at the time of file or parameter
* access.
*/
private boolean resolveLazily = false;
public boolean getEnabled() {
return this.enabled;
}
public void setEnabled(boolean enabled) {
this.enabled = enabled;
}
public String getLocation() {
return this.location;
}
public void setLocation(String location) {
this.location = location;
}
public DataSize getMaxFileSize() {
return this.maxFileSize;
}
public void setMaxFileSize(DataSize maxFileSize) {
this.maxFileSize = maxFileSize;
}
public DataSize getMaxRequestSize() {
return this.maxRequestSize;
}
public void setMaxRequestSize(DataSize maxRequestSize) {
this.maxRequestSize = maxRequestSize;
}
public DataSize getFileSizeThreshold() {
return this.fileSizeThreshold;
}
public void setFileSizeThreshold(DataSize fileSizeThreshold) {
this.fileSizeThreshold = fileSizeThreshold;
}
public boolean isResolveLazily() {
return this.resolveLazily;
}
public void setResolveLazily(boolean resolveLazily) {
this.resolveLazily = resolveLazily;
}
/**
* Create a new {@link MultipartConfigElement} using the properties.
* @return a new {@link MultipartConfigElement} configured using there properties
*/
public MultipartConfigElement createMultipartConfig() {
MultipartConfigFactory factory = new MultipartConfigFactory();
PropertyMapper map = PropertyMapper.get().alwaysApplyingWhenNonNull();
map.from(this.fileSizeThreshold).to(factory::setFileSizeThreshold);
map.from(this.location).whenHasText().to(factory::setLocation);
map.from(this.maxRequestSize).to(factory::setMaxRequestSize);
map.from(this.maxFileSize).to(factory::setMaxFileSize);
return factory.createMultipartConfig();
}
}
好了这样就实现了多文件上传