Skip to content
Advertisement

How to create a list of clickable items using Thymeleaf

In my Spring Boot web app, I need to create a list of items using Thymeleaf where clicking and submitting an item sends its value to my controller, which looks like this:

@PostMapping({"/mylist"})
public ModelAndView postList(@RequestParam(value = "item") String item) {
    ModelAndView mav = new ModelAndView("mylist");
    mav.addObject("items", someRepository.findAll());
    ...
    return mav;
}

Note the controller takes an item parameter.

For comparison, this following Thymeleaf dropdown list performs as expected in that when I select an item from the dropdown, then click Submit, the above controller receives that item’s value:

<form th:action="@{/mylist}" method="post">
    ...
    <div>
        <select th:name="item">
            <option th:each="item : ${metaqueryitems}"
                    th:value="${item.code}"
                    th:selected="${item.id eq item}"
                    th:text="${item.id}"></option>
        </select>
        <td><input type="submit" th:value="Submit"/></td>
    </div>
    ...
</form>

But instead of a dropdown list, I want to show the items in a regular, non-dropdown list, such as the following:

<form th:action="@{/mylist}" method="post">
    ...
    <div th:name="item" th:each="item : ${items}">
        <input type="submit" th:value="${item.code}"/>
    </div>
    ...
</form>

However, when I click an item in the above list, the controller always ends up with a null value for the item parameter.

How do I send value from a th:each style Thymeleaf list over to my controller?

Advertisement

Answer

You can add name="item" to each <input> element:

<div th:each="item : ${metaqueryitems}">
    <input type="submit" name="item" th:value="${item.code}"/>
</div>

Note that because item is just a literal string there is no need to use th:name=... here. You can just use name=....


Just a note of caution here: Within a form, you typically want to ensure that every input element has a unique name value, so you know which user-entered value came from which input element.

<form action="..." method="post">
    <input type="text" name="firstname" id="firstname">
    <input type="text" name="lastname"  id="lastname">
</form>

In this very specific case, you can get away with them all using the same name (item) because you only ever submit one non-null value at a time.

User contributions licensed under: CC BY-SA
1 People found this is helpful
Advertisement