aSsYin
aSsYin

Reputation: 1

SelectOnMenu with converter

I need the help I'm lost with this error .i have problem whith converter of selectonmenu when i click in submit of add new city .

this is my Facelets

 <p:commandButton value="New city" update=":form:display" id="withIcon" onclick="newvilledialog.show()" title="Nouveau"/>  

       <p:dialog header="Nouveau ville" widgetVar="newvilledialog" resizable="false" id="newvilleDlg"  
                showEffect="fade" hideEffect="explode" modal="true">   
        <h:panelGrid id="panel" columns="2" cellpadding="4" style="margin:0 auto;">

        <h:outputLabel for="pays" value="Pays :" />
            <h:selectOneMenu value="#{villeBean.villeList}"> 
                 <f:converter converterId="paysConverter"></f:converter> 
                 <f:selectItem itemLabel="select Pays" itemValue="" />
                <f:selectItems value="#{paysBean.paysList}" var="pays" itemLabel="#{pays.nompays}" itemValue="#{pays}"/>

            </h:selectOneMenu>

             <h:outputLabel for="nomville" value="Nom ville :" />  
            <p:inputText id="nomville1" value="#{villeBean.nomville}" />
            <p:commandButton id="Buttonnew" value="Valider"  action="#{villeBean.addVille}" update="form" oncomplete="newvilledialog.hide();"/>  
        </h:panelGrid>  
    </p:dialog> 

Class Pays.java

package ma.project.sgcheque.model;

import java.util.HashSet;
import java.util.Set;
import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import static javax.persistence.GenerationType.IDENTITY;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Table;

/**
 * Pays entity. @author MyEclipse Persistence Tools
 */

@Entity
@Table(name = "pays", catalog = "base_cheque")
public class Pays implements java.io.Serializable {

    // Fields

    private Integer idpays;
    private String nompays;
    private Set<Ville> villes = new HashSet<Ville>(0);

    // Constructors

    /** default constructor */
    public Pays() {
    }

    /** full constructor */
    public Pays(String nompays, Set<Ville> villes) {
        this.nompays = nompays;
        this.villes = villes;
    }

    // Property accessors
    @Id
    @GeneratedValue(strategy = IDENTITY)
    @Column(name = "idpays", unique = true, nullable = false)
    public Integer getIdpays() {
        return this.idpays;
    }

    public void setIdpays(Integer idpays) {
        this.idpays = idpays;
    }

    @Column(name = "nompays", length = 45)
    public String getNompays() {
        return this.nompays;
    }

    public void setNompays(String nompays) {
        this.nompays = nompays;
    }

    @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "pays")
    public Set<Ville> getVilles() {
        return this.villes;
    }

    public void setVilles(Set<Ville> villes) {
        this.villes = villes;
    }


  public boolean equals(Object other) {
        return other instanceof Pays && (idpays != null) ? idpays.equals(((Pays) other).idpays) : (other == this);
    }

}

the converter :

package com.project.sgcheque.web.converters;

import javax.faces.component.UIComponent;
import javax.faces.context.FacesContext;
import javax.faces.convert.Converter;
import javax.faces.convert.FacesConverter;


import java.util.List;


import ma.project.sgcheque.model.Pays;


@FacesConverter(forClass=Pays.class, value="paysConverter")

public class PaysConverter implements Converter {
      public List<Pays> paysList;


    public Object getAsObject(FacesContext context, UIComponent component, String value) {
        try{
           if (value.trim().equals("")) {
                 return null;
              } else {
                 for (Pays p : paysList) {
                    if (p.getIdpays().equals(value)) {
                       return p;
                    }
                 }
              }}catch (NullPointerException ex){}

              return null;

    }

    public String getAsString(FacesContext facesContext, UIComponent component, Object value) {


        try {
        Pays pays = (Pays) value;
        return pays.getIdpays() != null ? String.valueOf(pays.getIdpays()) : null;
            }catch (NullPointerException exception) {
        return null;
            }catch (ClassCastException exception) {
                return null;
            }


    }
}

and my Bean (PaysManagedBean )

package ma.project.sgcheque.managed.bean;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import javax.annotation.PostConstruct;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ManagedProperty;
import javax.faces.bean.RequestScoped;

