Netbeans不使用Hibernate填充联结表 [英] Netbeans not filling junction table using hibernate

查看:64
本文介绍了Netbeans不使用Hibernate填充联结表的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我刚接触Hibernate,但是我需要在工作中使用它.我们正在将Netbeans与Derby Embedded一起使用,并且无法更改为其他IDE.

I'm new at working with Hibernate but I need to use it for a project at work. We're using Netbeans with Derby Embedded and we can't change to a different IDE.

我遇到的问题与数据库中的多对多关系有关.

The problem I'm having is related to a many-to-many relationship in the database.

我有一个表问题,一个表机器和一个连接表MACHINEPROBLEM.一个问题可以有很多机器,而一台机器可以有很多问题.这些表通过联结表MACHINEPROBLEM相关.

I have a table PROBLEM, a table MACHINE and a junction table MACHINEPROBLEM. A Problem can have many machines, and a Machine can have many problems. Those tables are related through the junction table MACHINEPROBLEM.

我有必要的POJO和映射文件(在hibernate.cfg.xml中适当引用),并让Netbeans和Hibernate自动在数据库中创建表. 表格和各自的关系已正确创建.表MACHINEPROBLEM具有一个组合键,该组合键由在MACHINE表中引用"id"的"machineid"和在PROBLEM表中引用"id"的"problemid"组成.

I have the necessary POJOs and mapping files (appropriately referenced in hibernate.cfg.xml) and let Netbeans and Hibernate automatically create the tables in the database. The tables and respective relationships were created correctly. Table MACHINEPROBLEM has a composite key composed of "machineid" which references "id" in the MACHINE table, and "problemid" which references "id" in the PROBLEM table.

发生的事情是,当我创建一个Problem对象时,向其中添加一组计算机,然后将其保存在数据库中,联结表中没有任何数据.数据已正确保存在PROBLEM和MACHINE表中,但是MACHINEPROBLEM表为空.这意味着我无法搜索给定问题的所有机器,因为用于连接它们的联结表为空.

What's happening is that when I create a Problem object, add a Set of Machine to it, and then save it in the database the junction table isn't being filled with any data. The data is saved correctly in both the PROBLEM and MACHINE tables, but the MACHINEPROBLEM table is empty. This means I can't search for all the machines of a given problem, since the junction table used to connect them is empty.

有人可以帮我解决这个问题吗?谢谢.


Can anyone please help me solve this problem? Thanks.


映射文件:

Machine.hbm.xml

Machine.hbm.xml

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
    <class name="DataAccess.entity.Machine" table="MACHINE" schema="APP">
        <id name="id" type="long">
            <column name="ID" />
            <generator class="assigned" />
        </id>
        <set name="problems" inverse="false" lazy="true" fetch="select" table="MACHINEPROBLEM">
         <key column="MACHINEID"/>
         <many-to-many column="PROBLEMID" class="DataAccess.entity.Problem"/>
        </set>
        <property name="machineid" type="string">
            <column name="MACHINEID" length="10" not-null="true" />
        </property>
    </class>
</hibernate-mapping>



Problem.hbm.xml



Problem.hbm.xml

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
    <class name="DataAccess.entity.Problem" table="PROBLEM" schema="APP">
        <id name="id" type="long">
            <column name="ID" />
            <generator class="assigned" />
        </id>
        <set name="machines" inverse="true" lazy="true" fetch="select" cascade="all" table="MACHINEPROBLEM">
         <key column="PROBLEMID"/>
         <many-to-many column="MACHINEID" class="DataAccess.entity.Machine"/>
        </set>
        <property name="problemid" type="string">
            <column name="PROBLEMID" length="10" not-null="true" />
        </property>
        <property name="problemname" type="string">
            <column name="PROBLEMNAME" length="50" not-null="true" />
        </property>
        <property name="tipoproblema" type="string">
            <column name="TIPOPROBLEMA" length="50" />
        </property>
        <property name="linear" type="boolean">
            <column name="LINEAR" not-null="true" />
        </property>
        <property name="numtarefas" type="int">
            <column name="NUMTAREFAS" not-null="true" />
        </property>
        <property name="nummaquinas" type="int">
            <column name="NUMMAQUINAS" not-null="true" />
        </property>
    </class>
</hibernate-mapping>



POJO:



POJOs:

Machine.java

Machine.java

public class Machine  implements java.io.Serializable {


