springboot项目,一直运行很稳定,刚线上遇到一个文件上传报错的问题,虽然我解决的比较快,但是坑有点大,不熟悉的朋友可能还是得费些功夫,还是记录下吧。
出了问题首先看错误日志,报错信息如下:
Could not parse multipart servlet request; nested exception is java.io.IOException: The temporary upload loca
tion [/tmp/tomcat.4981350991684545020.8088/work/Tomcat/localhost/ROOT] is not valid
org.springframework.web.multipart.MultipartException: Could not parse multipart servlet request; nested exception is java.io.IOException: The temporary upload location [/tmp/tomcat.4981350991684545020.8088/work/Tomcat/localhost/ROOT] is not valid
=======================================
从上面可以看出,导致报错的具体原因在于找不到/tmp/tomcat**这个目录,于是直接百度搜索红色部分,看到很多解决方案,也找到了罪魁祸首,springboot默认会将上传的临时文件存放在/tmp/tomcat**这个目录,而在centos操作系统下,对于/tmp目录有个定时清理的cron,默认会清理10天内没有访问过的文件,于是这个目录一旦被删就会引发问题,这里总结下解决方案(方案三最快、最实用):
推荐先用方案三临时解决问题,再用方案二或者方案四 永久解决
1、重启应用(临时方案)
2、修改springboot文件上传的配置方式,把临时存放路径修改掉,再重启应用(永久方案)
@Configuration public class MultipartConfig{ /** *文件临时上传路径 */ @Bean MultipartConfigElement multipartConfigElement() { MultipartConfigFactory mcf = new MultipartConfigFactory(); String location = System.getProperty("user.dir") +"/data/xx";//自定义临时文件路径 File tmpFile = new File(location); if(!tmpFile.exists()){ tmpFile.mkdirs(); } Factory.setLocation(location); return mcf.createMultipartConfig(); } }
3、完整新建这个目录,mkdir -p /tmp/tomcat.4981350991684545020.8088/work/Tomcat/localhost/ROOT (用运行springboot项目的用户来建,没权限可以先用root,再修改归属)(临时方案)
4、在做完方案三后,去修改centos系统对/tmp目录的清理方案,centos6下面是修改/etc/cron.daily/tmpwatch 文件,找到
/usr/sbin/tmpwatch "$flags" -x /tmp/.X11-unix -x /tmp/.XIM-unix \
-x /tmp/.font-unix -x /tmp/.ICE-unix -x /tmp/.Test-unix \
-X '/tmp/hsperfdata_*' -X '/tmp/.hdb*lock' -X '/tmp/.sapstartsrv*.log' \
-X '/tmp/pymp-*' -X '/tmp/tomcat*' 10d /tmp 这行,追加红色部分,定期清理忽略/tmp/tomcat*目录;
centos7下是修改/usr/lib/tmpfiles.d/tmp.conf 文件,找到
# Exclude namespace mountpoints created with PrivateTmp=yes
x /tmp/systemd-private-%b-*
X /tmp/systemd-private-%b-*/tmp
x /var/tmp/systemd-private-%b-*
X /var/tmp/systemd-private-%b-*/tmp
x /tmp/tomcat.*
追加红色部分即可