SpringMVC接收图片
图片的上传
form表单上传
<form action="/user/upload/file" method="post" enctype="multipart/form-data">
<input type="file" name="img" />
<input type="submit" />
</form>
jquery.form.js提供的ajax上传
function updateFile() {
$('#file').ajaxSubmit({
url: url,
type: 'POST',
//contentType: false,
xhrFields: {
withCredentials: true
},
crossDomain: true,
success: function (result) {
},
error: function (result) {
}
});
}
Base64格式上传
有些APP插件会这么干,这里就不写了。
SpringMVC接收
MultipartFile接收
SpringMVC
提供的org.springframework.web.multipart.MultipartFile
很强大,接收file
只需要@RequestParam(value = "img") MultipartFile file
就可以了,MultipartFile
还提供的几个很好用的API:
- 获取文件类型getContentType()
- 获取文件大小getSize()
- 保存文件transferTo(java.io.File file)
接收、校验和保存:
@Controller
@RequestMapping("/user")
public class UserController extends BaseController {
private static Logger logger = LoggerFactory.getLogger(UserController.class);
@Value(value = "${image.path:./img}")
private String imagePath;
@Value(value = "${image.host:http://localhost}")
private String imageHost;
@RequestMapping(value = "/upload/file", method = RequestMethod.POST)
@ResponseBody
public Result<String> saveFile(@RequestParam(value = "img") MultipartFile file) {
StringBuffer fileName = new StringBuffer();
fileName.append(UUID.randomUUID().toString().replaceAll("-", ""));
String type = file.getContentType();
if ("image/png".equals(type)) {
fileName.append(".png");
} else if ("image/jpeg".equals(type)) {
fileName.append(".jpeg");
} else if ("image/gif".equals(type)) {
fileName.append(".gif");
} else {
return new Result.Builder<String>()
.code(-1)
.msg("请选择.png.jpg格式的图片")
.build();
}
if (file.getSize() > 1024000L) {
return new Result.Builder<String>()
.code(-1)
.msg("图片超过1Mb")
.build();
}
try {
file.transferTo(new File(imagePath, fileName.toString()));
return new Result.Builder<String>()
.code(0)
.msg("成功")
.data(imageHost + fileName.toString())
.build();
} catch (IOException e) {
e.printStackTrace();
return new Result.Builder<String>()
.code(-1)
.msg("保存失败")
.build();
}
}
}
Base64字符串接收
@RequestMapping(value = "/upload/base64", method = RequestMethod.POST)
@ResponseBody
public Result<String> saveBase64(@RequestParam(value = "img") String base64Str) {
StringBuffer fileName = new StringBuffer();
fileName.append(UUID.randomUUID().toString().replaceAll("-", ""));
if (StringUtils.isBlank(base64Str)) {
return new Result.Builder<String>()
.code(-1)
.msg("file不可缺省")
.build();
} else if (base64Str.indexOf("data:image/png;") != -1) {
base64Str = base64Str.replace("data:image/png;base64,", "");
fileName.append(".png");
} else if (base64Str.indexOf("data:image/jpeg;") != -1) {
base64Str = base64Str.replace("data:image/jpeg;base64,", "");
fileName.append(".jpeg");
} else {
return new Result.Builder<String>()
.code(-1)
.msg("请选择.png.jpg格式的图片")
.build();
}
File file = new File(imagePath, fileName.toString());
byte[] fileBytes = Base64.getDecoder().decode(base64Str);
try {
FileUtils.writeByteArrayToFile(file, fileBytes);
} catch (IOException e) {
e.printStackTrace();
return new Result.Builder<String>()
.code(-1)
.msg("保存失败")
.build();
}
return new Result.Builder<String>()
.code(0)
.msg("成功")
.data(imageHost + fileName.toString())
.build();
}
为了避免文件重名、Linux文件系统与Windows文件系统差异等因素会引起的异常,我通常使用UUID重命名后再保存。
nginx配置
上面代码中的image.path
是文件的保存路径, image.host
是提供给前端的访问方式,具体配置要结合nginx
代理的配置:
server {
listen 80 default_server;
listen [::]:80 default_server;
root /data/www;
……
}
这是一个本地测试环境的配置,仅供参考。image.path
配置为/data/www/img/
,image.host
配置为http://localhost/img/
,这样,图片文件会存储在/data/www/img/
,http访问img/test.jpeg
时,nginx
就会响应这张图片。