Giter Site home page Giter Site logo

Comments (29)

yanhua365 avatar yanhua365 commented on April 19, 2024 62

It works!

I user IntelliJ Idea debug the application.

After add application.properties with:

spring.thymeleaf.cache: false

Then,after edit html template, must use CTRL+F9 to make the project.

In this way,it works fine for me.

from spring-boot.

oak1980 avatar oak1980 commented on April 19, 2024 50

Springboot with IntelliJ and configurations in src/main/resources/application.properties I put in the following relative path, and started the Application.main(...) from IntelliJ:

# Templates reloading during development
spring.thymeleaf.prefix=file:src/main/resources/templates/
spring.thymeleaf.cache=false

# Static resources reloading during development
spring.resources.static-locations=file:src/main/resources/static/
spring.resources.cache-period=0

from spring-boot.

amr avatar amr commented on April 19, 2024 45

@MattFriedman The default template resolver registered by spring is classpath based, meaning that it loads the templates from the compiled resources. That's why it requires a recompilation. Thymeleaf includes a file-system based resolver, this loads the templates from the file-system directly not through the classpath (compiled resources). Spring Boot allows us to override the default resolver by making a bean with the name defaultTemplateResolver, here is a full example:

@Configuration
public class ThymeleafConfiguration {
  @Bean
  public ITemplateResolver defaultTemplateResolver() {
    TemplateResolver resolver = new FileTemplateResolver();
    resolver.setSuffix(".html");
    resolver.setPrefix("path/to/your/templates");
    resolver.setTemplateMode("HTML5");
    resolver.setCharacterEncoding("UTF-8");
    resolver.setCacheable(false);
    return resolver;
  }
}

With this, I basically Ctrl+S and refresh the browser. A better variation would be one that uses ThymeleafProperties, like that:

@Configuration
public class ThymeleafConfiguration {
  @Inject
  private ThymeleafProperties properties;

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

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

This would work with an application-dev.yml like:

spring:
    thymeleaf:
      mode: HTML5
      cache: false
      templates_root: src/main/resources/templates/

In my application, I annotate that resolver with @Profile(Constants.SPRING_PROFILE_DEVELOPMENT) to limit its use to development. That's why I also set the caching to false in the configuration file (it's -dev only). In production I use the default classpath-based loader.

from spring-boot.

dsyer avatar dsyer commented on April 19, 2024 11

"CTRL+F9" must be something you can automate (build on save or something). Other IntelliJ users manage it, so it must be possible (cc @snicoll in case he knows what the incantation is).

from spring-boot.

dsyer avatar dsyer commented on April 19, 2024 9

Well it works for other people so you must be doing something different, I'd say. Did you read everything above? E.g. you seem to be using the wrong property name for the cache setting.

from spring-boot.

MattFriedman avatar MattFriedman commented on April 19, 2024 8

I run the application from main() in Idea IDE. I set the application.properties as stated above.

If I'm using jsp then I can expect changes to the jsp files to be visible immediately without recompiling.

I think the issue here is that there is an expectation that the thymeleaf templates will have the same behaviour. This does not appear to be the case.

Is it possible to have changes to the th templates visible any time they are changed, without any recompiling or rebuilding of the project?

The point is that front-end developers need to make tons of changes to templates and view the results often. Having to recompile every time is a ton of overhead for a front-end developer so they want to avoid this.

from spring-boot.

ukitzmann avatar ukitzmann commented on April 19, 2024 5

You can use this to disable the Thymeleaf cache:

spring.thymeleaf.cache: false

from spring-boot.

snicoll avatar snicoll commented on April 19, 2024 5

https://www.jetbrains.com/idea/documentation/migration_faq.html

You can enable automatic compilation on every save (or autosave). To do that, turn on the Make project automatically option on the Compiler page in the Settings / Preferences dialog (File | Settings | Compiler on Windows or Linux, or IntelliJ IDEA | Preferences | Compiler on Mac OS X).