     private long id;
     private String machineid;
     private Set<Problem> problems = new HashSet<Problem>();

    public Machine() {
    }

    public Machine(long id, String machineid) {
       this.id = id;
       this.machineid = machineid;
    }

    public long getId() {
        return this.id;
    }

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

    public String getMachineid() {
        return this.machineid;
    }

    public void setMachineid(String machineid) {
        this.machineid = machineid;
    }

     public Set<Problem> getProblems() {
      return problems;
    }

    public void setProblems( Set<Problem> problems ) {
      this.problems = problems;
     }

    public boolean equals(Object obj) {
      if (obj == null) return false;
      if (!this.getClass().equals(obj.getClass())) return false;

      Machine obj2 = (Machine)obj;
      if((this.id == obj2.getId()) && (this.machineid.equals(obj2.getMachineid())))
      {
         return true;
      }
      return false;
    }

    public int hashCode() {
       int tmp = 0;
       tmp = ( id + machineid ).hashCode();
       return tmp;
    }
}



Problem.java



Problem.java

public class Problem  implements java.io.Serializable {


     private long id;
     private String problemid;
     private String problemname;
     private String tipoproblema;
     private boolean linear;
     private int numtarefas;
     private int nummaquinas;
     private Set<Machine> machines = new HashSet<Machine>();

    public Problem() {
    }


    public Problem(long id, String problemid, String problemname, boolean linear, int numtarefas, int nummaquinas) {
        this.id = id;
        this.problemid = problemid;
        this.problemname = problemname;
        this.linear = linear;
        this.numtarefas = numtarefas;
        this.nummaquinas = nummaquinas;
    }

    public Problem(long id, String problemid, String problemname, String tipoproblema, boolean linear, int numtarefas, int nummaquinas) {
       this.id = id;
       this.problemid = problemid;
       this.problemname = problemname;
       this.tipoproblema = tipoproblema;
       this.linear = linear;
       this.numtarefas = numtarefas;
       this.nummaquinas = nummaquinas;
    }

    public long getId() {
        return this.id;
    }

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

    public String getProblemid() {
        return this.problemid;
    }

    public void setProblemid(String problemid) {
        this.problemid = problemid;
    }

    public String getProblemname() {
        return this.problemname;
    }

    public void setProblemname(String problemname) {
        this.problemname = problemname;
    }

    public String getTipoproblema() {
        return this.tipoproblema;
    }

    public void setTipoproblema(String tipoproblema) {
        this.tipoproblema = tipoproblema;
    }

    public boolean isLinear() {
        return this.linear;
    }

    public void setLinear(boolean linear) {
        this.linear = linear;
    }

    public int getNumtarefas() {
        return this.numtarefas;
    }

    public void setNumtarefas(int numtarefas) {
        this.numtarefas = numtarefas;
    }

    public int getNummaquinas() {
        return this.nummaquinas;
    }

    public void setNummaquinas(int nummaquinas) {
        this.nummaquinas = nummaquinas;
    }

    public Set<Machine> getMachines() {
      return machines;
    }

    public void setMachines( Set<Machine> machines ) {
      this.machines = machines;
     }
}



主班:



Main class:

public class Test {

    public static void main(String[] args) {    

        try
        {
             //Adds a couple of machines to a hashset
             Set<Machine> machines = new HashSet<>();
             machines.add(new Machine(1, "M1"));
             machines.add(new Machine(2, "M2"));

             //creates a Problem with some random data
             Problem p = new Problem(2, "OSD1", "TestP", "jobshop", true, 2, 3);    
             p.setMachines(machines);

             //Adds Problem p to the database
             ProblemDAL pDal = new ProblemDAL(null); 
             pDal.add(p); //Doing this saves Problem p to table PROBLEM, as well as the set of machines to table MACHINE. However, nothing's saved in the junction table MACHINEPROBLEM.

             pDal.closeSession();
        }
        catch (Exception e){
            e.printStackTrace();
        }

    }
}



ProblemDAL



ProblemDAL

public class ProblemDAL {
    Session session;
    boolean closeSession;

    public ProblemDAL(Session session)
    {
        if(session == null)
        {
            this.session = HibernateUtil.getSessionFactory().openSession();
        }
        else
        {
            this.session = session;
        }        
    }

    public void add(Problem entity) throws Exception {
        Transaction tx = null;

        try {
            tx = session.beginTransaction();
            session.save(entity);
            tx.commit();
        } 
        catch (HibernateException e) {
            if (tx!=null) tx.rollback();
            e.printStackTrace(); 
        } 
    }

