1. 简介

在之前的《Spring 中使用 Thymeleaf 入门》文章中,我们学习了如何在 Thymeleaf 模板中通过 th:objectth:field 将用户输入绑定到 Java 对象,并在控制器中使用 @ModelAttribute 接收这些数据。

在本文中,我们将重点讲解如何在 Spring 控制器中使用 @RequestParam 注解,并结合 Thymeleaf 模板处理请求参数。✅

2. 表单中的参数

我们先创建一个简单的控制器,用于接收四个可选的请求参数:

@Controller
public class MainController {
    @RequestMapping("/")
    public String index(
        @RequestParam(value = "participant", required = false) String participant,
        @RequestParam(value = "country", required = false) String country,
        @RequestParam(value = "action", required = false) String action,
        @RequestParam(value = "id", required = false) Integer id,
        Model model
    ) {
        model.addAttribute("id", id);
        List<Integer> userIds = Arrays.asList(1,2,3,4);
        model.addAttribute("userIds", userIds);
        return "index";
    }
}

模板名称为 index.html,我们将通过三种不同的 HTML 表单元素来演示如何将参数传递给控制器。

2.1 输入框(Input)

我们先来看一个简单的文本输入框示例:

<form th:action="@{/}">
  <input type="text" th:name="participant"/>
  <input type="submit"/>
</form>

这个输入框通过 th:name="participant" 将用户输入的值绑定到控制器的 participant 参数上。⚠️注意:控制器中必须使用 @RequestParam("participant") 来接收。

2.2 下拉框(Select)

接下来是下拉框,用于选择国家:

<form th:action="@{/}">
  <input type="text" th:name="participant"/>
  <select th:name="country">
    <option value="de">Germany</option>
    <option value="nl">Netherlands</option>
    <option value="pl">Poland</option>
    <option value="lv">Latvia</option>
  </select>
</form>

选中的 option 值将通过 th:name="country" 传递给控制器的 country 参数。

2.3 按钮(Button)

按钮也可以作为参数传递的媒介,适用于需要根据点击不同按钮执行不同操作的场景:

<form th:action="@{/}">
  <button type="submit" th:name="action" th:value="in">check-in</button>
  <button type="submit" th:name="action" th:value="out">check-out</button>
</form>

点击不同的按钮,控制器将接收到对应的 action 值,如 inout

3. 超链接中的参数

除了表单提交,我们还可以通过超链接传递请求参数:

<a th:href="@{/index}">

也可以在 URL 中添加参数:

<a th:href="@{/index(param1='value1', param2='value2')}">

Thymeleaf 会将其解析为:

<a href="/index?param1=value1&param2=value2">

这种方式在需要根据变量动态生成链接时特别有用。例如,为每个用户 ID 生成一个链接:

<th:block th:each="userId: ${userIds}">
  <a th:href="@{/(id=${userId})}">User [[${userId}]]</a>
  <br/>
</th:block>

我们在控制器中传入用户 ID 列表:

List<Integer> userIds = Arrays.asList(1, 2, 3);
model.addAttribute("userIds", userIds);

生成的 HTML 效果如下:

<a href="/?id=1">User 1</a> <br/>
<a href="/?id=2">User 2</a> <br/>
<a href="/?id=3">User 3</a> <br/>

点击链接后,控制器将接收到 id 参数。

4. 小结

在本文中,我们学习了如何在 Spring 控制器中使用 @RequestParam 并结合 Thymeleaf 模板传递请求参数。✅

  • 使用 th:name 可以将表单元素的值绑定到控制器参数
  • 超链接中也可以通过 @{...} 表达式传递参数
  • 控制器中必须使用 @RequestParam 注解来接收这些参数

完整的示例代码可以在 GitHub 上找到:GitHub 示例代码。✅

如果你在实际开发中遇到参数绑定失败的问题,建议检查以下几点:

  • 控制器方法参数名是否与 th:name 一致
  • 是否遗漏了 @RequestParam 注解
  • 表单是否设置了正确的 method 类型(GET/POST)

原始标题:Spring Request Parameters with Thymeleaf