使用EJB Facade的create()方法,使用JSF的JPA,新记录没有持久化。没有错误返回

时间:2012-09-10 18:59:30

标签: java jsf jpa ejb

我正在使用JSF2.0和EJB和JPA。 我已经尝试使用EJB Facade的create方法添加新记录,并且没有问题。

但现在我无法在表格中添加类型问题的新记录。 我将代码发布到我的实体,控制器和EJB外观文件,但我想补充一点,我的Question实体有一个名为Questionireire类型的问卷调查表的外键。

新记录没有被添加,我的尝试中没有任何错误。 甚至我的问卷ID也会正确返回。唯一没有做的是persist()。

这是我控制器中的create方法:

 public void createMultipleChoiceSingleAnswerQuestion() {
    try {
        currentQuestion = new Question();
        currentQuestion.setId(0);
        currentQuestion.setQuestionnaireid(currentQuestionnaire);
        getFacade().create(currentQuestion);
        //System.out.println("QUESTIONNAIRE IIIIIIIDDDDDDDDDDD: "+currentQuestionnaire.getId());
        //getFacade().create(q);
    } catch (Exception e) {
        System.out.println("ERRORRRR: "+e.getMessage());

    }
}

这是我的问题实体:

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package model;

import java.io.Serializable;
import java.util.Collection;
import javax.persistence.*;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
import javax.xml.bind.annotation.XmlRootElement;
import javax.xml.bind.annotation.XmlTransient;

/**
 *
 * @author Pedram
 */
@Entity
@Table(name = "question")
@XmlRootElement
@NamedQueries({
    @NamedQuery(name = "Question.findAll", query = "SELECT q FROM Question q"),
    @NamedQuery(name = "Question.findById", query = "SELECT q FROM Question q WHERE q.id = :id"),
    @NamedQuery(name = "Question.findByType", query = "SELECT q FROM Question q WHERE q.type = :type"),
    @NamedQuery(name = "Question.findByMandatory", query = "SELECT q FROM Question q WHERE q.mandatory = :mandatory"),
    @NamedQuery(name = "Question.findByOrdernumber", query = "SELECT q FROM Question q WHERE q.ordernumber = :ordernumber"),
    @NamedQuery(name = "Question.findByWeight", query = "SELECT q FROM Question q WHERE q.weight = :weight"),
    @NamedQuery(name = "Question.findByQuestionnaire", query = "SELECT q FROM Question q WHERE q.questionnaireid = :questionnaireid"),
    @NamedQuery(name = "Question.findByTag", query = "SELECT q FROM Question q WHERE q.tag = :tag")})
public class Question implements Serializable {
    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Basic(optional = false)
    @NotNull
    @Column(name = "id")
    private Integer id;
    @Size(max = 40)
    @Column(name = "type")
    private String type;
    @Lob
    @Size(max = 65535)
    @Column(name = "questiontext")
    private String questiontext;
    @Lob
    @Size(max = 65535)
    @Column(name = "answertext")
    private String answertext;
    @Column(name = "mandatory")
    private Boolean mandatory;
    @Lob
    @Size(max = 65535)
    @Column(name = "correctanswer")
    private String correctanswer;
    @Column(name = "ordernumber")
    private Integer ordernumber;
    @Column(name = "weight")
    private Integer weight;
    @Size(max = 40)
    @Column(name = "tag")
    private String tag;
    @OneToMany(mappedBy = "questionid")
    private Collection<Textanswer> textanswerCollection;
    @JoinColumn(name = "questionnaireid", referencedColumnName = "id")
    @ManyToOne
    private Questionnaire questionnaireid;
    @OneToMany(mappedBy = "questionid")
    private Collection<Choiceanswer> choiceanswerCollection;

    public Question() {
    }

    public Question(Integer id) {
        this.id = id;
    }

    public Integer getId() {
        return id;
    }

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

    public String getType() {
        return type;
    }

    public void setType(String type) {
        this.type = type;
    }

    public String getQuestiontext() {
        return questiontext;
    }

    public void setQuestiontext(String questiontext) {
        this.questiontext = questiontext;
    }

    public String getAnswertext() {
        return answertext;
    }

    public void setAnswertext(String answertext) {
        this.answertext = answertext;
    }

    public Boolean getMandatory() {
        return mandatory;
    }

    public void setMandatory(Boolean mandatory) {
        this.mandatory = mandatory;
    }

    public String getCorrectanswer() {
        return correctanswer;
    }

    public void setCorrectanswer(String correctanswer) {
        this.correctanswer = correctanswer;
    }

    public Integer getOrdernumber() {
        return ordernumber;
    }

    public void setOrdernumber(Integer ordernumber) {
        this.ordernumber = ordernumber;
    }

    public Integer getWeight() {
        return weight;
    }

    public void setWeight(Integer weight) {
        this.weight = weight;
    }

    public String getTag() {
        return tag;
    }

    public void setTag(String tag) {
        this.tag = tag;
    }

    @XmlTransient
    public Collection<Textanswer> getTextanswerCollection() {
        return textanswerCollection;
    }

    public void setTextanswerCollection(Collection<Textanswer> textanswerCollection) {
        this.textanswerCollection = textanswerCollection;
    }

    public Questionnaire getQuestionnaireid() {
        return questionnaireid;
    }

    public void setQuestionnaireid(Questionnaire questionnaireid) {
        this.questionnaireid = questionnaireid;
    }

    @XmlTransient
    public Collection<Choiceanswer> getChoiceanswerCollection() {
        return choiceanswerCollection;
    }

    public void setChoiceanswerCollection(Collection<Choiceanswer> choiceanswerCollection) {
        this.choiceanswerCollection = choiceanswerCollection;
    }

    @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 Question)) {
            return false;
        }
        Question other = (Question) 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 "model.Question[ id=" + id + " ]";
    }

}

这是我的EJB外观类:

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package facade;

import java.util.List;
import javax.ejb.Stateless;
import javax.persistence.EntityManager;
import javax.persistence.Persistence;
import javax.persistence.PersistenceContext;
import javax.persistence.Query;
import model.Question;
import model.Questionnaire;

/**
 *
 * @author Pedram
 */
@Stateless
public class QuestionFacade extends AbstractFacade<Question> {
    @PersistenceContext(unitName = "MobileSamplingToolkit0.4PU")
    private EntityManager em;
    List<Question> results = null;

    @Override
    protected EntityManager getEntityManager() {
        return em;
    }

    public QuestionFacade() {
        super(Question.class);
    }

    public List<Question> getQuestionsByQuestionnaire(Questionnaire questionnaire){
        try {
            em = Persistence.createEntityManagerFactory("MobileSamplingToolkit0.4PU").createEntityManager();
            Query query = em.createNamedQuery("Question.findByQuestionnaire");
            query.setParameter("questionnaireid", questionnaire);
            results = query.getResultList();
        } catch (Exception e) {
            System.out.println("ERROR IN Question FACADE:" + e.getMessage());
        }
        return results;
    }

}

我的Facade实现了AbstractFacade。这是Abstract Facade的代码:

/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */
package facade;

import java.util.List;
import javax.persistence.EntityManager;

/**
 *
 * @author Pedram
 */
public abstract class AbstractFacade<T> {
    private Class<T> entityClass;

    public AbstractFacade(Class<T> entityClass) {
        this.entityClass = entityClass;
    }

    protected abstract EntityManager getEntityManager();

    public void create(T entity) {
        getEntityManager().persist(entity);
    }

    public void edit(T entity) {
        getEntityManager().merge(entity);
    }

    public void remove(T entity) {
        getEntityManager().remove(getEntityManager().merge(entity));
    }

    public T find(Object id) {
        return getEntityManager().find(entityClass, id);
    }

    public List<T> findAll() {
        javax.persistence.criteria.CriteriaQuery cq = getEntityManager().getCriteriaBuilder().createQuery();
        cq.select(cq.from(entityClass));
        return getEntityManager().createQuery(cq).getResultList();
    }

    public List<T> findRange(int[] range) {
        javax.persistence.criteria.CriteriaQuery cq = getEntityManager().getCriteriaBuilder().createQuery();
        cq.select(cq.from(entityClass));
        javax.persistence.Query q = getEntityManager().createQuery(cq);
        q.setMaxResults(range[1] - range[0]);
        q.setFirstResult(range[0]);
        return q.getResultList();
    }

    public int count() {
        javax.persistence.criteria.CriteriaQuery cq = getEntityManager().getCriteriaBuilder().createQuery();
        javax.persistence.criteria.Root<T> rt = cq.from(entityClass);
        cq.select(getEntityManager().getCriteriaBuilder().count(rt));
        javax.persistence.Query q = getEntityManager().createQuery(cq);
        return ((Long) q.getSingleResult()).intValue();
    }

}

顺便说一下,我刚刚启用了JPA日志记录,并意识到通过单击“创建”按钮,不会执行INSERT查询。而我的应用程序的其他部分插入记录没有问题。

1 个答案:

答案 0 :(得分:1)

首先,那里有很多草率的代码。

给出实例的方法setQuestionnaireid?将实体的id设置为0,而其生成策略是标识? 无状态 bean将单个客户端的结果分配给实例变量?使用Java SE Persistence类获取EM工厂的EJB?在实体之上的大量命名查询?使用无类型的JPA查询?

肯定这段代码不会飞。

你没有展示的一件事是你如何在JSF支持bean中获得对EJB的引用,以及这个支持bean究竟是什么类型的bean。它是原生的@ManagedBean,CDI @Named还是别的什么?

根据您所做的潜在“怪异”,实体未被持久化的一个原因可能是未提交的事务。如果由于这种可能的其他怪异你从工厂设置EM而不是使用注入的EM,这确实可能发生。