为什么这个 ajax @form 提交没有更新和渲染模型值?

Why is this ajax @form submit not updating and rendering model values?

我遇到以下情况,使用 ajax 提交表单时出现问题:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html
        PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
        "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
    xmlns:h="http://java.sun.com/jsf/html"
    xmlns:f="http://java.sun.com/jsf/core" xml:lang="en" lang="en"
    xmlns:ui="http://java.sun.com/jsf/facelets">
<h:head>
<h:outputStylesheet library="css" name="employee.css"  />

    <title>Welcome</title>
</h:head>
<h:body>
<h:form>
    <h:panelGrid>
        <h:outputLabel for="first_name" value="First Name" />
        <h:inputText id="first_name"
            value="#{employeeController.model.firstName}" required="true" />

        <h:outputLabel for="last_name" value="Last Name" />
        <h:inputText id="last_name"
            value="#{employeeController.model.lastName}" required="true" />

        <h:outputLabel for="email" value="Email" />
        <h:inputText id="email" value="#{employeeController.model.email}"
            required="true" />

        <h:outputLabel for="phone_number" value="Phone" />
        <h:inputText id="phone_number"
            value="#{employeeController.model.phoneNumber}" required="true" />

        <h:outputLabel for="salaray" value="Salary" />
        <h:inputText id="salaray" value="#{employeeController.model.salary}"
            required="true" />

        <h:commandButton value="Save(AJAX)">
            <f:ajax execute="@form" render="modelOutput"/>
        </h:commandButton>
    </h:panelGrid>
</h:form>
    <h:panelGrid id="modelOutput">
        <h:outputText id="fName"
            value="First Name: #{employeeController.model.firstName}" />
        <h:outputText value="Last Name: #{employeeController.model.lastName}" />
        <h:outputText value="E-Mail: #{employeeController.model.email}" />
        <h:outputText
            value="Phonenumber: #{employeeController.model.phoneNumber}" />
        <h:outputText value="Salary: #{employeeController.model.salary}" />
    </h:panelGrid>
</h:body>
</html>

该模型是一个简单的 javabean,只有 getter 和 setter 的值。

当我单击 ajax 按钮时,我可以看到发送到服务器的请求,其中包含我的表单数据。 我用输出文本的硬编码值得到了部分响应——但没有模型值。 我可以看到我的 setter 也没有被调用。

如果我将 ajax execute 更改为特定的 inputText 组件 ID - 它将适用于该组件 ID。

我错过了什么?

-- EmployeeBean

public class EmployeeBean {

    private String firstName;
    private String lastName;

    private String email;
    private String phoneNumber;
    private Float salary;

    public String getFirstName() {
        return firstName;
    }

    public void setFirstName(String firstName) {
        this.firstName = firstName;
    }

    public String getLastName() {
        return lastName;
    }

    public void setLastName(String lastName) {
        this.lastName = lastName;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

    public String getPhoneNumber() {
        return phoneNumber;
    }

    public void setPhoneNumber(String phoneNumber) {
        this.phoneNumber = phoneNumber;
    }

    public Float getSalary() {
        return salary;
    }

    public void setSalary(Float salary) {
        this.salary = salary;
    }



}

雇员控制器:

@ManagedBean
@RequestScoped
public class EmployeeController {

    private EmployeeBean model;

    @PostConstruct
    public void init() {
        model = new EmployeeBean();
    }

    public EmployeeBean getModel() {
        return model;
    }

    public void clearAjax(AjaxBehaviorEvent ajaxBehaviorEvent) {
        clearUiAreaForm(ajaxBehaviorEvent.getComponent());
        System.out.println("Form cleared");
    }
}

所以我找到了原因解决方法

主要问题如下:

从生命周期侦听器中,我看到服务器端的处理跳过了阶段 4 和 5。 这是什么原因? 好吧 - 第 3 阶段是关于验证的。我的表单有一些验证限制,即 required.

我没有填写所有输入字段,因此验证阶段不成功。 JSF 然后跳过阶段 4 和 5 - 现在我们也知道为什么没有调用 setter。

踢球者来了: 它完全无声地失败了! 您确实得到了一个很好的 ajax 请求,其中包含表单参数。而且您确实得到了很好的部分响应 - 但没有来自 bean 的动态值。

应用程序日志中没有错误消息(嗯,应该也有 none 但这会让您知道没有异常)。 但显然 Ajax 不会像使用整页请求时那样填充任何组件。 您没有关于验证失败的任何信息。 如果您不使用生命周期信息输出,那么您将无法以任何方式看到它。

此外,我唯一能找到的是添加一个组件来呈现一些信息。添加一个硬编码的 outputText,它只会在 facesContext.validationFailed 的信息上呈现,并由 ajax facelet 呈现。

<h:commandButton value="Save (AJAX)">
                <f:ajax execute="@form" render="modelOutput global_flag_validation_failed_render" />
            </h:commandButton>
            <h:messages />
            <h:panelGroup id="global_flag_validation_failed_render">
                <h:outputText id="global_flag_validation_failed" value="Fehler in Ajax aufgetreten!"
                    rendered="#{facesContext.validationFailed}" />
            </h:panelGroup>

我不知道这是否是 Mojarra 2.2.14 指定和想要的行为 - 有人知道吗?