import org.springframework.dao.DataAccessException;

import ma.project.sgcheque.model.Pays;
import ma.project.sgcheque.model.Ville;
import ma.project.sgcheque.service.interfaces.IVilleService;


@ManagedBean(name="villeBean")
@RequestScoped
public class VilleManagedBean implements Serializable {


    private static final long serialVersionUID = 1L;
    private static final String SUCCESS = "success";
    private static final String ERROR   = "error";

    //Spring Ville Service is injected...
    @ManagedProperty(value="#{VilleService}")
    IVilleService villeService;

    List<Ville> villeList;
    private Ville selectedVille = new Ville();

    private int idville;
    private String nomville;
    private Pays pays = new Pays();   


    /**
     * Add Ville
     *
     * @return String - Response Message
     */

    public String addVille() {
     try {
            Ville ville = new Ville();
            ville.setIdville(getIdville());
            ville.setNomville(getNomville());
            ville.setPays(getPays());
            getVilleService().addVille(ville);
            return "ville";
        } catch (DataAccessException e) {
           e.printStackTrace();
       }  
        return ERROR;
    }

    /**
     * Update Pays
     *
     * @return String - Response Message
     */



    public String updateVille() {

            getVilleService().updateVille(selectedVille);
            return "ville";
    } 

    public String update(){
        villeService.save(selectedVille);
        return null;
    }

    /**
     * Delete Pays
     *
     * @return String - Response Message
     */

    public String deleteVille() { 
            try {
                 getVilleService().deleteVille(selectedVille);
                 return "ville";
            } catch (DataAccessException e) {
                e.printStackTrace();
            }  

            return ERROR;
    }

    /**
     * Reset Fields
     *

    public void reset() {
        this.setIdville(0);
        this.setNomville("");
        this.setPays(null);
    }*/  

    /**
     * Get Ville Service
     *
     * @return IVilleService - Ville Service
     */
    public IVilleService getVilleService() {
        return villeService;
    }

    /**
     * Set Ville Service
     *
     * @param IVilleService - Ville Service
     */
    public void setVilleService(IVilleService villeService) {
        this.villeService = villeService;
    }
     public List<Ville> getVilleList() {
         villeList = new ArrayList<Ville>();
         villeList.addAll(getVilleService().getVille());
        return villeList;
    }

    public void setVilleList(List<Ville> villeList) {
        this.villeList = villeList;
    }

    /**
     * Get SelectedVille Id
     *
     * @return selectedVille
     */
    public Ville getSelectedVille() {
        return selectedVille;
    }
     /**
     * Set SelectedVille Id
     *
     * @return selectedVille
     */
    public void setSelectedVille(Ville selectedVille) {
        this.selectedVille = selectedVille;
    }
     /**
     * Get Ville Id
     *
     * @return int - Ville Id
     */
    public int getIdville() {
        return idville;
    }
    /**
     * Set Ville Id
     *
     * @param int - Ville Id
     */
    public void setIdville(int idville) {
        this.idville = idville;
    }
       /**
     * Get Ville Name
     *
     * @return String - Ville Name
     */
    public String getNomville() {
        return nomville;
    }
      /**
     * Set Ville Name
     *
     * @param String - Ville Name
     */
    public void setNomville(String nomville) {
        this.nomville = nomville;
    }
     /**
     * Get Pays Object
     *
     * @return String - Pays Object
     */
    public Pays getPays() {
        return pays;
    }
     /**
     * Set Pays Object
     *
     * @return String - Pays Object
     */
    public void setPays(Pays pays) {
        this.pays = pays;
    }

}

and this the Error

javax.faces.FacesException: #{villeBean.addVille}: org.springframework.dao.InvalidDataAccessApiUsageException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays; nested exception is org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays
    at com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:85)
    at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:97)
    at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:114)
    at javax.faces.webapp.FacesServlet.service(FacesServlet.java:308)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:230)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:175)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:128)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:104)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:261)
    at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:844)
    at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:581)
    at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:447)
    at java.lang.Thread.run(Thread.java:722)