    public void update(Problem entity)
    {
        Transaction tx = null;

        try {            
            tx = session.beginTransaction();
            session.update(entity);
            tx.commit();
        }
        catch (HibernateException e) {
            if (tx!=null) tx.rollback();
            e.printStackTrace(); 
        } 
    }

    public void delete(Problem entity){
        Transaction tx = null;

        try{
           tx = session.beginTransaction();         
           session.delete(entity); 
           tx.commit();
        }
        catch (HibernateException e) {
           if (tx!=null) tx.rollback();
           e.printStackTrace(); 
        }
    }



    public Problem getById(long id) {
        Transaction tx = null;
        Problem entity = null;

        try {
            tx = session.beginTransaction();
            entity = (Problem) session.get(Problem.class, id);
            tx.commit();   
        }
        catch (HibernateException e) {
            if (tx!=null) tx.rollback();
            e.printStackTrace(); 
        }
        finally {
            return entity;
        }

    }



    public List<Problem> getAll() {
        Transaction tx = null;
        List<Problem> entityList = null;

        try {
            tx = session.beginTransaction();
            entityList = session.createQuery("from Problem").list();
            tx.commit();             
        }
        catch (HibernateException e) {
            if (tx!=null) tx.rollback();
            e.printStackTrace(); 
        }
        finally {
            return entityList;
        }
    }

    public List<Machine> getMachines() {
        Transaction tx = null;
        List<Machine> entityList = null;

        try {
            tx = session.beginTransaction();
            entityList = session.createQuery("select machines from Problem").list();
            tx.commit();             
        }
        catch (HibernateException e) {
            if (tx!=null) tx.rollback();
            e.printStackTrace(); 
        }
        finally {
            return entityList;
        }
    }

    public void closeSession()
    {
        if(this.session!=null)
        {
            this.session.close();
        }
    } 
}



hibernate.cfg.xml



hibernate.cfg.xml

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
  <session-factory>
    <property name="hibernate.dialect">org.hibernate.dialect.DerbyDialect</property>
    <property name="hibernate.connection.driver_class">org.apache.derby.jdbc.EmbeddedDriver</property>
    <property name="hibernate.hbm2ddl.auto">update</property>
    <property name="hibernate.connection.url">jdbc:derby:DB;create=true</property>
    <property name="hibernate.connection.username">***</property>
    <property name="hibernate.connection.password">***</property>
    <property name="hibernate.show_sql">true</property>
    <mapping resource="DataAccess/entity/Problem.hbm.xml"/>
    <mapping resource="DataAccess/entity/Machine.hbm.xml"/>
    <mapping resource="DataAccess/entity/Operation.hbm.xml"/>
    <mapping resource="DataAccess/entity/EvaluationParameters.hbm.xml"/>
    <mapping resource="DataAccess/entity/Generatedjobs.hbm.xml"/>
    <mapping resource="DataAccess/entity/Jobs.hbm.xml"/>
  </session-factory>
</hibernate-configuration>

推荐答案

此类问题最常见的问题是您没有设置关系的两面.

The most common issue for such issues is that you have not set both sides of the relationship.

这时最好忽略当前的任何Hibernate问题.

Ignoring any Hibernate issues at the moment this is best practive anyway.

如果您考虑:

Problem p = new Problem();
Machine m = new Machine();
m.addProblem(p);

忽略任何持久性问题,是您的域模型处于持续状态,即.机器"m"与问题"p"相关联吗?即p.getMachines().contains(m)返回true吗?

Ignoring any persistence concerns, is your domain model in a consitent state, viz. Is machine 'm' associated with problem 'p'? i.e. does p.getMachines().contains(m) return true?

因此通常最好封装以下操作:

So it's normally best to encapsulate these operations:

public class Machine{

public void addProblem(Problem p){
problems.add(p);
p.getMachines.add(this);
}


public class Problem{
public void addMachine(Machine m){
machines.add(m);
m.getProblems().add(this);
}

作为实验,您可以尝试使用当前代码来保存带有一组问题的新计算机.结果应该与Machine是拥有(非反)面一样好.

As an experiment you can try with your current code to save a new Machine with a set of Problems. Result should be as expected as Machine is the owning (non-inverse) side.

这篇关于Netbeans不使用Hibernate填充联结表的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