为什么 Spring Boot MVC 总是从我的表单返回空值?



我已经研究了好几天,但没有一个对我有用。我从互联网上得到的大部分是jsp,但我使用的是Thymeleaf。我正在尝试编写的是一种通用类型的 CRUD,它接受任何类及其变量以成为视图页面的字段标签和输入。

但是,每次我尝试提交填写的表单时,它都会保存在数据库中,但只有 ID 不为空,其他所有内容均为空值。

这是我的方法,它有@ModelAttribute的注释:

@ModelAttribute
public void instantiateEntity(Model model,
@RequestParam("entityName") String entityName)
throws Exception {
String className = SimpleEntity.NAMEPREF + entityName;
SimpleEntity entity =
(SimpleEntity) Class.forName(className).getDeclaredConstructor().newInstance();
Field[] fields = Class.forName(className).getDeclaredFields();
List<FieldUI> fieldUISpecs = new ArrayList<>();
for (Field f : fields) {
System.out.println(f.getName());
FieldUI fieldUI = new FieldUI(f);
UI ui = f.getAnnotation(UI.class);
if (ui != null){
fieldUI.setColHeading(ui.colHeading());
fieldUI.setFldPrompt(ui.fldPrompt());
fieldUI.setCss(ui.css());
fieldUI.setInputHidden(ui.inputHidden());
fieldUI.setColHidden(ui.colHidden());
fieldUI.setType(ui.type());
if(!ui.option().equals("")){
fieldUI.setOption(entityDBA.listEntities(ui.option()));
System.out.println(fieldUI.getOption());
}
System.out.println("n --- CSS: "+fieldUI.getCss());
} else {
fieldUI.setColHeading(f.getName());
fieldUI.setFldPrompt(f.getName());
fieldUI.setColHidden(false);
fieldUI.setInputHidden(false);
}
fieldUISpecs.add(fieldUI);
}
List<SimpleEntity> entities = entityDBA.listEntities(entityName);
model.addAttribute("fieldUISpecs", fieldUISpecs);
model.addAttribute("entity", entity);
model.addAttribute("entities", entities);
model.addAttribute("currentEntity", entityName);
model.addAttribute("displayAddButton", true);
model.addAttribute("displayList", true);
}

这是我的保存控制器:

@PostMapping("/add") 
public String addEntity(@Valid @ModelAttribute("entity") SimpleEntity entity, BindingResult result, Model model, @RequestParam("entityName") String entityName){
List<SimpleEntity> entities = db.listEntities(entityName);
model.addAttribute("displayList", true);
System.out.println("Entity values: "+entityName);
if (result.hasErrors()) {
model.addAttribute("displayForm", true);
model.addAttribute("isNew", true);
return "th_home";
}
db.saveEntity(entity);
return "redirect:/list-edit-entities?entityName="+entityName;}
//Here's my transactional or service layer:
public long saveEntity(SimpleEntity entity) {
long id = 0;
Session ses = sf.getCurrentSession();
if (entity.getId() == 0) ses.persist(entity);
else ses.merge(entity);
return entity.getId();
}

以下是我的观点:

<form th:if="${isNew}" method="POST" th:action="@{'/add?entityName='+${currentEntity}}" th:object="${entity}">
<th:block th:each="field: ${fieldUISpecs}">
<div class="input-group" th:unless="${field.inputHidden}">
<label th:unless="${field.name} == 'id'" th:text="${field.name}"></label>
<input type="hidden" th:if="${field.name} == 'id'" class="c-form" th:field="*{__${field.name}__}" readonly>
<input th:type="${field.type}" th:unless="${field.name} == 'id'" class="c-form" th:field="*{__${field.name}__}">
</th:block>
</div>
</th:block>
<div class="input-group input-button">
<input class="save-button" type="submit" value="Save">
</div>
</form>

您正在使用@ModelAttribute这就是您在提交后在控制器上收到空值的原因。

在请求视图页面的控制器上,需要发送SimpleEntity对象。

例如 -

步骤 1 -

@RequestMapping("/openRequestedPage")
public String addReferralPack(Model model) { 
model.addAttribute("simpleEntityObject", new SimpleEntity());
return "openRequestedPage";
} 

步骤 2 -

<form th:if="${isNew}" method="POST" th:action="@{'/add?entityName='+${currentEntity}}"  th:object="${simpleEntityObject}"">
//Some Code
</form>

步骤 3

@PostMapping("/add") 
public String addEntity(@Valid @ModelAttribute("simpleEntityObject") SimpleEntity entity, BindingResult result, Model model, @RequestParam("entityName") String entityName){
//some code
return "yourPageName";
}

有关@ModelAttribute的信息,这里有一个链接 -

春季 MVC 中的@ModelAttribute是什么?

这是关于它如何工作的参考 -

https://www.baeldung.com/spring-MVC和模型属性注释][1]

最新更新