Exception evaluating SpringEL expression for String array - spring-boot

While at spring boot <= 2.4.3 the below snippet worked fine.
<div class="link-red ddmenu" th:with="urls=${new String[]{'/'}}"
th:classappend="${#arrays.contains(urls, #httpServletRequest.getRequestURI()) ? 'selected' : ''}">
<a href="/" th:href="#{/}"> <i class="fa fas fa-home"></i>Home
</a>
</div>
But after upgrading to 2.7.0, I am getting this parsing exception. What should I do to fix it?
Exception evaluating SpringEL expression: "new String[]{'/'}"
Or any related information for this break, available on any Thymeleaf's official site?

Interestingly enough, if you keep looking down the stack track you find this error at the bottom:
Caused by: org.springframework.expression.spel.SpelEvaluationException: EL1005E: Type cannot be found 'String'
If I change the expression to:
th:with="urls=${new java.lang.String[]{'/'}}"
Everything works again for me (tested with Spring Boot starter 2.6.7).

Related

insert quotes into expression thymeleaf

I have a fragment of thymeleaf code with form. I want to validate this form.
<form>
<th:block th:fragment="input (label, name, type)">
<div class="col-md-3 form-group" th:class="${#fields.hasErrors(*{__${name}__})}
? 'col-md-3 form-group has-error' : 'col-md-3 form-group'">
Here I got exception:
Caused by: org.thymeleaf.exceptions.TemplateProcessingException: Exception evaluating SpringEL expression: "#fields.hasErrors(name)" (template: "fragments/inputFieldWithType" - line 5, col 42)
Caused by: java.lang.IllegalStateException: Neither BindingResult nor plain target object for bean name 'user' available as request attribute
As I seen in Baeldung, i have to bring field name in quotes like this:
${#fields.hasErrors('name')}
So how can I put name param into quotes?
You can use th:class="${#fields.hasErrors('__${fieldName}__')}"

Thymeleaf expression parse exception

I've 2 lists; allkontrols (2 element), risk.kontrols (1 element)
I'm listing all kontrols as checkbox and trying to 'select' them if risk.kontrols list contains it.
The one element in risk.kontrols is also in allkontrols.
So, when I tried to print the results of this:
<div th:each="kontrol : ${allkontrols}" th:text="${#lists.contains(risk.kontrols, kontrol)}"/>
I got results as
true
false
Everything is ok till here. Now, when I tried to populate them with data, I got errors. Here is the code:
<div th:each="kontrol : ${allkontrols}" class="items form-control-lg">
<label>
<input th:value="${kontrol.id}" th:selected="{#lists.contains(risk.kontrols, kontrol)}" type="checkbox" class="flat">
<div style="display: inline-block;" th:utext=" ${kontrol.name}"></div>
</label>
</div>
Error part:
th:selected="{#lists.contains(risk.kontrols, kontrol)}"
Stacktrace:
2018-07-27 20:36:55 ERROR o.a.c.c.C.[.[.[.[dispatcherServlet] - Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.thymeleaf.exceptions.TemplateInputException: An error happened during template parsing (template: "view/riskkontrol.html")] with root cause
org.thymeleaf.exceptions.TemplateProcessingException: Could not parse as expression: "{#lists.contains(risk.kontrols, kontrol)}" (template: "riskkontrol" - line 44, col 140)
It looks like you're missing a $ before the { in your th:selected, try changing it to: th:selected="${#lists.contains(risk.kontrols, kontrol)}"

Spring Boot Thymeleaf Could not parse as expression with an url

I'm putting a button on page 1 to navigate to page 2. Page 1 and 2 are on different controllers.
This is the code of my button. The pid is the ID of the project. p.id gives the ID of the project. But I don't know what the problem here is.
<td><a th:href="#{/projects/project/{pid}/clusters(pid=${p.id})" class="btn btn-info" role="button">Clusters</a></td>
The exception:
org.thymeleaf.exceptions.TemplateProcessingException: Could not parse as expression: "#{/projects/project/{pid}/clusters(pid=${p.id})" (projects:53)
You've missed one curly bracket at the end of expression
<a th:href="#{/projects/project/{pid}/clusters(pid=${p.id})}" class="btn btn-info" role="button">Clusters</a>

Spring Thyme Leaf checking for global errors results in NPE

To display global errors created with Spring MVC with Thyme Leaf, I tried the example given at http://www.thymeleaf.org/doc/tutorials/2.1/thymeleafspring.html#global-errors:
That, is:
<div th:if="${#fields.hasGlobalErrors()}">
and
<ul th:if="${#fields.hasErrors('global')}">
and
<div th:if="${#fields.hasGlobalErrors()}">
When I add them to my HTML, the page won't even render, nevermind about submitting the form. All the examples result in:
org.springframework.web.util.NestedServletException: Request processing failed; nested exception is org.thymeleaf.exceptions.TemplateProcessingException: Exception evaluating SpringEL expression: "#fields.hasErrors('global')"
I tried this with v2.1.4 and v.2.1.3 and got the same error. Bug or am I doing something wrong?
Yes, the tags are all closed and properly formed. Yes, this code was within a form. Yes, all the other aspects of the form work without the global error check.
Here is a short version of broken HTML:
<form action="search.html" th:action="#{/auto/search}">
<p th:if="${#fields.hasErrors('global')}" th:errors="*{global}">
Incorrect date
</p>
<input type="text" th:field="${command.stockNumber}" />
<select th:field="*{command.startYear}">
<option value="" th:each="year : ${modelYears}" th:value="${year}"
th:text="${year}"></option>
</select>
</form>
And the controller..
#RequestMapping(value = "/auto/search", method = RequestMethod.POST)
public String search(#Validated
#ModelAttribute("command")
AutoSearchCommand autoSearchCommand
BindingResult result, Model model) {
return "search";
}
Solved:
th:object is needed in a tag preceding to the global error check. Unfortunately, this isn't mentioned in the Spring Thyme Leaf tutorial. Presumably, there's a default form name somewhere which I've overridden in my controller.
Adding the tag in results in this working html:
<form action="search.html" th:action="#{/auto/search}">
<div th:object="${command}" th:remove="tag">
<p th:if="${#fields.hasErrors('global')}" th:errors="*{global}">
Incorrect date
</p>
</div>
<input type="text" th:field="${command.stockNumber}" />
<select th:field="*{command.startYear}">
<option value="" th:each="year : ${modelYears}" th:value="${year}"
th:text="${year}"></option>
</select>
</form>
.. Where "command" is the name of the form bean in the controller.
This thread helped me figure it out.

assert_select not working after upgrading to latest rails version

I have the following HTML snippet, and my assert_select is no longer working (after upgrading to the latest version of Rails):
<div id="content">
<div class="container">
<div class="foo">
<h2>Latest</h2>
<p>
<a href="/downloads/latest.zip" class="button download">
<span>Download</span>
</a>
</p>
</div>
</div>
</div>
Here's the assertion:
assert_select '.container a.downloadbutton[href^=/downloads]', assigns(:downloads).count
Here's the error:
Expected exactly 1 element matching ".container a.button[href^='/downloads']", found 0.
Anyone know what I'm doing wrong?
Thanks!!!
V
Looks like a mismatch in the class between the classes in the code fragment 'button' and 'download' and the class in the assertion 'downloadbutton'. Perhaps getting rid of the space between 'button' and 'download' in the fragment will work.

Resources