hibernate多对多关系配置--增删改查

hibernate多对多关联配置--并实现增删改查

         hibernate就不多介绍了,这里就直接上我项目中使用的例子做说明。

         数据模型


这是项目中用户和用户组的数据模型er图草稿,具体的model对象字段就以项目中的为主了。

model类以及pojo接口,这里pojo接口用不上,大家测试的时候也可以去掉

package com.supre.model;
import java.io.Serializable;
import java.util.Set;

public class User {

	private int userId;
	private String userNo;
	private String userName;
	private String password;
	private String telephone;
	private String remark;
	private int userStatus;
	private Set<Group> groups;
	
	public User() {
		super();
		// TODO Auto-generated constructor stub
	}

	public User(int userId, String userNo) {
		super();
		this.userId = userId;
		this.userNo = userNo;
	}

	public User(int userId, String userNo, String userName, String password,
			String telephone, String remark, int userStatus, Set<Group> groups) {
		super();
		this.userId = userId;
		this.userNo = userNo;
		this.userName = userName;
		this.password = password;
		this.telephone = telephone;
		this.remark = remark;
		this.userStatus = userStatus;
		this.groups = groups;
	}

	public int getUserId() {
		return userId;
	}

	public void setUserId(int userId) {
		this.userId = userId;
	}

	public String getUserNo() {
		return userNo;
	}

	public void setUserNo(String userNo) {
		this.userNo = userNo;
	}

	public String getUserName() {
		return userName;
	}

	public void setUserName(String userName) {
		this.userName = userName;
	}

	public String getPassword() {
		return password;
	}

	public void setPassword(String password) {
		this.password = password;
	}

	public String getTelephone() {
		return telephone;
	}

	public void setTelephone(String telephone) {
		this.telephone = telephone;
	}

	public String getRemark() {
		return remark;
	}

	public void setRemark(String remark) {
		this.remark = remark;
	}

	public int getUserStatus() {
		return userStatus;
	}

	public void setUserStatus(int userStatus) {
		this.userStatus = userStatus;
	}

	public Set<Group> getGroups() {
		return groups;
	}

	public void setGroups(Set<Group> groups) {
		this.groups = groups;
	}

	@Override
	public String toString() {
		return "User [userId=" + userId + ", userNo=" + userNo + ", userName="
				+ userName + ", password=" + password + ", telephone="
				+ telephone + ", remark=" + remark + ", userStatus="
				+ userStatus + ", groupSize=" + groups.size() + "]";
	}
	
	
}

package com.supre.model;

import java.io.Serializable;
import java.util.Date;
import java.util.Set;

public class Group{

	private int groupId;
	private String groupName;
	private Date createTime;
	private String remark;
	//private User user;   //负责人
	private Set<User> users;
	
	public Group() {
		super();
		// TODO Auto-generated constructor stub
	}

	public int getGroupId() {
		return groupId;
	}

	public void setGroupId(int groupId) {
		this.groupId = groupId;
	}

	public String getGroupName() {
		return groupName;
	}

	public void setGroupName(String groupName) {
		this.groupName = groupName;
	}

	public Date getCreateTime() {
		return createTime;
	}

	public void setCreateTime(Date createTime) {
		this.createTime = createTime;
	}

	public String getRemark() {
		return remark;
	}

	public void setRemark(String remark) {
		this.remark = remark;
	}

	public Set<User> getUsers() {
		return users;
	}

	public void setUsers(Set<User> users) {
		this.users = users;
	}

	public Group(int groupId, String groupName, Date createTime, String remark,
			Set<User> users) {
		super();
		this.groupId = groupId;
		this.groupName = groupName;
		this.createTime = createTime;
		this.remark = remark;
		this.users = users;
	}

	@Override
	public String toString() {
		return "Group [groupId=" + groupId + ", groupName=" + groupName
				+ ", createTime=" + createTime + ", remark=" + remark
				+ ", userSize=" + users.size() + "]";
	}

}

hibernate的配置信息

         这里项目中使用的xml配置   hibernate主配置文件:hibernate.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="dialect">org.hibernate.dialect.MySQLDialect</property>  
<property name="connection.driver_class">com.mysql.jdbc.Driver</property>  
<property name="connection.url">jdbc:mysql://localhost:3306/idisk?useUnicode=true&characterEncoding=utf-8</property> 
<property name="connection.username">root</property>  
<property name="connection.password">supre2015</property>
<property name="show_sql">true</property>

<mapping resource="hibernate/user.hbm.xml"/>
<mapping resource="hibernate/group.hbm.xml"/>
</session-factory>
</hibernate-configuration>

Model类User的映射文件

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC 
    "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
    <hibernate-mapping package="com.supre.model">
    	<class name="User" table="tb_user">
    		<id name="userId" column="user_id">
    			<generator class="native"></generator>
    		</id>
    		<property name="userNo" column="user_no"></property>
    		<property name="userName" column="user_name"></property>
    		<property name="password" column="password"></property>
    		<property name="telephone" column="telephone"></property>
    		<property name="remark" column="remark"></property>
    		<property name="userStatus" column="user_status"></property>
    		<set name="groups" table="user_group" inverse="true" cascade="none" lazy="false">
    			<key column="user_id"></key>
    			<many-to-many class="Group" column="group_id" ></many-to-many>
    		</set>
    	</class>
    </hibernate-mapping>

Model类Group的映射文件

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-mapping PUBLIC 
    "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
    <hibernate-mapping package="com.supre.model">
    	<class name="Group" table="tb_group">
    		<id name="groupId" column="group_id">
    			<generator class="native"></generator>
    		</id>
    		<property name="groupName" column="group_name"></property>
    		<property name="createTime" column="create_time"></property>
    		<property name="remark" column="remark"></property>
    		<!-- <many-to-one name="user" class="User" column="user_id" lazy="false"></many-to-one> -->
    		<set name="users" table="user_group" inverse="false" cascade="none" lazy="false">
    			<key column="group_id"></key>
    			<many-to-many class="User" column="user_id" lazy="false"></many-to-many>
    		</set>
    	</class>
    </hibernate-mapping>

hibernate的帮助类

package com.supre.util;

import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;


public class HibernateSessionFactory {

	private static SessionFactory factory;
	private static Configuration cfg;
	private static ThreadLocal<Session> local = new ThreadLocal<Session>();

	static {
		cfg = new Configuration().configure("hibernate.xml");
		factory = cfg.buildSessionFactory();
	}

	public static void buildSessionFactory() {
		cfg = new Configuration().configure("hibernate.xml");
		factory = cfg.buildSessionFactory();
	}
	private HibernateSessionFactory(){};
	
	public static SessionFactory getSessionFactory(){
		   return factory;
	}
	public static Session getSession(){
		Session session=local.get();
		if(session==null || !session.isOpen()){
			if(factory==null){
				buildSessionFactory();
			}
			session = factory.openSession();
			local.set(session);
		}
		return session;
	}
	public  static void closeSession(){
		Session session=local.get();
		if(session!=null && session.isOpen()){
			session.close();
		}
		local.set(null);
	}
	}

下面是测试类,


package com.supre.util;

import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.hibernate.Session;

import com.supre.model.Group;
import com.supre.model.User;

public class TestHibernate {
	
	public static void main(String[] args) {
//		testAddGroup();
//		testAddUser();
//		testAddGroup2();
//		testAddUser2();
//		testAddUser3();
//		testSelect();
//		testDeleteUser();
		testDeleteGroup();
	}

	//测试添加简单主控方对象(Group)
	public static void testAddGroup(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		Group g = new Group();
		g.setGroupName("分组1");
		s.save(g);
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
	
	//测试添加简单被控方对象(User)
	public static void testAddUser(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		User u = new User();
		u.setUserName("用户1");
		s.save(u);
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
	
	//测试添加主控方对象(Group)以及对应关系
	/**
	 * 如果主控方(group.hbm.xml)
	 * 配置cascade=‘save-update’,则在下述结果中会修改被控方(User)数据
	 * 配置cascade=‘none’,则在下述结果不会修改被控方(User)数据
	 */
	public static void testAddGroup2(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		User u = new User();
		u.setUserId(3);//数据库中已有的用户id
		User u1 = new User();
		u1.setUserId(4);//数据库中已有的用户id
		Group g = new Group();
		g.setGroupName("分组4");
		Set<User> us = new HashSet<>();
		us.add(u);
		us.add(u1);
		g.setUsers(us);
		s.save(g);
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
	
	//测试添加被控方对象(User)以及对应关系
	/**
	 *这里被控方和主控方都配置cascade="none"
	 * 
	 * 如下代码中,无法实现将关系添加到user_group表中,
	 * 相反会删掉g和g1在user_group中的全部关系,
	 * 因为g和g1中的users全部为空的
	 */
	public static void testAddUser2(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		User u = new User();
		u.setUserName("用户4");
		Group g = new Group();
		g.setGroupId(6);//数据库中已有的用户id
		Group g1 = new Group();
		g1.setGroupId(8);//数据库中已有的用户id
		Set<Group> gs = new HashSet<>();
		gs.add(g);
		gs.add(g1);
		u.setGroups(gs);
		s.save(u);
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
	
	//测试添加被控方对象(User)以及对应关系
	/**
	 * 这里被控方和主控方都配置cascade="none"
	 * 
	 * 因为Group是主控方(维护关系方),在添加或者修改关系时,
	 * 必须由Group方来控制,下面代码中的1和2两处是必须的,
	 * 如果没有下面1和2两行代码,则只会简单的添加User数据,
	 * 不写将关系写到user_group表中
	 */
	public static void testAddUser3(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		User u = new User();
		u.setUserName("用户8");
		Group g = (Group) s.get(Group.class, 9);
		Group g1 = (Group) s.get(Group.class, 10);
		Set<Group> gs = new HashSet<>();		
		g.getUsers().add(u); // ----1
		g1.getUsers().add(u); // -----2
		gs.add(g);
		gs.add(g1);
		u.setGroups(gs);
		s.save(u);
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
	
	/**
	 * update和save方法大致一样,不过要注意主控方(Group)执行update方法前,
	 * 必须先将原Group中的users取到,再进行修改,这样才能保证修改时能准确的维护关系
	 * 如果是修改关系,则通过修改Group中的users来修改关系
	 */
	public static void testUpdate(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		Group g = (Group) s.get(Group.class, 9);
		g.setGroupName("管理员");
		//g.getUsers().remove(new User(7, ""));
		s.save(g);
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
	
	
	/**
	 *  这里被控方和主控方都配置cascade="none"
	 *  如果主控方group.hbm.xml中配置的cascade="delete"或者cascade="all"
	 *  则删除的时候会级联删除掉User
	 */
	public static void testDeleteGroup(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		//删除指定的User以及关系
		Group g = (Group) s.get(Group.class, 9);
		User u = (User) s.get(User.class, 7);
		g.getUsers().remove(u);//删除关系需要先把users中的相应的user移除掉
		s.delete(g);
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
	
	
	/**
	 *  这里被控方和主控方都配置cascade="none"
	 * 	这里如果需要删除关系还是需要先获得主控方,通过主控方来维护关系
	 */
	public static void testDeleteUser(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		//删除指定的User以及关系
		User u = (User) s.get(User.class, 12);
		Set<Group> gs = u.getGroups();
		for (Group g : gs) {
			g.getUsers().remove(u); //如果需要删除关系就需要此操作
		}
		s.delete(u);
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
	
	/**
	 * 这里查询不分主控方和被控方
	 * 配置查询加载方式 
	 * 	lazy="false" 不使用懒加载,查询时直接加载关联数据
	 *  lazy="true" 支持懒加载,只有在用到关联数据时再去执行查询
	 *  支持懒加载需要注意:在用到关联数据时只能在一个事务内(即一个数据库session内)
	 *  如果事务外使用到该数据,程序则会报数据库连接异常,因为在事务外执行查询时,session已经关闭。 
	 * 这里要根据自己项目中需要来采取最佳配置
	 */
	public static void testSelect(){
		Session s = HibernateSessionFactory.getSession();
		s.beginTransaction();
		List<Group> gs = s.createQuery("from Group").list();
		for (Group g : gs) {
			/**
			 * 这里还需要注意,这里打印对象时不能使用默认的toString()方法
			 * 因为默认的toString()方法中对Set集合的处理是直接调用Set集合中每个对象的toString()
			 * 如果Group对象中有User值,则在会出现Group.toString() 中调用Set中的 User.toString()
			 * 而User.toString()中则会掉用Set中的Group.toString()方法,而出现死循环而导致内存溢出异常
			 */
			System.out.println(g);//
		}
		Set<User> us = gs.get(3).getUsers();
		for (User user : us) {
			System.out.println(user);
		}
		List<User> users = s.createQuery("from User").list();
		for (User u : users) {
			System.out.println(u);
		}
		s.flush();
		s.getTransaction().commit();
		s.clear();
		s.close();
	}
}


  • 0
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 7
    评论
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值