本人在学习Spring路上想实现此类功能,照着《Spring实战》依葫芦画瓢都无法实现,下面是我写的一个demo,如果你们也遇到这个问题,可以看看能否解决
先上demo项目的目录
上后端代码和前端代码
//成年人信息Data类
package com.validError.demo.Configuration;
import lombok.Data;
import javax.validation.constraints.Min;
@Data
public class AdultData {
@Min(value = 18, message = "年龄不得小于18")
private Integer age;
}
//Controller类
package com.validError.demo.Controller;
import com.validError.demo.Configuration.AdultData;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.Errors;
import org.springframework.web.bind.annotation.*;
import javax.validation.Valid;
@Controller
@RequestMapping("/home")
public class InquiryAdultData {
@GetMapping
public String get(Model model){
model.addAttribute("adult", new AdultData());
return "Upload";
}
@PostMapping
public String add(@Valid AdultData adultData,
Errors errors, Model model) {
model.addAttribute("adult", adultData);
if (errors.hasErrors()) {
return "Upload";
}
return "Succeed";
}
}
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>Title</title>
<style>
.errorText{ color:red; }
</style>
</head>
<body>
<form th:action="@{/home}" method="post" th:object="${adult}">
<label>请输入你的年龄</label>
<input type="number" th:field="*{age}"/>
<span class="errorText"
th:if="${#fields.hasErrors('age')}"
th:errors="*{age}">age Error</span><br/>
<input type="submit" value="提交">
</form>
</body>
</html>
可以看到后端发送了一个名为"adult"的对象给了前端,前端引用了这个对象,并在输入框中引用了adult对象的age属性
理想状态:如果age<18将会报错
可是实际上并没有提示年龄不得小于18岁,这里给出个人的见解,并且提出两种解决办法
在InquiryAdultData类中的add方法第一行代码,我期望通过model.addAttribute("adult", adultData);
将adultData实例再次发送给前端,因为如果不添加将报错,所以我只能添加了
问题就出在此!
个人理解为:使用addAttribute()意味着添加了一个新的名键对,而前端并不知道这个叫做"adult"的还是原来的"adult",毕竟我也可以将model.addAttribute("adult", adultData);
换成model.addAttribute("adult", new AdultData());
,所以Spring就将原来的"adult"里的内容抹去,换成新的"adult"所指的对象,因此我们会误以为还是原来的对象只是我重新发送给前端了而已(实际上原先的对象还夹带的信息被抹去了,例如这里的errors)
那么如何解决?
在《Spring实战》一书中,我并没看到他需要加形如model.addAttribute();
的代码将对象重新发送给前端,原因在于他的前端引用的是对象名的小写形式(开头小写的驼峰式名称)而我的前端引用的是"adult"而不是"adultData"
解决方法一:让我们去适应Spring的机制
对后端代码进行的微调:
对前端代码进行的微调:
这样,前端就能正常显示对象返回过来的错误信息
解决方法二:让Spring机制适应我们
只要添加注解@ModelAttribute(“自定义的名值”)即可,前端使用的${adult}
便不用作更改了
最后,如果我哪里有纰漏的或理解有误的,欢迎大家来指正~