简体   繁体   English

使用Spring Boot动态更改静态内容

[英]Serve dynamically changing static content with Spring Boot

Right now I have a simple Spring Boot application that serves static images that I have placed in resources/static/img . 现在我有一个简单的Spring Boot应用程序,它提供了我放在resources/static/img This works just fine for displaying the actual content, but there are two things I'd like to fix: 这适用于显示实际内容,但有两件事我想解决:

  1. I don't want any of these images to be bundled with the resulting .jar file, and I know that placing these images in the resources folder will do that. 我不希望任何这些图像与生成的.jar文件捆绑在一起,我知道将这些图像放在resources文件夹中就可以了。

  2. Using my current setup, in order to see a new image on the webapp, I have to add it to the folder and restart it. 使用我当前的设置,为了在webapp上看到新图像,我必须将其添加到该文件夹​​并重新启动它。 I would instead like Spring to serve any static content that exists in a specific folder, so I can add images while the application is running and have them automatically served at localhost:8080/img/{image name} . 我希望Spring能够提供特定文件夹中存在的任何静态内容,因此我可以在应用程序运行时添加图像并让它们自动在localhost:8080/img/{image name}

I attempted to solve this by setting up a resource handler, but I'm not sure if this is any different than simply serving them from resources/static . 我试图通过设置资源处理程序来解决这个问题,但我不确定这是否与仅从resources/static服务它们有什么不同。 Unfortunately, I'm still struggling with getting this configured correctly, as I'm unable to see any images at all. 不幸的是,我仍然在努力正确配置,因为我根本无法看到任何图像。 Here's what I tried: 这是我试过的:

@Configuration
public class StaticResourceConfiguration extends WebMvcConfigurerAdapter {
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/img/**").addResourceLocations("file:" + Application.IMAGE_DIR);
        super.addResourceHandlers(registry);
    }
}

And here is my Application configuration: 这是我的应用程序配置:

@SpringBootApplication
public class Application extends SpringBootServletInitializer {

    static String IMAGE_DIR;

    @Override
    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(Application.class);
    }

    public static void main(String[] args) throws IOException {
        SpringApplication.run(Application.class, args);
        IMAGE_DIR = new File(".").getCanonicalPath() + "/img/";
    }

}

Again, my goal is to set up a folder in the root of my project called img which will store the images that I would like the webapp to serve on localhost:8080/img/{image name} . 同样,我的目标是在项目的根目录中设置一个名为img的文件夹,它将存储我希望webapp在localhost:8080/img/{image name}上提供的localhost:8080/img/{image name} If possible, I'd like to be able to add content to this folder while the application is running and have Spring automatically serve them without having to restart it. 如果可能的话,我希望能够在应用程序运行时向该文件夹添加内容,并让Spring自动为它们提供服务而无需重新启动它。

Does anyone have any ideas? 有没有人有任何想法? Thanks in advance. 提前致谢。

the problem with your approach is that you set IMAGE_DIR after spring boot application is ran and the constant IMAGE_DIR is not initialized and is null . 您的方法的问题是您在运行Spring启动应用程序并且未初始化常量IMAGE_DIR并且为null设置IMAGE_DIR Change it as follows: 更改如下:

public static void main(String[] args) throws IOException {
        IMAGE_DIR = "/opt/img/";
        SpringApplication.run(Application.class, args);
    }

and remove all File(".").getCanonicalPath() related stuff and it will work. 并删除所有File(".").getCanonicalPath()相关的东西,它将工作。 Your approach will fit in your needs when you have new image in selected directory it can be served. 当您在所选目录中有新图像时,您的方法将满足您的需求。

to solve the problem with your point 2. 用你的观点解决问题2。

  1. Using my current setup, in order to see a new image on the webapp, I have to add it to the folder and restart it. 使用我当前的设置,为了在webapp上看到新图像,我必须将其添加到该文件夹​​并重新启动它。 I would instead like Spring to serve any static content that exists in a specific folder, so I can add images while the application is running and have them automatically served at localhost:8080/img/{image name}. 我希望Spring能够提供特定文件夹中存在的任何静态内容,因此我可以在应用程序运行时添加图像并让它们自动在localhost:8080 / img / {image name}中提供。

You can create all those images under: 您可以在以下位置创建所有图像:

/resources/public
    -img
    -js,...

And to access just localhost:8080/img/yourImage.png 并且只访问localhost:8080 / img / yourImage.png

Everything under "public" folder will be accessible “public”文件夹下的所有内容都可以访问

To serve dynamically content with spring boot, I found a solution that's work. 为了通过spring boot动态提供内容,我找到了一个可行的解决方案。 The idea is to link static content directory to a symbolic link with no cache and after that, you just need to rebuild sym link every time you need. 我们的想法是将静态内容目录链接到没有缓存的符号链接之后,您只需要在每次需要时重建sym链接。 So in your case: 所以在你的情况下:

@Configuration
public class StaticResourceConfiguration extends WebMvcConfigurerAdapter {
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/img/**").addResourceLocations("file:/tmp/images/").setCacheControl(CacheControl.noCache());
        super.addResourceHandlers(registry);
    }
}

After that, you change your image directory like this: 之后,您可以像这样更改图像目录:

Path link = Paths.get("/tmp/images"); //Symlink
Files.deleteIfExists(link);
Files.createSymbolicLink(link, Paths.get(your_new_images_directory));

The choice of symlink /tmp/images is personal, you can choose what you want. symlink / tmp / images的选择是个人的,你可以选择你想要的。 Pay attention, your application need to have good right for symlink creation. 注意,您的应用程序需要具有创建符号链接的良好权利。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM