0

I have a rich:pickList, when submit values it still displays error: "Validation Error: Value is not valid". I also set breakpoint to debug (getAsobject), but after system invocation I had nothing.

BalusC said that I would implement the equals() method in my entities, or I have the entities in the web service, and I fill the right side of the picklist with data from this web service.

xHTML file

            <h:form>
                <rich:panel>
                    <h:panelGrid columns="2" styleClass="criteresSaisie"
                        rowClasses="critereLigne" columnClasses="titreColonne,">

                        <h:outputLabel for="libelleComplement" value="           "
                            size="20" />
                        <rich:pickList id="libelleComplement" sourceCaption="Compléments"
                            targetCaption="Compléments sélectionnés"
                            value="#{listeCmpltDispoModel.listeCmpltSelect}" size="15"
                            addText="&gt;" addAllText="&gt;&gt;" removeText="&lt;"
                            removeAllText="&lt;&lt;" listWidth="270px" listHeight="110px"
                            orderable="true">
                            <f:selectItems value="#{listeCmpltDispoModel.listeCmpltDispo}"
                                var="liste" itemLabel="#{liste.libelleComplement}"
                                itemValue="#{liste}" />
                            <f:converter converterId="cmpltsTitresConcerter" />
                        </rich:pickList>
                    </h:panelGrid>

                    <h:panelGroup>
                        <div align="right">
                            <h:panelGrid columns="8">
                                <h:commandButton value="Valider"
                                    action="#{saisieCmpltsTitreCtrl.valider}" />
                            </h:panelGrid>
                        </div>
                    </h:panelGroup>

                </rich:panel>
            </h:form>

Converter

@FacesConverter(value="cmpltsTitresConcerter")
public class CmpltsTitresConcerter implements Converter
{

public Object getAsObject(FacesContext context, UIComponent component, String value)
{
    ComplementsDispoSortieDTO cmpltSelect= new ComplementsDispoSortieDTO();
    if(value != null)
    {
        cmpltSelect.setCdComplement(Long.parseLong(value));
        //cmpltSelect.setLibelleComplement("aaa");
    }

    return cmpltSelect;
}

public String getAsString(FacesContext arg0, UIComponent arg1, Object obj)
{
    String result = null;

    if(obj != null)
    {
        result = String.valueOf(((ComplementsDispoSortieDTO) obj).getCdComplement());
    }

    return result;
}
}

Model