@MattFriedman if you want to discuss this further, please create a separate issue.

from spring-boot.

MattFriedman avatar MattFriedman commented on April 19, 2024 4

Hi Dave,

I have done the following: I read all the posts. I put the system in debug (running from main()) and verified that the TemplateResolver/ViewResolver had caching set to false. I used both properties mentioned above, both set to false. I tried changing the template and opened the page in two separate browsers to see if it was the browser that was caching the older version but this is not the case. I checked using curl as well.

I think what it comes down to is how you define: "it works"

Above, yanhua365 says "Then,after edit html template, must use CTRL+F9 to make the project"

For me, "it works" means: change the template => refresh browser => changes are visible.

So yanhua365 is correct, it does work in the way he describes. However, as far as I can determine, it does not work in the way I am describing.

I'm just trying to point out that the intermediate step of having to rebuild is a problem as it adds a boatload of overhead to the development flow for front-end developers. Front-end developers are constantly making changes and then refreshing the page to check the result. (to the point of developing repetitive stress injuries) Adding an intermediate step is a problem from that perspective.

I don't know if it possible for it to work in the way I'm describing, but if it is it would be a great improvement.

from spring-boot.

thesurlydev avatar thesurlydev commented on April 19, 2024 4

For other folks that might run into this issue. I had the same problem until I realized that IntelliJ's key mapping for Ctrl-F9 was not actually doing what it was supposed to (Make Project). You can verify this in a couple of ways:

  1. monitor the timestamp of a Thymeleaf template in target/classes/templates after you make a change and use Ctrl-F9.
  2. make a change to a template, then use the Build > Make Project via the main menu.

The fix for my particular case was to remap the keyboard shortcut for "Make Project". After I did this I was able to make changes to my templates, use my new keyboard shortcut for "Make Project", then reload the browser to see the changes.

from spring-boot.

anuragphadke19 avatar anuragphadke19 commented on April 19, 2024 4

Springboot with IntelliJ and configurations in src/main/resources/application.properties I put in the following relative path, and started the Application.main(...) from IntelliJ:

# Templates reloading during development
spring.thymeleaf.prefix=file:src/main/resources/templates/
spring.thymeleaf.cache=false

# Static resources reloading during development
spring.resources.static-locations=file:src/main/resources/static/
spring.resources.cache-period=0

If someone else drop's by this long-closed issue, the parameter should be(as of Spring Boot 2.0.5 release)
spring.resources.cache.period=0

from spring-boot.

giovannicandido avatar giovannicandido commented on April 19, 2024 3

In my application-development.yml:

resources:
  projectroot: /Users/giovanni/Projects/projectName
spring:
   thymeleaf:
     cache: false
     prefix: file:///${resources.projectroot}/server/src/main/resources/templates/

This way in development it use the direct files, and in production the classpath
Note: There is a subproject named server in the projectName project root

from spring-boot.

checketts avatar checketts commented on April 19, 2024 1

This ticket is noting that even when using that property, they are being cached.

from spring-boot.

henryabra avatar henryabra commented on April 19, 2024 1

@giovannicandido Thanks for the tip.
One note though, ${resources.projectroot} did not work for me but ${user.dir} worked like a charm.
Cheers

from spring-boot.

dsyer avatar dsyer commented on April 19, 2024

mvn spring-boot:run probably runs from the compiled jar. To use spring.template.cache: false effectively you need to launch from an IDE. Does that make sense? It seems to work for other people.

from spring-boot.

dsyer avatar dsyer commented on April 19, 2024

I guess if you mvn package you will get the source files copied into the classpath of the running process. If that works I'm not sure what else we can do. Did you try it?

from spring-boot.

pieterdegraeuwe avatar pieterdegraeuwe commented on April 19, 2024

