JSF 2 - f:ajax标签不起作用

时间:2010-08-13 12:04:08

标签: java ajax facelets jsf-2

我遇到f:ajax标签的问题。在我以前的项目中,一切都很完美。现在我有另一个项目和f:ajax标签根本不起作用,我不知道为什么。

我在带有Facelets的JSF页面中有这个:

<h:form>
...
    <h:selectOneMenu id="employeeId" value="#{employeeBean.employeeId}">
        <f:selectItems value="#{employeeBean.employeesSelectItem}"/>
        <f:ajax event="change" listener="#{employeeBean.changeOwner}"/>
     </h:selectOneMenu>
...
</h:form>

使用带有数据库访问权限的changeOwner方法的employeeBean:

...
public void changeOwner(AjaxBehaviorEvent event) {
    try {
        update.updateOwner(...params...);
        JSF.setMessage(Messages.UPDATE_OK);
    } catch (UpdateDBException ex) {
        JSF.setMessage(ex.getMessage());
    }
}
...

我看不出有什么不对。谢谢你的帮助。

更新

面-配置:

<faces-config version="2.0"
    xmlns="http://java.sun.com/xml/ns/javaee" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facesconfig_2_0.xsd">

    <converter>
        <converter-for-class>java.util.Date</converter-for-class>
        <converter-class>misc.TimeZoneConverter</converter-class>
    </converter>
</faces-config>

xhtml页面:

<ui:composition xmlns:ui="http://java.sun.com/jsf/facelets"
            template="./../templates/mainTemplate.xhtml"
            xmlns:h="http://java.sun.com/jsf/html"
            xmlns:f="http://java.sun.com/jsf/core">

