Spring MVC 将上传的 MultipartFile 保存到特定文件夹

Posted

技术标签:

【中文标题】Spring MVC 将上传的 MultipartFile 保存到特定文件夹【英文标题】:Spring MVC save uploaded MultipartFile to specific folder 【发布时间】:2012-06-06 13:26:17 【问题描述】:

我想将上传的图像保存到部署在 Tomcat 上的 Spring 3 MVC 应用程序中的特定文件夹中

我的问题是我无法将上传的图像文件保存到运行应用程序的主机。

这是我尝试过的:

private void saveFile(MultipartFile multipartFile, int id) throws Exception 
    String destination = "/images/" + id + "/"  + multipartFile.getOriginalFilename();
    File file = new File(destination);
    multipartFile.transferTo(file);

结果:FileNotFoundException - 是的,我确实想创建这个文件!?!

我尝试使用context.getRealPathgetResources("destination"),但没有任何成功。

如何在我的应用程序的特定文件夹中使用我的多部分文件的内容创建一个新文件?

【问题讨论】:

您在尝试 context.getRealPath 或 getResources("destination") 时遇到了哪些错误,请参阅 ***.com/questions/2970643/… 嗯,好的,谢谢,getRealPath 不起作用,因为如果应用程序被部署到一个 war 文件中并且没有被提取,它会返回 null!它在战争容器之外工作!但是有没有办法在战争中获取文件的路径? 我不会这么说的。将文件添加到已部署的战争中并没有真正意义。这是你想做的吗? 不,不是,但我读到有些网络服务器不提取war文件,所以我认为要使上述示例成为可能,必须有一种方法可以在该war目录中写入。因此 getRealPath 不是正确的方法,因为它会返回 null。幸运的是,它正在我的 tomcat 上运行,但只是为了让我的视野更加开阔,我想知道是否还有其他解决方案 FileNotFoundException 表示您没有文件夹 /images/id/,您应该先创建文件夹。 【参考方案1】:

此代码一定会对您有所帮助。

String filePath = request.getServletContext().getRealPath("/"); 
multipartFile.transferTo(new File(filePath));

【讨论】:

但不使用 http servlet 请求我们如何获取路径..? 方法有很多:可以使用request或者session获取真实路径。谢谢拉维。米【参考方案2】:

让我们在 webapp 中创建 uploads 目录并将文件保存在 webapp/uploads 中:

@RestController
public class GreetingController 

    private final static Logger log = LoggerFactory.getLogger(GreetingController.class);

    @Autowired
    private HttpServletRequest request;


    @RequestMapping(value = "/uploadfile", method = RequestMethod.POST)
        public
        @ResponseBody
        ResponseEntity handleFileUpload(@RequestParam("file") MultipartFile file) 
            if (!file.isEmpty()) 
                try 
                    String uploadsDir = "/uploads/";
                    String realPathtoUploads =  request.getServletContext().getRealPath(uploadsDir);
                    if(! new File(realPathtoUploads).exists())
                    
                        new File(realPathtoUploads).mkdir();
                    

                    log.info("realPathtoUploads = ", realPathtoUploads);


                    String orgName = file.getOriginalFilename();
                    String filePath = realPathtoUploads + orgName;
                    File dest = new File(filePath);
                    file.transferTo(dest);

代码String realPathtoUploads = request.getServletContext().getRealPath(uploadsDir);

如果我从 Idea IDE 运行应用程序,则返回下一条路径C:\Users\Iuliia\IdeaProjects\ENumbersBackend\src\main\webapp\uploads\

如果我制作 .war 并在 Tomcat 下运行它的下一个路径:D:\Programs_Files\apache-tomcat-8.0.27\webapps\enumbservice-0.2.0\uploads\

我的项目结构:

【讨论】:

最后一行代码'file.transferTo(dest);'给我 IO 异常,错误消息是“系统找不到指定的路径”。知道为什么会这样吗? @AND,您确定该路径存在于您的文件系统中吗?您需要首先(手动或以编程方式)创建目录。 这很有帮助。虽然它实际上与 Ravi 的答案相同,但这是一个更彻底的答案。这个答案在 Spring Boot 1.5.10 中仍然有效【参考方案3】:

您可以从 multipartfile 中获取 inputStream 并将其复制到您想要的任何目录。

public String write(MultipartFile file, String fileType) throws IOException 
    String date = LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyMMddHHmmss-"));
    String fileName = date + file.getOriginalFilename();
    
    // folderPath here is /sismed/temp/exames
    String folderPath = SismedConstants.TEMP_DIR + fileType;
    String filePath = folderPath + File.separator + fileName;
    
    // Copies Spring's multipartfile inputStream to /sismed/temp/exames (absolute path)
    Files.copy(file.getInputStream(), Paths.get(filePath), StandardCopyOption.REPLACE_EXISTING);
    return filePath;

这适用于 Linux 和 Windows。

【讨论】:

很好的例子。刚刚用 File.separator 替换了“/”【参考方案4】:

我看到了一个使用 xml 配置的 spring 3 示例(注意这不适用于 spring 4.2。*):http://www.devmanuals.com/tutorials/java/spring/spring3/mvc/spring3-mvc-upload-file.html `

<bean id="multipartResolver"
class="org.springframework.web.multipart.commons.CommonsMultipartResolver">
<property name="maxUploadSize" value="100000" />
<property name="uploadTempDir" ref="uploadDirResource" />
</bean>

<bean id="uploadDirResource" class="org.springframework.core.io.FileSystemResource">
<constructor-arg>
<value>C:/test111</value>
</constructor-arg>
</bean>

【讨论】:

【参考方案5】:
String ApplicationPath = 
        ContextLoader.getCurrentWebApplicationContext().getServletContext().getRealPath("");

这是在Spring中获取App真实路径的方法(不使用response, session ...)

【讨论】:

您不应该使用getRealPath() 来保存文件。请参阅this answer【参考方案6】:

以下在 ubuntu 上对我有用:

String filePath = request.getServletContext().getRealPath("/");
File f1 = new File(filePath+"/"+multipartFile.getOriginalFilename());
multipartFile.transferTo(f1);

【讨论】:

以上是关于Spring MVC 将上传的 MultipartFile 保存到特定文件夹的主要内容,如果未能解决你的问题,请参考以下文章

spring-mvc实现网页文件上传

form表单上传文件使用multipart请求处理

java之spring mvc之文件上传

Spring MVC文件上传

Spring MVC,文件上传

spring mvc(注解)上传文件的简单例子