【问题标题】:Spring boot and Thymeleaf - Hot swap templates and resources once againSpring boot 和 Thymeleaf - 再次热插拔模板和资源
【发布时间】:2017-02-24 16:56:39
【问题描述】:

我尝试了在此处和文档中找到的所有提示和技巧,但仍然没有运气。我有带有 Thymeleaf 的 Spring webapp。当我在 IDEA 中调用 update 时,不会重新加载资源和模板(它没有说明要重新加载)。然后我可以在浏览器中疯狂地按 ctrl+f5,只是没有更改。

一切都在一个 Java 类中配置,如下所示:

@EnableWebMvc
public class MvcConfig extends WebMvcConfigurerAdapter implements ApplicationContextAware {

我的文件夹结构现在看起来像 this,但我也尝试将没有“静态”文件夹的资源放入 webapp/resources。

ResourceHandlerRegistry:

@Override
public void addResourceHandlers(final ResourceHandlerRegistry registry) {
    super.addResourceHandlers(registry);
    registry.addResourceHandler("/img/**").addResourceLocations("classpath:/static/img/");
    registry.addResourceHandler("/css/**").addResourceLocations("classpath:/static/css/");
    registry.addResourceHandler("/js/**").addResourceLocations("classpath:/static/js/");
}

我在两个 application.properties 中都指定了 cache=false:

spring.thymeleaf.cache=false

在提到的 MvcConfig 类中:

@Bean
public SpringResourceTemplateResolver templateResolver() {
    SpringResourceTemplateResolver templateResolver = new SpringResourceTemplateResolver();
    templateResolver.setApplicationContext(this.applicationContext);
    templateResolver.setPrefix("/WEB-INF/templates/");
    templateResolver.setSuffix(".html");
    templateResolver.setTemplateMode(TemplateMode.HTML);
    templateResolver.setCacheable(false);
    return templateResolver;
}

根据一些关于 SO 的答案,我添加了对 devtools 的依赖:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-devtools</artifactId>
    <version>1.4.1.RELEASE</version>
    <optional>true</optional>
</dependency>

还是不行。有人说用 addResources=true 添加 maven 启动插件,所以我做了:

<plugin>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-maven-plugin</artifactId>
    <version>1.4.1.RELEASE</version>
    <configuration>
        <addResources>true</addResources>
    </configuration>
</plugin>

我猜我的想法设置正确,因为当我调用更新时,我的 Java 类会立即重新加载。只有资源和html文件不是,我必须为它重新启动服务器。实际上 *.html 文件并不是什么大不了的事,但是在每次小的 css 和 js 更改后重新启动服务器让我的速度变慢了很多,而且我花了将近 15 个小时来找出问题所在,这开始非常令人沮丧。

任何帮助将不胜感激。

【问题讨论】:

标签: java spring-mvc spring-boot thymeleaf hotswap


【解决方案1】:

我已经花了一些时间,最后在这里我将解释我是如何让它工作的。 谷歌搜索你可能会发现几个信息:

我最初的方法是禁用缓存并添加 Spring 开发工具:

春季开机application.properties

spring.thymeleaf.cache=false
spring.thymeleaf.mode=LEGACYHTML5
spring.thymeleaf.prefix=/templates/

pom.xml

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-devtools</artifactId>
        <optional>true</optional>
    </dependency>

但是,使用上面的 sn-p 是不够的,因为热插拔仅在制作项目时完成(Intellij Idea 中的 CTRL + F9)。这是因为默认的模板解析器是基于类路径的,因此需要重新编译。


一个可行的解决方案是使用基于文件系统的解析器覆盖defaultTemplateResolver

application.properties

spring.thymeleaf.cache=false
spring.thymeleaf.mode=LEGACYHTML5
spring.thymeleaf.templates_root=src/main/resources/templates/

应用类

@SpringBootApplication
public class MyApplication {

    @Autowired
    private ThymeleafProperties properties;

    @Value("${spring.thymeleaf.templates_root:}")
    private String templatesRoot;

    public static void main(String[] args) {
        SpringApplication.run(MyApplication.class, args);
    }

    @Bean
    public ITemplateResolver defaultTemplateResolver() {
        FileTemplateResolver resolver = new FileTemplateResolver();
        resolver.setSuffix(properties.getSuffix());
        resolver.setPrefix(templatesRoot);
        resolver.setTemplateMode(properties.getMode());
        resolver.setCacheable(properties.isCache());
        return resolver;
    }
}

我发现此解决方案是最佳解决方案,因为它允许您将配置外部化并使用不同的配置文件(dev、prod 等),同时还可以通过 只需按 F5 :) 重新加载更改

【讨论】:

  • 我收到警告Cannot resolve configuration property 'spring.thymeleaf.templates_root'。这个属性真的存在吗?
  • 写就存在,看答案中的例子application.properties
  • 使用一行配置可以做最后的工作(覆盖defaultTemplateResolver):spring.thymeleaf.prefix=file:///${user.dir}/src/main/resources/templates/
【解决方案2】:

这是我使用 IntelliJ IDEA (2018.3) 的设置,保存更改后会重新加载 HTML:

  1. 在 application.properties 中:

    spring.resources.static-locations = classpath:/resources/static
    spring.resources.cache.period = 0
    
  2. 在 pom.xml 中,设置&lt;addResources&gt;true&lt;/addResources&gt;

    <plugin>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-maven-plugin</artifactId>
        <configuration>
            <addResources>true</addResources>
        </configuration>
    </plugin>
    
  3. 菜单Run => Edit Configurations (IntelliJ IDEA)

帧停用:Update resources

【讨论】:

    【解决方案3】:

    好的,所以我找到了针对我的具体案例的答案。问题根本不在我的应用程序或其配置中(嗯..可能)。我没有使用 Tomcat 8.5.5,而是切换回 Tomcat 7。现在一切正常。有人知道为什么吗?

    【讨论】:

      【解决方案4】:

      @Luke 我的解决方案非常简单:

      在 Spring Thymeleaf 中自动重新加载 HTML / CSS / JS 可以简单且无错误,仅在 IntelliJ 中测试过。

      将此添加到 maven,使用 ${spring.version} var 或替换为您的版本:

      <dependency>
          <groupId>org.springframework.boot</groupId>
          <artifactId>spring-boot-devtools</artifactId>
          <version>${spring.version}</version>
          <optional>true</optional>
          <scope>runtime</scope>
      </dependency>
      

      添加到html的头部:

      <script src="http://localhost:35729/livereload.js"></script>
      

      使用 IntelliJ 时:

      【讨论】:

        猜你喜欢
        • 2019-07-17
        • 2015-03-11
        • 2014-02-19
        • 2019-10-31
        • 2018-10-07
        • 2016-05-14
        • 2017-03-08
        • 2014-11-21
        相关资源
        最近更新 更多