复选框值在 false 时不绑定到对象中?

2022-09-03 12:47:29

我使用ModelAttribute在Spring Web应用程序中绑定对象。

一旦我注意到,如果一个对象的布尔值A为真,如果我们取消选中A的复选框,它的值将不会更新

例如,我有一个 Lesson 对象,其属性为“active” = true。在“编辑课程”视图中,我制作了一个复选框,该复选框绑定到“活动”中。如果选中复选框(绑定对象反映更改),则一切正常,但是如果我们取消选中该复选框,则对象课程不会更改。

进一步的研究告诉我,这是因为复选框值可能不会被浏览器提交(这是HTML的设计)。因此,我必须使用丑陋的 request.getParameter 来检查是否设置了该值。

我只是通过这个问题来,我看到 asp.net mvc提供了一种更优雅地解决它的方法。我认为春天必须提供类似的东西。有人知道如何做到这一点吗?

以下是我的代码:

控制器代码:

    @RequestMapping(value="/test", method = RequestMethod.POST)
    public String processEditLesson(@Valid Lesson lesson, BindingResult bindingResult, Model model) {
        System.out.println("Lesson is active: " + lesson.isActive()); // still "true" even if the checkbox is unset

        // Current work-around
        String isActive = request.getParameter("active");
        if (StringUtils.isNotNullOrEmpty(isActive)) {
            lesson.setActive(true);
        } else {
            lesson.setActive(false);
        }
        ...
    }

查看代码:

<form id="lesson" class="EditorForm" action="${rc.getContextUrl('/test.html')}" method="post" >

    <fieldset>
        <legend><@spring.message code="lesson.edit"/></legend>
        <@spring.formHiddenInput "lesson.id" />
        <@spring.formHiddenInput "lesson.studio.id" />

        <div class="Entry">
            <label for="name"><@spring.message code="lesson.message"/></label>
            <@spring.formInput "lesson.message" />
            <span class="ErrorMessage"><@spring.showErrors "<br/>" /></span>
        </div>

        <input type="checkbox" name="active" checked="checked" />
        <label for="active">${rc.getMessage('lesson.active')}</label>

        <input type="submit" value="<@spring.message code='common.update' />" />
    </fieldset>
</form>

答案 1

Spring有一个内置的解决方法。

只需将此附加隐藏字段添加到表单中:

<input type="hidden" value="on" name="_active"/>

带有前导下划线的参数是某种标记,用于指示存在具有相同名称但没有下划线的复选框参数。

如果仅提交,则现在应将 Spring 设置为 false。lesson.active_active=on


答案 2

我认为你应该使用弹簧框架标签 - 你为什么使用普通的html?如果您的视图是 JSP 页面,只需导入:

<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>

然后您可以使用:

<form:checkbox path="path" label="label" />

它处理了问题。