如何通过HTML按钮修改对象status字段并保持在当前页面?
问题解决方案
1. 修复URL路径拼接错误
原链接直接拼接ID和状态值,导致路径格式错误,需在两者间添加斜杠分隔:
<a th:href="@{'projects/update/' + ${project.id} + '/' + 'InProgress'}" class="btn btn-secondary">InProgress</a>
修改后生成的URL为http://localhost:8080/projects/update/852/InProgress,符合Controller中双路径变量的结构。
2. 修正Controller的请求映射与请求方式
方式一:改用GET请求(简单直接)
调整Controller的映射路径,匹配带ID和状态的URL,并将请求方式改为GET:
@GetMapping("/update/{id}/{status}") String update(@PathVariable Long id, @PathVariable String status) { Project project = projectService.getOne(id); project.setStatus(Status.valueOf(status)); projectService.save(project); return "redirect:/projects"; }
方式二:保持POST请求(符合REST规范)
将a标签改为表单提交(a标签默认是GET请求,无法触发PostMapping):
<form th:action="@{'projects/update/' + ${project.id} + '/' + 'InProgress'}" method="post" style="display: inline;"> <button type="submit" class="btn btn-secondary">InProgress</button> </form>
同时修正Controller的映射路径:
@PostMapping("/update/{id}/{status}") String update(@PathVariable Long id, @PathVariable String status) { Project project = projectService.getOne(id); project.setStatus(Status.valueOf(status)); projectService.save(project); return "redirect:/projects"; }
3. 实现点击后停留在当前页面(无刷新更新)
若要避免页面跳转,需用AJAX异步请求实现:
前端修改
<button class="btn btn-secondary" onclick="updateStatus([[${project.id}]], 'InProgress')">InProgress</button> <!-- 需在页面头部添加CSRF令牌(Spring Boot POST请求必填) --> <meta name="_csrf" th:content="${_csrf.token}"/> <meta name="_csrf_header" th:content="${_csrf.headerName}"/> <script> function updateStatus(projectId, status) { const csrfToken = document.querySelector('meta[name="_csrf"]').content; const csrfHeader = document.querySelector('meta[name="_csrf_header"]').content; fetch('/projects/update/' + projectId + '/' + status, { method: 'POST', headers: { [csrfHeader]: csrfToken } }) .then(response => { if (response.ok) { // 局部更新页面,比如隐藏当前卡片或修改状态显示 event.target.closest('.card-inner').style.display = 'none'; } }) .catch(error => console.error('更新失败:', error)); } </script>
后端调整(返回JSON而非跳转)
修改Controller返回JSON,告知前端更新结果:
@PostMapping("/update/{id}/{status}") @ResponseBody Map<String, String> update(@PathVariable Long id, @PathVariable String status) { Project project = projectService.getOne(id); project.setStatus(Status.valueOf(status)); projectService.save(project); Map<String, String> result = new HashMap<>(); result.put("status", "success"); return result; }
内容的提问来源于stack exchange,提问作者Matthew
相关产品推荐
相关产品推荐

