In Thymeleaf < 3.1 I used below expression to get the request URI.
th:classappend="${#arrays.contains(urls, #httpServletRequest.getRequestURI()) ? 'active' : ''}"
It worked all the time till recently I upgraded to Spring Boot 3.0 that pulls Thymeleaf 3.1. I am getting this exceptions:
[THYMELEAF][parallel-2] Exception processing template "index": Exception evaluating SpringEL expression: "#arrays.contains(urls, #servletServerHttpRequest.getRequestURI()) ? 'active' : ''" (template: "fragments/header" - line 185, col 6)
Caused by: org.springframework.expression.spel.SpelEvaluationException: EL1011E: Method call: Attempted to call method getRequestURI() on null context object
What is the alternative now since I am using Netty instead of Tomcat in Spring Boot 3.0? I could not figure this from here.
As a workaround, for now to tackle this, I am using:
@GetMapping ("/")
String homePage(Model model) {
model.addAttribute("pagename", "home");
return "index";
}
AND
th:classappend="${pagename == 'home' ? 'active' : ''}"
CodePudding user response:
In Thymeleaf 3.0, access is provided to HttpServletRequest
:
#request : direct access to the javax.servlet.http.HttpServletRequest object associated with the current request. reference
This has been removed from Thymeleaf in 3.1.0. Here is the equivalent section from the documentation: Web context namespaces for request/session attributes, etc..
The "what's new in 3.1" documentation does not specifically mention HttpServletRequest
, but it does mention the removal of all the "web-API based expression utility objects".
The #request, #response, #session, and #servletContext are no longer available to expressions in Thymeleaf 3.1.
Spring Boot 3.0.0 uses Thymeleaf 3.1.0 (as you noted).
What to do instead?
See the related GitHub issue: Recommended way to go after upgrade to SpringBoot3 - attributes
Specifically:
These objects are not directly available in templates in Thymeleaf 3.1 for security reasons. The recommended way to make this information available to templates is to add the specific pieces of information that are really needed by the template as context variables (model attributes in Spring).
Example:
model.addAttribute("servletPath", request.getServletPath();
That is the same basic approach as what you are already doing, in your work-around.