f:viewParam bean 属性 在通过转换器提交时重新创建

f:viewParam bean property recreated on submit via Converter

我有以下 JSF 页面。我将 id 作为参数传递给它,转换器使用该 ID 在支持 bean 中创建对象。该页面主要用于编辑数据库中的现有记录。按下保存后,我的 roleInformation 对象将使用转换器重新创建,因此未设置来自 inputtext 的新 namedescription,我该如何解决?如何防止 Converter 在单击 commandButton 时插入新的 roleInformation

<ui:composition xmlns="http://www.w3.org/1999/xhtml"
            xmlns:ui="http://java.sun.com/jsf/facelets"
            xmlns:h="http://java.sun.com/jsf/html"
            xmlns:f="http://java.sun.com/jsf/core"
            xmlns:p="http://primefaces.org/ui"
            template="/WEB-INF/template.xhtml">
<ui:define name="metadata">
    <f:metadata>
        <f:viewParam name="id" value="#{roleEdit.roleInformation}"
                     converter="#{roleConverter}"
                     required="true" requiredMessage="Bad request, please use a link from within the system."
                />
        <f:viewAction action="#{roleEdit.init}"/>
    </f:metadata>
</ui:define>
<ui:define name="content">

    <h3>Here you can edit information about the single role #{param} </h3>

    <h:form>
        <p:dataTable id="roleTable" var="roleInformation" value="#{roleEdit.roleInformation}">
            <p:column headerText="Id">
                <h:outputText value="#{roleInformation.id}"/>
            </p:column>
            <p:column headerText="Name">
                <p:inputText value="#{roleInformation.name}"/>
            </p:column>
            <p:column headerText="Description">
                <p:inputText value="#{roleInformation.description}"/>
            </p:column>
        </p:dataTable>
        <br/>
        <p:pickList value="#{roleEdit.rightInformations}" var="rightInformation" itemLabel="#{rightInformation.id}"
                    itemValue="#{rightInformation}" converter="#{rightConverter}">
            <f:facet name="sourceCaption">Available</f:facet>
            <f:facet name="targetCaption">Role rights</f:facet>
            <p:column style="width:100%">
                #{rightInformation.name}
            </p:column>
        </p:pickList>
        <p:commandButton value="Save" action="#{roleEdit.save}">
        </p:commandButton>
    </h:form>
</ui:define>

更新

@ManagedBean(name = "roleEdit")
@ViewScoped
public class Edit implements Serializable {

private DualListModel<RightInformation> rightInformations;
private RoleInformation roleInformation;

@Inject
@RoleServiceJPA
private RoleService roleService;

@Inject
@RightServiceJPA
private RightService rightService;

public void init() {
    List<RightInformation> target = new ArrayList<>();
    List<RightInformation> source = rightService.find(null);
    source.removeAll(roleInformation.getRightInformations());
    target.addAll(roleInformation.getRightInformations());
    rightInformations = new DualListModel<>(source, target);
    System.out.println("init roleinfor tostring " + roleInformation.toString());
}

public String save() {
    System.out.println("role save to string " + roleInformation.toString());
    System.out.println(roleInformation.getName());
    System.out.println(roleInformation.getDescription());
    roleInformation.getRightInformations().clear();
    roleInformation.getRightInformations().addAll(rightInformations.getTarget());
    roleService.updateRole(roleInformation);
    return "role?faces-redirect=true&id=" + roleInformation.getId();
}

角色信息接口

public interface RoleInformation {
long getId();

String getName();

String getDescription();

List<RightInformation> getRightInformations();

void setName(String name);

void setDescription(String description);

}

角色转换器

@ManagedBean
@FacesConverter(forClass = RoleInformation.class)
public class RoleConverter implements Converter, Serializable {

@Inject
@RoleServiceJPA
private RoleService roleService;

@Override
public Object getAsObject(FacesContext facesContext, UIComponent uiComponent, String value) {
    if (value == null || value.isEmpty()) {
        return null;
    }

    Long id = Long.valueOf(value);
    return roleService.findSingle(id);
}

@Override
public String getAsString(FacesContext facesContext, UIComponent uiComponent, Object o) {
    return Long.toString(((RoleInformation) o).getId());
}
}

问题是在我按下 commandButton 时重新创建了支持 bean。 @ManagedBean 是 jsf 注释,在切换到 @Named 之后我能够实现我想要的(没有重新创建支持 bean,因此我能够从 inputText 中保存 String) .