您好,登錄后才能下訂單哦!
這篇文章主要介紹了如何解決MultipartFile.transferTo(dest) 報FileNotFoundExcep的問題,具有一定借鑒價值,感興趣的朋友可以參考下,希望大家閱讀完這篇文章之后大有收獲,下面讓小編帶著大家一起了解一下。
環境:
Springboot 2.0.4
JDK8
內嵌 Apache Tomcat/8.5.32
表單,enctype 和 input 的type=file 即可,例子使用單文件上傳
<form enctype="multipart/form-data" method="POST" action="/file/fileUpload"> 圖片<input type="file" name="file" /> <input type="submit" value="上傳" /> </form>
@Controller @RequestMapping("/file") public class UploadFileController { @Value("${file.upload.path}") private String path = "upload/"; @RequestMapping(value = "fileUpload", method = RequestMethod.POST) @ResponseBody public String fileUpload(@RequestParam("file") MultipartFile file) { if (file.isEmpty()) { return "false"; } String fileName = file.getOriginalFilename(); File dest = new File(path + "/" + fileName); if (!dest.getParentFile().exists()) { dest.getParentFile().mkdirs(); } try { file.transferTo(dest); // 保存文件 return "true"; } catch (Exception e) { e.printStackTrace(); return "false"; } } }
運行在保存文件 file.transferTo(dest) 報錯
dest 是相對路徑,指向 upload/doc20170816162034_001.jpg
file.transferTo 方法調用時,判斷如果是相對路徑,則使用temp目錄,為父目錄
因此,實際保存位置為 C:\Users\xxxx\AppData\Local\Temp\tomcat.372873030384525225.8080\work\Tomcat\localhost\ROOT\upload\doc20170816162034_001.jpg
一則,位置不對,二則沒有父目錄存在,因此產生上述錯誤。
transferTo 傳入參數 定義為絕對路徑
@Controller @RequestMapping("/file") public class UploadFileController { @Value("${file.upload.path}") private String path = "upload/"; @RequestMapping(value = "fileUpload", method = RequestMethod.POST) @ResponseBody public String fileUpload(@RequestParam("file") MultipartFile file) { if (file.isEmpty()) { return "false"; } String fileName = file.getOriginalFilename(); File dest = new File(new File(path).getAbsolutePath()+ "/" + fileName); if (!dest.getParentFile().exists()) { dest.getParentFile().mkdirs(); } try { file.transferTo(dest); // 保存文件 return "true"; } catch (Exception e) { e.printStackTrace(); return "false"; } } }
另外也可以 file.getBytes() 獲得字節數組,OutputStream.write(byte[] bytes)自己寫到輸出流中。
application.properties 中增加配置項
spring.servlet.multipart.location= # Intermediate location of uploaded files.
1、增加一個自定義的ResourceHandler把目錄公布出去
// 寫一個Java Config @Configuration public class webMvcConfig implements org.springframework.web.servlet.config.annotation.WebMvcConfigurer{ // 定義在application.properties @Value("${file.upload.path}") private String path = "upload/"; public void addResourceHandlers(ResourceHandlerRegistry registry) { String p = new File(path).getAbsolutePath() + File.separator;//取得在服務器中的絕對路徑 System.out.println("Mapping /upload/** from " + p); registry.addResourceHandler("/upload/**") // 外部訪問地址 .addResourceLocations("file:" + p)// springboot需要增加file協議前綴 .setCacheControl(CacheControl.maxAge(30, TimeUnit.MINUTES));// 設置瀏覽器緩存30分鐘 } }
application.properties 中 file.upload.path=upload/
實際存儲目錄
D:/upload/2019/03081625111.jpg
訪問地址(假設應用發布在http://www.a.com/)
https://cache.yisu.com/upload/information/20210701/112/14684.jpg
2、在Controller中增加一個RequestMapping,把文件輸出到輸出流中
@RestController @RequestMapping("/file") public class UploadFileController { @Autowired protected HttpServletRequest request; @Autowired protected HttpServletResponse response; @Autowired protected ConversionService conversionService; @Value("${file.upload.path}") private String path = "upload/"; @RequestMapping(value="/view", method = RequestMethod.GET) public Object view(@RequestParam("id") Integer id){ // 通常上傳的文件會有一個數據表來存儲,這里返回的id是記錄id UploadFile file = conversionService.convert(id, UploadFile.class);// 這步也可以寫在請求參數中 if(file==null){ throw new RuntimeException("沒有文件"); } File source= new File(new File(path).getAbsolutePath()+ "/" + file.getPath()); response.setContentType(contentType); try { FileCopyUtils.copy(new FileInputStream(source), response.getOutputStream()); } catch (Exception e) { e.printStackTrace(); } return null; } }
今天使用transferTo這個方法進行上傳文件的使用發現了一些路徑的一些問題,查找了一下記錄問題所在
前端上傳網頁,使用的是單文件上傳的方式
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/> </head> <body> <form enctype="multipart/form-data" method="post" action="/upload"> 文件:<input type="file" name="head_img"> 姓名:<input type="text" name="name"> <input type="submit" value="上傳"> </form> </body> </html>
后臺網頁
@Controller @RequestMapping("/file") public class UploadFileController { @Value("${file.upload.path}") private String path = "upload/"; @RequestMapping(value = "fileUpload", method = RequestMethod.POST) @ResponseBody public String fileUpload(@RequestParam("file") MultipartFile file) { if (file.isEmpty()) { return "false"; } String fileName = file.getOriginalFilename(); File dest = new File(path + "/" + fileName); if (!dest.getParentFile().exists()) { dest.getParentFile().mkdirs(); } try { file.transferTo(dest); // 保存文件 return "true"; } catch (Exception e) { e.printStackTrace(); return "false"; } } }
這個確實存在一些問題
路徑是不對的
dest 是相對路徑,指向 upload/doc20170816162034_001.jpg
file.transferTo 方法調用時,判斷如果是相對路徑,則使用temp目錄,為父目錄
因此,實際保存位置為 C:\Users\xxxx\AppData\Local\Temp\tomcat.372873030384525225.8080\work\Tomcat\localhost\ROOT\upload\doc20170816162034_001.jpg
所以改為:
@Controller @RequestMapping("/file") public class UploadFileController { @Value("${file.upload.path}") private String path = "upload/"; @RequestMapping(value = "fileUpload", method = RequestMethod.POST) @ResponseBody public String fileUpload(@RequestParam("file") MultipartFile file) { if (file.isEmpty()) { return "false"; } String fileName = file.getOriginalFilename(); File dest = new File(new File(path).getAbsolutePath()+ "/" + fileName); if (!dest.getParentFile().exists()) { dest.getParentFile().mkdirs(); } try { file.transferTo(dest); // 保存文件 return "true"; } catch (Exception e) { e.printStackTrace(); return "false"; } } }
感謝你能夠認真閱讀完這篇文章,希望小編分享的“如何解決MultipartFile.transferTo(dest) 報FileNotFoundExcep的問題”這篇文章對大家有幫助,同時也希望大家多多支持億速云,關注億速云行業資訊頻道,更多相關知識等著你來學習!
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。