For the ones that are struggling with this too.
Be sure that your application.properties is on the right location! (more on this here)
When you have in your resources directory also a sub directory 'templates', it can be quickly overseen that your application.properties is not IN, but on the same level as the 'resourses' directory.
At least this was the case for me on a late evening....
I discovered it by putting the application.properties in a config directory... then the reloading did suddenly work..
This lead me to see that the other application.properties was not found, since it was not in the resources directory...

from spring-boot.

dsyer avatar dsyer commented on April 19, 2024

You should be able to just use the default classpath loader as long as you are running in debug mode (and your IDE is configured to copy resources on save - Eclipse does this out of the box).

from spring-boot.

jgon avatar jgon commented on April 19, 2024

@amr : Thank you.
The solution using the ThymeleafConfiguration worked perfectly.
I just had to replace @Inject by @Autowired in my case.

from spring-boot.

snicoll avatar snicoll commented on April 19, 2024

@henryabra ${resources.projectroot} is a custom key that is defined in the same yml file (see the two first line).

from spring-boot.

henryabra avatar henryabra commented on April 19, 2024

@giovannicandido You are absolutely correct.

from spring-boot.

checketts avatar checketts commented on April 19, 2024

@oak1980 You are using a debug configuration and hitting CTRL-F9? (See #34 (comment)) What versions of SpringBoot are you using if you believe it is a regression?

from spring-boot.

oak1980 avatar oak1980 commented on April 19, 2024

With this approach, I don't need to press CTRL-F9.

from spring-boot.

checketts avatar checketts commented on April 19, 2024

Ah so you are reporting an alternative approach that works for you and avoids the need to rebuild in IntelliJ.

It is good to call out that you wouldn't want to check it spring.resources.static-locations=file:src/main/resources/static/ in your application.yml, and instead set it via a run config in intelliJ so you don't accidentally check it in (or perhaps set it in a profile specific file)

from spring-boot.

PhaneendraNakkala avatar PhaneendraNakkala commented on April 19, 2024

@oak1980 you are awesome!
that works like charm.

from spring-boot.

attacomsian avatar attacomsian commented on April 19, 2024

I recommend using Gulp to automate templates and resources reload. Following is a little Gulp task that does the magic for me:

var gulp = require('gulp'), 
   watch = require('gulp-watch');

gulp.task('watch', function () {
   return watch('src/main/resources/**/*.*', () => {
           gulp.src('src/main/resources/**')
               //replace with build/resources/main/ for netBeans
               .pipe(gulp.dest('out/production/resources/')); 
   });
});

gulp.task('default', ['watch']);

I wrote a short blog post on this topic as well.

from spring-boot.

pdurejachd avatar pdurejachd commented on April 19, 2024

A working solution is to override the defaultTemplateResolver by using a file system based resolver:

application.properties

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

Application class

@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;
    }
}

from spring-boot.

waltervi avatar waltervi commented on April 19, 2024

Springboot with IntelliJ and configurations in src/main/resources/application.properties I put in the following relative path, and started the Application.main(...) from IntelliJ:

# Templates reloading during development
spring.thymeleaf.prefix=file:src/main/resources/templates/
spring.thymeleaf.cache=false

# Static resources reloading during development
spring.resources.static-locations=file:src/main/resources/static/
spring.resources.cache-period=0

You saved my day buddy!

from spring-boot.

dtonhofer avatar dtonhofer commented on April 19, 2024

The latest configuration names seem to be as follows, based off Spring Boot 3.1.0:

Unchanged:

# Templates reloading during development
spring.thymeleaf.prefix=file:src/main/resources/templates/
spring.thymeleaf.cache=false

Changed:

# Static resources reloading during development
spring.web.resources.static-locations=file:src/main/resources/static/
spring.web.resources.cache.period=0

Or in YAML (application.yml):

spring:
  thymeleaf:
    # Template reloading during development
    prefix: file:src/main/resources/templates/
    cache: false
  web:
    resources:
      # Static resource reloading during development
      static-locations: file:src/main/resources/static/
      cache:
        period: 0

from spring-boot.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.