@ManagedBean(name = "listeCmpltDispoModel")
@SessionScoped
public class ListeCmpltDispoModel implements Serializable {
private static final long serialVersionUID = 1L;

private Long cdComplement;
private String libelleComplement;
private int nbCompl;

private List<ComplementsDispoSortieDTO> listeCmpltDispo ;
private List<ComplementsDispoSortieDTO> listeCmpltSelect ;

public ListeCmpltDispoModel() {
}

public Long getCodeComplement() {
    return cdComplement;
}

public void setCodeComplement(Long cdComplement) {
    this.cdComplement = cdComplement;
}

public String getLibelleComplement1() {
    return libelleComplement;
}

public void setLibelleComplement1(String libelleCoplement) {
    this.libelleComplement = libelleCoplement;
}

public Long getCdComplement() {
    return cdComplement;
}

public void setCdComplement(Long cdComplement) {
    this.cdComplement = cdComplement;
}


public String getLibelleComplement() {
    return libelleComplement;
}

public void setLibelleComplement(String libelleComplement) {
    this.libelleComplement = libelleComplement;
}

public List<ComplementsDispoSortieDTO> getListeCmpltDispo() {
    return listeCmpltDispo;
}

public void setListeCmpltDispo(List<ComplementsDispoSortieDTO> listeCmpltDispo) {
    this.listeCmpltDispo = listeCmpltDispo;
}

public int getNbCompl() {
    return nbCompl;
}

public void setNbCompl(int nbCompl) {
    this.nbCompl = nbCompl;
}

public List<ComplementsDispoSortieDTO> getListeCmpltSelect() {
    return listeCmpltSelect;
}

public void setListeCmpltSelect(List<ComplementsDispoSortieDTO> listeCmpltSelect) {
    this.listeCmpltSelect = listeCmpltSelect;
}

@Override
public int hashCode() {
    final int prime = 31;
    int result = 1;
    result = prime * result
            + ((cdComplement == null) ? 0 : cdComplement.hashCode());
    result = prime
            * result
            + ((libelleComplement == null) ? 0 : libelleComplement
                    .hashCode());
    result = prime * result
            + ((listeCmpltDispo == null) ? 0 : listeCmpltDispo.hashCode());
    result = prime
            * result
            + ((listeCmpltSelect == null) ? 0 : listeCmpltSelect.hashCode());
    result = prime * result + nbCompl;
    return result;
}

@Override
public boolean equals(Object obj){
    if(!(obj instanceof ComplementsDispoSortieDTO)){
        return false;
    }
    return ((ComplementsDispoSortieDTO)obj).getCdComplement()==this.cdComplement;
}
}
Netmaster
  • 287
  • 1
  • 10
  • 27
  • You already gave the answer yourself. What exactly is the problem? Why don't you show the `equals()` of `ComplementsDispoSortieDTO` if you already know that it's one of the possible causes? – BalusC May 24 '13 at 12:47
  • I implemented it, and I still have the same problem, the question is : where can I implement the equals() if I have not acces to the entity ? – Netmaster May 24 '13 at 12:53
  • How exactly did you implement it if you don't have access to the entity? – BalusC May 24 '13 at 12:55
  • I put it in the Model (I edited it), is it right like this ? – Netmaster May 24 '13 at 12:55
  • I call a web service to get data – Netmaster May 24 '13 at 12:55
  • You implemented it in the backing bean instead of the entity representing the selected item. What did you think? This is not right. You need to implement it in the entity. If you can't edit the entity for some reason, just extend it and use it instead. – BalusC May 24 '13 at 12:58
  • thanks, the problem is that I have a web service, in this web service I have entities, and I use dao and dto to use this entities in the service. In th presentation I call this web service to get the data from the database, it's more clear ? here I can't find how can I call the equals() from the presentation – Netmaster May 24 '13 at 13:04
  • You don't need to call it yourself. JSF calls it. Just make sure that the entity (the model, not the backing bean -the controller!) has the `equals()` method implemented. – BalusC May 24 '13 at 13:07
  • If I understand correctly, I implement (or generate!) the equals() in my entities and models, and the JSF well do the rest. Thank you very much, I asked a lot of question because I'm a beginner ;) – Netmaster May 24 '13 at 13:12

2 Answers2

1

The equals() method of your entity is not right. It's not only in the wrong class (the backing bean class instead of the model class), but it's also using == on an Object (the == on an object only tests the reference, not the internal value; as a starter, you should have experienced this mistake on String values already).

The == on a Long would only return true is the Long instance was created by Long#valueOf() or Long#parseLong() and the value is between -128 and 127. Anything else, including new Long(value) and those with values beyond the given "flyweight" range, return false.

As with every other Java object (such as your current one), you need equals() instead. Put it in the right class and implement it as follows:

public class ComplementsDispoSortieDTO {
    
    private Long cdComplement;

    // ...

    @Override
    public boolean equals(Object obj){
        if (!(obj instanceof ComplementsDispoSortieDTO)){
            return false;
        }

        return (cdComplement != null) 
             ? cdComplement.equals(((ComplementsDispoSortieDTO) obj).cdComplement) 
             : (obj == this); 
    }

}

Note that I also added the missing reflexive obj == this. See also the javadoc for list of requirements.

See also:

Community
  • 1
  • 1
BalusC
  • 1,082,665
  • 372
  • 3,610
  • 3,555
-1

I know which could be the solution. You should store the list and selected element in properties and maintain them in the scope as long as the component is used.

MadMad666
  • 955
  • 3
  • 11
  • 19
  • OP has already used `@SessionScoped` for this. This is very definitely not the cause of the problem. – BalusC Aug 29 '13 at 14:34
  • believe or not I removed in a similar situation the equals and hashcode and it worked. Then I decided to use a DTO instead of the real object to maintain in my entity hashcode and equals. But my dto only has the needed attributes + serializable implementation. And finally worked. – MadMad666 Aug 29 '13 at 15:44
  • That can happen if your `equals()` implementation is seriously broken and you're storing references to available items in application scope without ever reloading them from DB. Once you start to reload them from DB, then your approach dies. – BalusC Aug 29 '13 at 15:53