This discussion is archived
11 Replies Latest reply: Feb 17, 2013 5:55 AM by REDO LOG RSS

enumeration convertion in jsf

REDO LOG Newbie
Currently Being Moderated
Hi all
I am about dealing with enumerations in my academic JSF project
so, I have an entity Employee:
package com.entities;

import com.enumeration.Gender;
import java.io.Serializable;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.EnumType;
import javax.persistence.Enumerated;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.NamedQuery;


@Entity
@NamedQuery(name="Employee.findAll", query="SELECT e FROM Employee e")
public class Employee implements Serializable {
    
    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Integer id;
    @Column(name="nom", length=30)
    private String nom;
    @Enumerated(EnumType.STRING)
    @Column(length=1)
    private Gender gender;

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getNom() {
        return nom;
    }

    public void setNom(String nom) {
        this.nom = nom;
    }

    public Gender getGender() {
        return gender;
    }

    public void setGender(Gender gender) {
        this.gender = gender;
    }

    

    @Override
    public int hashCode() {
        int hash = 0;
        hash += (id != null ? id.hashCode() : 0);
        return hash;
    }

    @Override
    public boolean equals(Object object) {
        // TODO: Warning - this method won't work in the case the id fields are not set
        if (!(object instanceof Employee)) {
            return false;
        }
        Employee other = (Employee) object;
        if ((this.id == null && other.id != null) || (this.id != null && !this.id.equals(other.id))) {
            return false;
        }
        return true;
    }

    @Override
    public String toString() {
        return "com.entities.Employee[ id=" + id + " ]";
    }
    
}
the enumeration:
/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package com.enumeration;

import java.io.Serializable;


public enum Gender implements Serializable{

    M("Male"), F("Female");
    private String description;

    private Gender(String description) {
        this.description = description;
    }

    public String getDescription() {
        return description;
    }
    

    
}
and the index page that shows the list of employees:
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
      xmlns:h="http://java.sun.com/jsf/html"
      xmlns:f="http://java.sun.com/jsf/core"
      xmlns:p="http://primefaces.org/ui">
    <h:head>
        <title>Facelet Title</title>
    </h:head>
    <h:body>
        <f:view>
            <h:form>
                <h1><h:outputText value="List"/></h1>
                <h:dataTable value="#{employee.employees}" var="item" id="liste">
                    <h:column>
                        <f:facet name="header">
                            <h:outputText value="Id"/>
                        </f:facet>
                        <h:outputText value="#{item.id}"/>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText value="Nom"/>
                        </f:facet>
                        <h:outputText value="#{item.nom}"/>
                    </h:column>
                    <h:column>
                        <f:facet name="header">
                            <h:outputText value="Gender"/>
                        </f:facet>
                        <h:outputText value="#{item.gender}"/>
                    </h:column>
                </h:dataTable>
            
                        <h1><h:outputText value="Create/Edit"/></h1>
                        <h:panelGrid columns="2">
                            <h:outputLabel value="Nom:" for="nom" />
                            <h:inputText id="nom" value="#{employee.newEmployee.nom}" title="Nom" />
                            
                            <h:outputLabel value="Gender:" for="gender" />
                            <h:selectOneMenu value="#{employeeBean.newEmployee.gender}" id="gender">
                                <f:selectItem itemLabel="Male" itemValue="Male"/>
                                <f:selectItem itemLabel="Female" itemValue="Female"/>
                            </h:selectOneMenu>
                            
                        </h:panelGrid>
                        <h:commandButton value="ajouter" action="index.xhtml" actionListener="#{employeeBean.ajouter}" />
                    </h:form>
        </f:view>
    </h:body>
</html>
with the ejb associated( not included here)

the problem I am facing is to convert the field selected in the selectOneMenu to an enumeration
I did some search and I found that I have to add a converter class the faces-config.xml file, but still facing the same problem

I am sure that I missed understood something with this but cannot detect what it is wrong with