<ui:define name="content">
    <h2>Smazání zaměstnance</h2>
            Protože s daným zaměstnancem (#{employeeBean.employee.name} #{employeeBean.employee.surname}) souvisejí některé úkoly, je potřeba, aby se jich ujal jiný. Vyberte prosím nové zaměstnance u všech níže uvedených úkolů.
            <h:form>
                <h:dataTable value="#{taskBean.employeeTasks}" var="item">
                    <h:column>
                        <f:facet name="header">ID</f:facet>
                        <center>#{item.idtask}</center>
                    </h:column>
                    <h:column>
                        <f:facet name="header">Zadavatel</f:facet>
                        <h:selectOneMenu id="managerId" value="#{employeeBean.newManagerId}" rendered="#{employeeBean.employeeId == item.employeeByIdmanager.idemployee}">
                            <f:selectItems value="#{employeeBean.otherEmployeesSelectItem}"/>
                            <f:ajax event="change" listener="#{employeeBean.changeOwner}"/>
                        </h:selectOneMenu>
                        <h:outputText value="#{item.employeeByIdmanager.name} #{item.employeeByIdmanager.surname}" rendered="#{employeeBean.employeeId != item.employeeByIdmanager.idemployee}"/>
                    </h:column>
                    <h:column>
                        <f:facet name="header">Zodpovědná osoba</f:facet>
                        <h:selectOneMenu id="employeeId" value="#{employeeBean.newEmployeeId}" rendered="#{employeeBean.employeeId == item.employeeByIdemployee.idemployee}">
                            <f:selectItems value="#{employeeBean.otherEmployeesSelectItem}"/>
                            <f:ajax event="change" listener="#{employeeBean.changeOwner}"/>
                        </h:selectOneMenu>
                        <h:outputText value="#{item.employeeByIdemployee.name} #{item.employeeByIdemployee.surname}" rendered="#{employeeBean.employeeId != item.employeeByIdemployee.idemployee}"/>
                    </h:column>
                    <h:column>
                        <f:facet name="header">Čas zadání</f:facet>
                        <center><h:outputText value="#{item.timestart}"/></center>
                    </h:column>
                    <h:column>
                        <f:facet name="header">Udělat do</f:facet>
                        <center><h:outputText value="#{item.timetodo}"/></center>
                    </h:column>
                    <h:column>
                        <f:facet name="header">Popis úkolu</f:facet>
                        #{item.text}
                    </h:column>
                    <h:column>
                        <f:facet name="header">Zákazník</f:facet>
                        <h:link outcome="viewCustomerDetails">
                            <h:panelGrid columns="1">
                                <h:outputText value="#{item.customer.name}"/>
                                <h:outputText value="#{item.customer.addresscity}"/>
                            </h:panelGrid>
                            <f:param name="customerId" value="#{item.customer.idcustomer}"/>
                        </h:link>
                    </h:column>
                    <h:column>
                        <f:facet name="header">Stav úkolu</f:facet>
                        #{item.taskstate.state}
                    </h:column>
                    <h:column>
                        <f:facet name="header">Poznámky</f:facet>
                        <h:outputText escape="false" value="#{item.note}"/>
                    </h:column>
                </h:dataTable>
            </h:form>

    <h:messages globalOnly="true" styleClass="messages"/>
</ui:define>

UPDATE2

引用EmployeeBean:

package beans;
import beans.jsf.JSF;
import ejb.Get;
import ejb.Update;
import entities.Employee;
import entities.Permission;
import java.util.ArrayList;
import java.util.List;
import javax.ejb.EJB;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ManagedProperty;
import javax.faces.bean.RequestScoped;
import javax.faces.model.SelectItem;
import javax.validation.constraints.Pattern;
import misc.Messages;

@ManagedBean(name="employeeBean")
@RequestScoped
public class EmployeeBean {

@EJB
private Get get;

@EJB
private Update update;

@ManagedProperty(name="employeeId", value="#{param['employeeId']}")
private int employeeId;

private int newManagerId;

private int newEmployeeId;

private String edit = "none";

@Pattern(regexp=".+", message="Jméno musí být vyplněno.")
private String name;

@Pattern(regexp=".+", message="Příjmení musí být vyplněno.")
private String surname;

private int permissionId;

private Employee employee;

/** Creates a new instance of EmployeeBean */
public EmployeeBean() {
}

public int getNewEmployeeId() {
    return newEmployeeId;
}

public void setNewEmployeeId(int newEmployeeId) {
    this.newEmployeeId = newEmployeeId;
}

public int getNewManagerId() {
    return newManagerId;
}

public void setNewManagerId(int newManagerId) {
    this.newManagerId = newManagerId;
}

public int getEmployeeId() {
    return employeeId;
}

public void setEmployeeId(int employeeId) {
    this.employeeId = employeeId;
    employee = get.getEmployee(employeeId);
}

public String getEdit() {
    return edit;
}

public void setEdit(String edit) {
    this.edit = edit;
}

public String getName() {
    return name;
}

public void setName(String name) {
    this.name = name;
}

public int getPermissionId() {
    return permissionId;
}

public void setPermissionId(int permissionId) {
    this.permissionId = permissionId;
}

public String getSurname() {
    return surname;
}

public void setSurname(String surname) {
    this.surname = surname;
}

public Employee getEmployee() {
    return employee;
}

public void setEmployee(Employee employee) {
    this.employee = employee;
}

private void showEdit() {
    edit = "block";
}

private void hideEdit() {
    edit = "none";
}

/**
 * Naplní SelectItem všemi zaměstnanci.
 * @return seznam zaměstnanců
 */
public List<SelectItem> getEmployeesSelectItem() {
    List<SelectItem> employees = new ArrayList<SelectItem>();

    for (Employee e : get.getEmployees()) {
        employees.add(new SelectItem(e.getIdemployee(), e.getName() + " " + e.getSurname()));
    }

    return employees;
}

/**
 * Vrátí seznam zákazníků.
 * @return seznam zákazníků
 */
public List<Employee> getEmployees() {
    return get.getEmployees();
}


/**
 * Načte úkol pro editaci.
 */
public void loadEmployee() {
    Employee e = get.getEmployee(employeeId);

    if (e != null) {
        name = e.getName();
        surname = e.getSurname();
        permissionId = e.getPermission().getIdpermission();

        showEdit();
    } else {
        JSF.setMessage(Messages.DB_RETURN_NULL);
    }
}

/**
 * Naplní SelectItem všemi oprávněními.
 * @return seznam oprávnění
 */
public List<SelectItem> getPermissionsSelectItem() {
    List<SelectItem> permissions = new ArrayList<SelectItem>();

    for (Permission p : get.getPermissions()) {
        permissions.add(new SelectItem(p.getIdpermission(), p.getPermissionname()));
    }

    return permissions;
}    

/**
 * Zapíše úpravy úkolu.
 */
public void updateEmployee() {
    try {
        update.updateEmployee(name, surname, employeeId, permissionId);
        JSF.setMessage(Messages.EMPLOYEE_UPDATE_OK);
    } catch (Exception ex) {
        showEdit();
        JSF.setMessage(ex.getMessage());
    } 
}

/**
 * Zruší prováděné úpravy a skryje editaci.
 */
public void cancel() {
    hideEdit();
}

public void changeOwner(int taskId) {
    System.out.println("taskId: "+taskId);
    System.out.println("managerId: "+newManagerId);
    System.out.println("employeeId: "+newEmployeeId);
//        try {
//            update.updateOwner(taskId, newManagerId, newEmployeeId);
//            JSF.setMessage(Messages.UPDATE_OK);
//        } catch (UpdateDBException ex) {
//            JSF.setMessage(ex.getMessage());
//        }
}

/**
 * Naplní SelectItem všemi možnými stavy pro úkol.
 * @return seznam stavů úkolu
 */
public List<SelectItem> getOtherEmployeesSelectItem() {
    List<SelectItem> employees = new ArrayList<SelectItem>();

    for (Employee e : get.getOtherEmployees(employeeId)) {
        employees.add(new SelectItem(e.getIdemployee(), e.getName() + " " + e.getSurname()));
    }

    return employees;
}
}

2 个答案:

答案 0 :(得分:4)

这仅在输入元素位于表单内时才有效。因此,将整个菜单放在<h:form>


更新: f:ajax实际上是一个JSF 2.0标记。如果您更改了JSF库或faces-config.xml以符合JSF 1.2,那么f:ajax将停止工作。验证您是否使用了正确的版本化库,并且任何faces-config.xml的根声明都设置为JSF 2.0。

如果这没有帮助,那么我没有看到其他原因,而不是您没有运行您认为正在运行的代码。你读过服务器日志了吗?你运行调试器了吗?您是否消除了周围的代码,以便JSF页面最终只使用 代码中的h:body内的代码?


更新2: EmployeeBean设置为@RequestScoped,这意味着它在请求结束时(在发送响应之后)被攻击。员工的加载取决于是否存在已设置为请求参数的员工ID。基本上,您需要在每个请求上传递员工ID,以便让员工加载,包括ajaxical请求。此外,下拉列表的呈现取决于请求中是否存在有效员工。如果呈现的条件在ajaxical请求期间评估false,则不会调用ajax操作。我不确定这个复杂的情况,但理论上将员工ID作为隐藏参数传递应该有所帮助:

<h:inputHidden value="#{employeeBean.employeeId}" />

将其放在表格旁边的表格中。

答案 1 :(得分:1)

由于f:ajax listener期望AjaxBehaviorEvent

将其更改为:

public void changeOwner(AjaxBehaviorEvent event) {
    try {
        update.updateOwner(...params...);
        JSF.setMessage(Messages.UPDATE_OK);
    } catch (UpdateDBException ex) {
        JSF.setMessage(ex.getMessage());
    }
}

已编辑:检查表单中的任何其他组件是否阻止提交表单。 (也许是h:selectonemenu等。)