Caused by: javax.faces.FacesException: #{villeBean.addVille}: org.springframework.dao.InvalidDataAccessApiUsageException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays; nested exception is org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays
    at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:114)
    at javax.faces.component.UICommand.broadcast(UICommand.java:311)
    at javax.faces.component.UIViewRoot.broadcastEvents(UIViewRoot.java:781)
    at javax.faces.component.UIViewRoot.processApplication(UIViewRoot.java:1246)
    at com.sun.faces.lifecycle.InvokeApplicationPhase.execute(InvokeApplicationPhase.java:77)
    ... 15 more
Caused by: javax.faces.el.EvaluationException: org.springframework.dao.InvalidDataAccessApiUsageException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays; nested exception is org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays
    at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:98)
    at com.sun.faces.application.ActionListenerImpl.processAction(ActionListenerImpl.java:98)
    ... 19 more
Caused by: org.springframework.dao.InvalidDataAccessApiUsageException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays; nested exception is org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays
    at org.springframework.orm.hibernate3.SessionFactoryUtils.convertHibernateAccessException(SessionFactoryUtils.java:654)
    at org.springframework.orm.hibernate3.HibernateTransactionManager.convertHibernateAccessException(HibernateTransactionManager.java:793)
    at org.springframework.orm.hibernate3.HibernateTransactionManager.doCommit(HibernateTransactionManager.java:664)
    at org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:754)
    at org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:723)
    at org.springframework.transaction.interceptor.TransactionAspectSupport.commitTransactionAfterReturning(TransactionAspectSupport.java:393)
    at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:120)
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172)
    at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:202)
    at $Proxy20.addVille(Unknown Source)
    at ma.project.sgcheque.managed.bean.VilleManagedBean.addVille(VilleManagedBean.java:52)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:601)
    at org.apache.el.parser.AstValue.invoke(AstValue.java:131)
    at org.apache.el.MethodExpressionImpl.invoke(MethodExpressionImpl.java:276)
    at com.sun.faces.facelets.el.TagMethodExpression.invoke(TagMethodExpression.java:102)
    at javax.faces.component.MethodBindingMethodExpressionAdapter.invoke(MethodBindingMethodExpressionAdapter.java:84)
    ... 20 more
Caused by: org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: ma.project.sgcheque.model.Pays
    at org.hibernate.engine.ForeignKeys.getEntityIdentifierIfNotUnsaved(ForeignKeys.java:242)
    at org.hibernate.type.EntityType.getIdentifier(EntityType.java:430)
    at org.hibernate.type.ManyToOneType.isDirty(ManyToOneType.java:265)
    at org.hibernate.type.TypeFactory.findDirty(TypeFactory.java:619)
    at org.hibernate.persister.entity.AbstractEntityPersister.findDirty(AbstractEntityPersister.java:3141)
    at org.hibernate.event.def.DefaultFlushEntityEventListener.dirtyCheck(DefaultFlushEntityEventListener.java:501)
    at org.hibernate.event.def.DefaultFlushEntityEventListener.isUpdateNecessary(DefaultFlushEntityEventListener.java:227)
    at org.hibernate.event.def.DefaultFlushEntityEventListener.onFlushEntity(DefaultFlushEntityEventListener.java:150)
    at org.hibernate.event.def.AbstractFlushingEventListener.flushEntities(AbstractFlushingEventListener.java:219)
    at org.hibernate.event.def.AbstractFlushingEventListener.flushEverythingToExecutions(AbstractFlushingEventListener.java:99)
    at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:49)
    at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:1028)
    at org.hibernate.impl.SessionImpl.managedFlush(SessionImpl.java:366)
    at org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:137)
    at org.springframework.orm.hibernate3.HibernateTransactionManager.doCommit(HibernateTransactionManager.java:656)
    ... 36 more

Error appear when i click in submit of add new city (who have pays(country) as foreign key) .

Sorry for my english but I hope that you understand what is my problem. realy am stoped.

Upvotes: 0

Views: 836

Answers (1)

cremersstijn
cremersstijn

Reputation: 2395

The problem is that the Pays is no longer associate in your hibernate session or persistence context. When you try to save the Ville, the hibernate session doesn't know you the Pays.

You can solve this by using merge instead of persist or do a refresh of your Pays in the VilleService.

Upvotes: 1

Related Questions