记一次上传文件保存被File.getParentFile().exists()和MultipartFile.transferTo()联坑的异常问题

  最近搞项目需要实现将前端文件上传至后台服务器保存起来的功能,很轻松的将之前的代码复制黏贴一份,本以为就此完成,结果调试时,被坑残了。

  后台上传文件功能用的是MultipartFile来接收前端的文件,大概方法简写如下:

void uploadFile(MultipartFile uploadFile) throws Exception {
    if(uploadFile!=null && uploadFile.getSize()>0){
        String path = "/var/uploadFiles";
        // 文件原名
        String fileName = uploadFile.getOriginalFilename();
        // 文件后缀
        String suffix = fileName.substring(fileName.lastIndexOf(".") + 1);
        // FTP存放名
        String realFileName = (new Date()).getTime().concat(".").concat(suffix);
        File file = new File(path, realFileName);
        if(file.getParentFile().exists()) {
            file.getParentFile().mkdirs();
        }
        // 存入临时文件
        uploadFile.transferTo(file);
    }            
}

  这串上传代码看着没什么问题,唯一的问题就是path用的是相对路径的写法,但这种写法在Windosws中其实也是允许的。然而,就是这种相对目录的写法,在配合file.getParentFile().exists()和MultipartFile.transferTo()把我坑惨了,除了第一次运行以外其他每次运行时file.getParentFile().exists()都是返回true,而向下运行uploadFile.transferTo(file);时,却每次都报找不到文件路径异常,简直一脸懵逼,一个getParentFile().exists()说父级目录存在,一个uploadFile.transferTo(file)又提示异常说目录不存在,十分诡异,没法子,只能网上找答案了,找了一会才由这篇博客https://blog.csdn.net/lcczpp/article/details/88887045中找到问题,原因如下:

   file.getParentFile().mkdirs()对于相对目录,默认采用当前程序运行所在盘符(我运行的时候在D:盘),而MultipartFile.transferTo()对于相对目录,默认采用temp目录(temp目录在C:盘)为父目录,所以,file.getParentFile().mkdirs()根据我提供的相对目录在D:盘创建了父级目录,而MultipartFile.transferTo()则将文件传入到C:盘,但C:盘不存在这个父级目录所以异常报错,找到问题了,剩下的解决方案,博客中也说了,使用new File(path).getAbsolutePath()就可以。

  so,问题解决,最后总结一下,当使用MultipartFile.transferTo(File)方法时,传入的File不能直接使用,而应该转一道MultipartFile.transferTo(File.getAbsoluteFile())再用。下面给出修改后的代码:

void uploadFile(MultipartFile uploadFile) throws Exception {
    if(uploadFile!=null && uploadFile.getSize()>0){
        String path = "/var/uploadFiles";
        // 文件原名
        String fileName = uploadFile.getOriginalFilename();
        // 文件后缀
        String suffix = fileName.substring(fileName.lastIndexOf(".") + 1);
        // FTP存放名
        String realFileName = (new Date()).getTime().concat(".").concat(suffix);
        File file = new File(path, realFileName);
        if(file.getParentFile().exists()) {
            file.getParentFile().mkdirs();
        }
        // 存入临时文件  修改file为file.getAbsoluteFile()
        uploadFile.transferTo(file.getAbsoluteFile());
    }            
}
原文地址:https://www.cnblogs.com/lovelyli/p/13731095.html