@FacesConverter предотвращает вызов методов p: selectOneMenu и p: ajax - PullRequest
2 голосов
/ 13 января 2012

У меня странная проблема с пользовательским @FacesConverter с JBoss-7.1.0.CR1b во время вызова AJAX в p:selectOneMenu (Primefaces 3.0).

Упрощенный конвертер выглядит следующим образом:нет NPE или других исключений в этом классе

@FacesConverter("MyConverter")
public class MyConverter implements Converter
{      
  public Object getAsObject(FacesContext fc, UIComponent uic, String value)
  {
    logger.debug("getAsObject value: "+value);
    if (submittedValue.trim().equals("")) {return null;}
    else
    {           
      MyEjb ejb = new MyEjb();
      ejb.setId(Long.parseLong(value()));
      return ejb;  //**** alternative with return null; ****
    }
  }  
  public String getAsString(FacesContext fc, UIComponent uic, Object value)
  { 
    if (value == null || value.equals("")) {return "";}
    else
    {
        MyEjb ejb = (MyEjb)value;
        return ""+ejb.getId(); 
    }  
  }  
}

Конвертер используется в p:selectOneMenu:

<h:form>  
  <p:selectOneMenu value="#{clientBean.selected}" converter="MyConverter">
    <f:selectItems value="#{clientBean.all}" var="my"
                   itemLabel="#{my.name}" itemValue="#{my}"/>
      <p:ajax listener="#{clientBean.changed}" />  
  </p:selectOneMenu>
</h:form>

Это не ракетостроение, измененный метод просто делает отладку:

public void changed()
{
  logger.info("changed() "+selected);
}

Но теперь раздражающая часть: changed() никогда не вызывается с кодом, как описано выше, но я получаю вызов преобразователя три раз:

12:37:51,500 DEBUG getAsObject value: 35
12:37:51,502 DEBUG getAsObject value:
12:37:51,503 DEBUG getAsObject value:

Если я изменю p:selectOneMenu value="#{clientBean.selectedId}" на long selectedId и не буду использовать конвертер, метод вызывается один раз.Даже если я return null в getAsObject(), changed() называется (один раз).Я не предполагаю, что это связано с Primefaces, потому что у меня такое же поведение, если я использую h:selectOneMenu и f:ajax.

1 Ответ

5 голосов
/ 13 января 2012

У вас должны быть <p:messages />, <p:growl /> или <h:messages />, которые, по вашему мнению, были обновлены с помощью ajax. Также следует обратить внимание на предупреждения в журналах сервера о возможных сообщениях о пропавших лицах. Вероятность того, что вы увидите печально известную Validation error: Value not valid ошибку проверки, велика.

После преобразования JSF проверит, является ли предоставленный объект одним из доступных элементов в рамках защиты от подделанных / взломанных запросов. JSF сделает это по submittedObject.equals(oneOfAvailableObjects) для каждого из доступных объектов, как у вас там в <f:selectItems>. Если ничего не найдено, JSF отобразит эту ошибку проверки.

В вашем конкретном случае класс MyEjb, по-видимому, не имеет метода equals() или его реализация нарушена. См. Также Правильный способ реализации контракта равных .

...