PrimeFaces Datatable CellEditor — разные значения для ввода и вывода фасетов

У меня есть редактируемый DataTable для пользователя объекта. В этой таблице есть поле с именем пользователя, которое имеет уникальное ограничение.

    <h:form id="form">
<p:dataTable id="userTable" value="#{users}" var="entity" editable="true" editMode="cell" tableStyle="width:auto">
<p:ajax event="cellEdit" listener="#{userController.onCellEdit}" update="form:msgs form:display form:userTable" />
<p:column headerText="UserID">
<p:outputLabel value="#{entity.id}" />
</p:column>
<p:column headerText="Username">
<p:cellEditor>
<f:facet name="output"><p:outputLabel for="username" value="#{entity.username}" /></f:facet>
<f:facet name="input">
<p:inputText id="username" value="#{entity.username}" >
<f:validateRequired />
<f:validateLength maximum="50" />
</p:inputText>
</f:facet>
</p:cellEditor>
</p:column>
</p:dataTable>
</h:form>

В пользовательском контроллере bean-компонента поддержки у меня есть следующий метод onCellEdit

public void onCellEdit(CellEditEvent event) {
        Object newValue = event.getNewValue();
        String columnName = event.getColumn().getHeaderText();
        facesContext = FacesContext.getCurrentInstance();
        User entity = facesContext.getApplication().evaluateExpressionGet(facesContext, "#{entity}", User.class);
        if(columnName.equals("Username") {
            entity.setUsername((String) newValue);
        }


        try {
            service.createOrUpdateEntity(entity);
        }
        catch (EJBTransactionRolledbackException ex) {
            Throwable t = ex.getCause();
            while (t != null) {
                t = t.getCause();
                if(t.getClass().getSimpleName().equals("SQLIntegrityConstraintViolationException")) {
                        entity.setUsername((String) event.getOldValue());
                    facesContext.addMessage(null, new FacesMessage(FacesMessage.SEVERITY_WARN, "Duplicate entry for the field username. Write a different username", ""));
                    break;
                }
            }
            return;
        }
        catch (Exception e) {
            e.printStackTrace();
        }

Проблема заключается в том, что при перехвате исключения конечное значение для ввода фасета отличается от значения из вывода фасета. В этом случае выходные данные фасета показывают правильное значение, а входные данные фасета показывают значение, вызвавшее исключение.


person julianfperez    schedule 28.03.2017    source источник


Ответы (1)


Вам необходимо убедиться, что компонент UIInput был сброшен до исходных значений. Компонент UIInput можно получить из файла CellEditEvent.

((UIInput)event.getComponent()).resetValue();

Вышеприведенное предполагает, что вы проверили возврат из getComponent() на нуль и безопасность типов. Вот API для UIInput.

person axemoi    schedule 30.03.2017