thanks for any help
  • 1. Re: enumeration convertion in jsf
    r035198x Pro
    Currently Being Moderated
    Have you tried the suggestion given here:Enumerations in JPA ?
  • 2. Re: enumeration convertion in jsf
    REDO LOG Newbie
    Currently Being Moderated
    yes I did, but still facing the same problem
  • 3. Re: enumeration convertion in jsf
    r035198x Pro
    Currently Being Moderated
    What exactly is the problem? Do you get errors/exceptions?
  • 4. Re: enumeration convertion in jsf
    REDO LOG Newbie
    Currently Being Moderated
    here is what I am searching to do:

    the form is used to add new employees to the database,
    the employees in the database are stored with there Ids, names and there gender,

    in the gender column I just want to store one character so I create an enumeration Gender as :

    package com.enumeration;
    
    
    public enum Gender {
        Male('M'), Female('F');
        
        private char value;
    
        public char getValue() {
            return value;
        }
        
        private Gender(char value){
            this.value = value;
        }
    }
    and the employee entity as :
    package com.entities;
    
    import com.enumeration.Gender;
    import java.io.Serializable;
    import javax.persistence.Column;
    import javax.persistence.Entity;
    import javax.persistence.EnumType;
    import javax.persistence.Enumerated;
    import javax.persistence.GeneratedValue;
    import javax.persistence.GenerationType;
    import javax.persistence.Id;
    import javax.persistence.NamedQuery;
    
    
    @Entity
    @NamedQuery(name="Employee.findAll", query="SELECT e FROM Employee e")
    public class Employee implements Serializable {
        
        private static final long serialVersionUID = 1L;
        @Id
        @GeneratedValue(strategy = GenerationType.AUTO)
        private Integer id;
        @Column(name="nom", length=30)
        private String nom;
        @Enumerated(EnumType.STRING)
        @Column(length=1)
        private Gender gender;
    
        public Integer getId() {
            return id;
        }
    
        public void setId(Integer id) {
            this.id = id;
        }
    
        public String getNom() {
            return nom;
        }
    
        public void setNom(String nom) {
            this.nom = nom;
        }
    
        public Gender getGender() {
            return gender;
        }
    
        public void setGender(Gender gender) {
            this.gender = gender;
        }
    
        
    }
    in the jsf form I will have a combobox that shows Female and Male strings ,
    then when Female is picked up for example the letter to be stored in the database is F


    sorry for being annoying, but couldn't really get it sorted(at the moment)
    thanks for help
  • 5. Re: enumeration convertion in jsf
    r035198x Pro
    Currently Being Moderated
    You don't need to explain the whole project again and you don't need to keep posting the enum and the entity, the important things here are the section of your page that uses the enum and the backing bean method that is used by that section. Just explain what is happening with the enums and h:selectOneMenu. Is it throwing an exception? What is happening?
  • 6. Re: enumeration convertion in jsf
    REDO LOG Newbie
    Currently Being Moderated
    here is the message shown when I click on the button: j_idt7:gender: 'Female' must be convertible to an enum.

    the combo box is
    <h:outputLabel value="Gender:" for="gender" />
                        <h:selectOneMenu value="#{employeeBean.newEmployee.gender}" id="gender">
                            <f:selectItem itemLabel="Male" itemValue="Male" />
                            <f:selectItem itemLabel="Female" itemValue="Female"/>
                        </h:selectOneMenu>
  • 7. Re: enumeration convertion in jsf
    r035198x Pro
    Currently Being Moderated
    Use
    <f:selectItems value="#{employeeBean.genders}" /> 
    for your select items and add a method getGenders in the backing bean that returns an array of all Gender enums using Gender.values()
  • 8. Re: enumeration convertion in jsf
    REDO LOG Newbie
    Currently Being Moderated
    here is the log content after submitting the values:
    WARNING: Local Exception Stack: 
    Exception [EclipseLink-4002] (Eclipse Persistence Services - 2.2.0.v20110202-r8913): org.eclipse.persistence.exceptions.DatabaseException
    Internal Exception: com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException: Duplicate entry '1' for key 'PRIMARY'
    Error Code: 1062
    Call: INSERT INTO EMPLOYEE (ID, GENDER, nom) VALUES (?, ?, ?)
         bind => [3 parameters bound]
    Query: InsertObjectQuery(com.entities.Employee[ id=1 ])
         at org.eclipse.persistence.exceptions.DatabaseException.sqlException(DatabaseException.java:324)
         at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.executeDirectNoSelect(DatabaseAccessor.java:798)
         at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.executeNoSelect(DatabaseAccessor.java:864)
         at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.basicExecuteCall(DatabaseAccessor.java:583)
         at org.eclipse.persistence.internal.databaseaccess.DatabaseAccessor.executeCall(DatabaseAccessor.java:526)
         at org.eclipse.persistence.internal.sessions.AbstractSession.basicExecuteCall(AbstractSession.java:1729)
         at org.eclipse.persistence.sessions.server.ClientSession.executeCall(ClientSession.java:234)
         at org.eclipse.persistence.internal.queries.DatasourceCallQueryMechanism.executeCall(DatasourceCallQueryMechanism.java:207)
         at org.eclipse.persistence.internal.queries.DatasourceCallQueryMechanism.executeCall(DatasourceCallQueryMechanism.java:193)
         at org.eclipse.persistence.internal.queries.DatasourceCallQueryMechanism.insertObject(DatasourceCallQueryMechanism.java:342)
         at org.eclipse.persistence.internal.queries.StatementQueryMechanism.insertObject(StatementQueryMechanism.java:162)
         at org.eclipse.persistence.internal.queries.StatementQueryMechanism.insertObject(StatementQueryMechanism.java:177)
         at org.eclipse.persistence.internal.queries.DatabaseQueryMechanism.insertObjectForWrite(DatabaseQueryMechanism.java:469)
         at org.eclipse.persistence.queries.InsertObjectQuery.executeCommit(InsertObjectQuery.java:80)
         at org.eclipse.persistence.queries.InsertObjectQuery.executeCommitWithChangeSet(InsertObjectQuery.java:90)
         at org.eclipse.persistence.internal.queries.DatabaseQueryMechanism.executeWriteWithChangeSet(DatabaseQueryMechanism.java:291)
         at org.eclipse.persistence.queries.WriteObjectQuery.executeDatabaseQuery(WriteObjectQuery.java:58)
         at org.eclipse.persistence.queries.DatabaseQuery.execute(DatabaseQuery.java:808)
         at org.eclipse.persistence.queries.DatabaseQuery.executeInUnitOfWork(DatabaseQuery.java:711)
         at org.eclipse.persistence.queries.ObjectLevelModifyQuery.executeInUnitOfWorkObjectLevelModifyQuery(ObjectLevelModifyQuery.java:108)
         at org.eclipse.persistence.queries.ObjectLevelModifyQuery.executeInUnitOfWork(ObjectLevelModifyQuery.java:85)
         at org.eclipse.persistence.internal.sessions.UnitOfWorkImpl.internalExecuteQuery(UnitOfWorkImpl.java:2842)
         at org.eclipse.persistence.internal.sessions.AbstractSession.executeQuery(AbstractSession.java:1521)
         at org.eclipse.persistence.internal.sessions.AbstractSession.executeQuery(AbstractSession.java:1503)
         at org.eclipse.persistence.internal.sessions.AbstractSession.executeQuery(AbstractSession.java:1463)
         at org.eclipse.persistence.internal.sessions.CommitManager.commitNewObjectsForClassWithChangeSet(CommitManager.java:224)
         at org.eclipse.persistence.internal.sessions.CommitManager.commitAllObjectsWithChangeSet(CommitManager.java:123)
         at org.eclipse.persistence.internal.sessions.AbstractSession.writeAllObjectsWithChangeSet(AbstractSession.java:3766)
         at org.eclipse.persistence.internal.sessions.UnitOfWorkImpl.commitToDatabase(UnitOfWorkImpl.java:1404)
         at org.eclipse.persistence.internal.sessions.RepeatableWriteUnitOfWork.commitToDatabase(RepeatableWriteUnitOfWork.java:616)
         at org.eclipse.persistence.internal.sessions.UnitOfWorkImpl.commitToDatabaseWithChangeSet(UnitOfWorkImpl.java:1511)
         at org.eclipse.persistence.internal.sessions.UnitOfWorkImpl.issueSQLbeforeCompletion(UnitOfWorkImpl.java:3115)
         at org.eclipse.persistence.internal.sessions.RepeatableWriteUnitOfWork.issueSQLbeforeCompletion(RepeatableWriteUnitOfWork.java:331)
         at org.eclipse.persistence.transaction.AbstractSynchronizationListener.beforeCompletion(AbstractSynchronizationListener.java:157)
         at org.eclipse.persistence.transaction.JTASynchronizationListener.beforeCompletion(JTASynchronizationListener.java:68)
         at com.sun.enterprise.transaction.JavaEETransactionImpl.commit(JavaEETransactionImpl.java:437)
         at com.sun.enterprise.transaction.JavaEETransactionManagerSimplified.commit(JavaEETransactionManagerSimplified.java:867)
         at com.sun.ejb.containers.BaseContainer.completeNewTx(BaseContainer.java:5115)
         at com.sun.ejb.containers.BaseContainer.postInvokeTx(BaseContainer.java:4880)
         at com.sun.ejb.containers.BaseContainer.postInvoke(BaseContainer.java:2039)
         at com.sun.ejb.containers.BaseContainer.postInvoke(BaseContainer.java:1990)
         at com.sun.ejb.containers.EJBLocalObjectInvocationHandler.invoke(EJBLocalObjectInvocationHandler.java:222)
         at com.sun.ejb.containers.EJBLocalObjectInvocationHandlerDelegate.invoke(EJBLocalObjectInvocationHandlerDelegate.java:88)
         at $Proxy241.persist(Unknown Source)
         at com.sessionBeans.__EJB31_Generated__EmployeeFacade__Intf____Bean__.persist(Unknown Source)
         at com.beans.EmployeeBean.ajouter(EmployeeBean.java:37)
  • 9. Re: enumeration convertion in jsf
    r035198x Pro
    Currently Being Moderated
    If you read the error message you will see that it's telling you that you are trying to add a new record using an id that already exists in the database.
  • 10. Re: enumeration convertion in jsf
    REDO LOG Newbie
    Currently Being Moderated
    hi thanks for your help,
    there one problem witch is the name and the gender do not appear in the database table it must be a problem in the managed bean,
    anyhow, thanks a lot for help
  • 11. Re: enumeration convertion in jsf
    REDO LOG Newbie
    Currently Being Moderated
    thanks to all of you, here is a solution:

    http://stackoverflow.com/questions/14892967/using-enum-in-selectonemenu-fails-with-male-must-be-convertible-to-an-enum

Legend

  • Correct Answers - 10 points
  • Helpful Answers - 5 points