还是级联删除的问题!

<?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="com.zjlolife.netstore.domain.Category" table="t_category">
	    <id name="id" column="category_id">
	         <generator class="increment"/>
	    </id>
	    <property name="name"/>
	   <many-to-one name="parentCatrgory" class="com.zjlolife.netstore.domain.Category" column="category_pid" cascade="save-update"/>
	   <set name="childCatrgories" cascade="save-update" >
	       <key column="category_pid"/>
	       <one-to-many class="com.zjlolife.netstore.domain.Category" />
	   </set>
	  
	</class>
</hibernate-mapping>


public void test4() {
		Session session = HibernateUtil.getInstance().getSession();
		Transaction tx = null;
		tx = session.beginTransaction();
		try {
			Category foodCategory = (Category)session.get(Category.class, 1);
			session.delete(foodCategory);
			tx.commit();
		}catch(Exception e) {
			tx.rollback();
			e.printStackTrace();
		}finally {
			session.close();
		}
	}

当设置cascade="save-update"的时候,当delete(foodCategory)的时候,不会加载foodCategory下的childCategory,以及parentCategory.因此只设定了save-update,删除的时候不会级联到set端的对象以及many-to-one的对象,因此delete(foodCategory)会发出如下语句:

Hibernate: select category0_.category_id as category1_0_0_, category0_.name as name0_0_, category0_.category_pid as category3_0_0_ from t_category category0_ where category0_.category_id=?
Hibernate: update t_category set category_pid=null where category_pid=?
Hibernate: delete from t_category where category_id=?

只会发出一条select语句,不会级联关联对象,那么此时就必须要求foodCategory对象没有任何对象与它关联,否则会报错

至于为什么会发update null,因为foodCategory控制了关系,删除它的时候必须维护好表之间的关系!

呵呵,为什么上面get上来的foodCategory对象没有关联对象,因为many-to-one,以及set端默认是lazy,因此没有关联对象,因此可以正常删除

如果foodCategory有关联对象,那么肯定要清除foodCategory与关联对象的关系了,否则无法正常删除的。

猜想:当执行delete的时候,Hibernate发现foodCategory的关联对象根本就没加载上来,那么为了维护表与对象的关系,就必须发出update语句,来控制关系!

当然如果inverse="true",foodCategory无法控制关系了,那就会报外键约束错误!



当cascade="all"的时候,就不一样了,delete(foodCategory)的时候会加载foodCategory的关联对象,此时会删除所有与foodCategory的对象,而此时inverse就没有任何作用,因为在cascade="all"的情况下,inverse不用维护关系了。

以下是cascade="all"发出语句:

Hibernate: select category0_.category_id as category1_0_0_, category0_.name as name0_0_, category0_.category_pid as category3_0_0_ from t_category category0_ where category0_.category_id=?
Hibernate: select childcatrg0_.category_pid as category3_0_1_, childcatrg0_.category_id as category1_1_, childcatrg0_.category_id as category1_0_0_, childcatrg0_.name as name0_0_, childcatrg0_.category_pid as category3_0_0_ from t_category childcatrg0_ where childcatrg0_.category_pid=?
Hibernate: select childcatrg0_.category_pid as category3_0_1_, childcatrg0_.category_id as category1_1_, childcatrg0_.category_id as category1_0_0_, childcatrg0_.name as name0_0_, childcatrg0_.category_pid as category3_0_0_ from t_category childcatrg0_ where childcatrg0_.category_pid=?
Hibernate: select childcatrg0_.category_pid as category3_0_1_, childcatrg0_.category_id as category1_1_, childcatrg0_.category_id as category1_0_0_, childcatrg0_.name as name0_0_, childcatrg0_.category_pid as category3_0_0_ from t_category childcatrg0_ where childcatrg0_.category_pid=?
Hibernate: update t_category set category_pid=null where category_pid=?
Hibernate: update t_category set category_pid=null where category_pid=?
Hibernate: delete from t_category where category_id=?
Hibernate: delete from t_category where category_id=?
Hibernate: delete from t_category where category_id=?

注意那么多的select语句是在delete(foodCategory)的时候才进行的。

你可能感兴趣的:(hibernate级联删除问题)