Spring Boot 镜像上传和服务

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/45651119/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-08 01:28:51  来源:igfitidea点击:

Spring Boot images uploading and serving

springimagespring-bootfile-uploadstatic-content

提问by Weras Adve

I'm making new Spring Boot app and want to be able to store and serve images, I want images to be stored in applications directory:
enter image description here

我正在制作新的 Spring Boot 应用程序并希望能够存储和提供图像,我希望图像存储在应用程序目录中:
在此处输入图片说明

this is what uploading looks like for now:

这是现在上传的样子:

@PostMapping("/")
@ResponseBody
public String upload(@RequestPart String title, @RequestPart MultipartFile img) throws IOException{
    String imgName = img.getOriginalFilename();
    Post p = new Post();
    p.setTitle(title);
    p.setImageName(imgName);
    postService.add(p);
    File upl = new File("images/" + imgName);
    upl.createNewFile();
    FileOutputStream fout = new FileOutputStream(upl);
    fout.write(img.getBytes());
    fout.close();
    return "ok";
}

this is how I want to get images

这就是我想要获取图像的方式

<img th:src="@{'images/' + ${post.imageName}}"/>

for now I get 404 and when I want to view some images in directory I get

现在我得到 404,当我想查看目录中的一些图像时,我得到

Fatal error reading PNG image file: Not a PNG file

how should I do it to make it work?

我该怎么做才能让它发挥作用?

回答by Kevin Peters

Per default your Spring Boot application serves staticcontent- in your case images - found at following locations:

默认情况下,您的 Spring Boot 应用程序提供静态内容- 在您的情况下为图像 - 可在以下位置找到:

  • /static
  • /public
  • /resources
  • /META-INF/resources
  • /静止的
  • /民众
  • /资源
  • /META-INF/资源

So usually, static/images/would perhaps be the place where Thymeleaf should expect the staticimages which have to be delivered for rendering. But since this place is about staticcontent and since it is in general a bad idea to save uploaded (dynamic) content inside your application I would recommend to DON'T do that. Did you think about what happens if your application is redeployed or moved to another machine? Your would have to backup / move the images in a cumbersome way. There are better solutions, storing the upload content at a separate location outside your app (which could for example be configurable and also reused by multiple instances) or even use a database to store image data. That would also enable handling images in a transactional context (e.g. isolation & rollbacks).

所以通常,static/images/可能是 Thymeleaf 应该期望必须交付用于渲染的静态图像的地方。但是由于这个地方是关于静态内容的,并且因为在您的应用程序中保存上传的(动态)内容通常是一个坏主意,所以我建议不要这样做. 你有没有想过如果你的应用程序被重新部署或移动到另一台机器上会发生什么?您将不得不以繁琐的方式备份/移动图像。有更好的解决方案,将上传内容存储在应用程序之外的单独位置(例如,可以配置并由多个实例重用),或者甚至使用数据库来存储图像数据。这也将能够在事务上下文中处理图像(例如隔离和回滚)。

But If you now want to still store it inside your app, your can extend the locations by adding places to search for (actually staticcontent). Although the answer of Ajit and even the documentation still gives the advice to extend your own WebMvcConfigurerAdapter, I personally would tend to implement WebMvcConfigurerinstead, because the former is deprecated.

但是,如果您现在仍想将其存储在您的应用程序中,您可以通过添加要搜索的位置(实际上是静态内容)来扩展位置。虽然阿吉特的答案,甚至是文档还是给出了建议以延长自己的WebMvcConfigurerAdapter,我个人会倾向于实施WebMvcConfigurer代替,因为前者已被弃用。

In this case it should look like:

在这种情况下,它应该如下所示:

@Configuration
public class AdditionalResourceWebConfiguration implements WebMvcConfigurer {
    @Override
    public void addResourceHandlers(final ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/images/**").addResourceLocations("file:images/");
    }
}

回答by Ajit Soman

To access image from your images folder,

要从您的images folder

enter image description here

在此处输入图片说明

You need to override addResourceHandlersmethod of WebMvcConfigurerAdapterclass like this:

您需要像这样覆盖类的addResourceHandlers方法WebMvcConfigurerAdapter

@Configuration
public class ResourceConfig extends WebMvcConfigurerAdapter {
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/images/**").addResourceLocations("file:images/");
    }
}

After that you need add /before images in URL like this:

之后,您需要/在 URL 中添加图像之前,如下所示:

<img th:src="@{'/images/' + ${post.imageName}}"/>

回答by Scott

You can store external files in a folder named /staticin the same directory as your jar and spring will scan them by default. So if you have static/images/you can reference your images with:

您可以将外部文件存储/static在与 jar 相同目录中的文件夹中,默认情况下 spring 将扫描它们。所以如果你有static/images/你可以参考你的图像:

<img th:src="@{/images/img.ext}"/>

<img th:src="@{/images/img.ext}"/>

So you would want to use new File("/static/images/" + imgName);

所以你会想要使用 new File("/static/images/" + imgName);