zoukankan      html  css  js  c++  java
  • mybatis 多对多 处理

    转载于 @ feiyeguohai;本人绝无抄袭之意,仅为借鉴大神见解;如有冒犯,敬请见谅

     

    mybatis 多对多 处理

    博客分类:
     
      下面的例子让新手看不错。可以改进的一点是
              1、不必建立 关联对象实体,可以用map传递两个id进去
              2、文章的resultMap 继承和 查询配置 比较清楚,可以借鉴
     

          mybatis3.0添加了association和collection标签专门用于对多个相关实体类数据进行级联查询,但仍不支持多个相关实体类数据 的级联保存和级联删除操作。因此在进行实体类多对多映射表设计时,需要专门建立一个关联对象类对相关实体类的关联关系进行描述。下文将以“User”和 “Group"两个实体类之间的多对多关联映射为例进行CRUD操作。

         建立user表,对应实体类"User",建表语句如下:
         <!--StartFragment-->

    Sql代码  收藏代码
    1. CREATE TABLE `user` (  
    2.   `id` int(11) NOT NULL auto_increment,  
    3.   `name` varchar(40) collate utf8_unicode_ci default NULL,  
    4.   `password` varchar(20) collate utf8_unicode_ci default NULL,  
    5.   `createtime` timestamp NULL default CURRENT_TIMESTAMP,  
    6.   PRIMARY KEY  (`id`)  
    7. )   

     

        建立group_info表,对应实体类"Group",建表语句如下:

       

    Sql代码  收藏代码
    1. CREATE TABLE `group_info` (  
    2.   `id` int(11) NOT NULL auto_increment,  
    3.   `name` varchar(40) collate utf8_unicode_ci default NULL,  
    4.   `createdate` timestamp NULL default CURRENT_TIMESTAMP,  
    5.   `state` int(1) default '0' COMMENT '0:可见;1:不可见',  
    6.   PRIMARY KEY  (`id`)  
    7. )  

     

       建立user_group表,对应实体类"UserGroupLink"(该类为User和Group两个实体类之间的关系描述),建表语句如下:

       

    Sql代码  收藏代码
    1. CREATE TABLE `user_group` (  
    2.   `user_id` int(11) default NULL,  
    3.   `group_id` int(11) default NULL,  
    4.   `createdate` timestamp NULL default CURRENT_TIMESTAMP,  
    5.   KEY `FK_user_group_user_id` (`user_id`),  
    6.   KEY `FK_user_group_group_id` (`group_id`),  
    7.   CONSTRAINT `FK_user_group_group_id` FOREIGN KEY (`group_id`) REFERENCES `group_info` (`id`),  
    8.   CONSTRAINT `FK_user_group_user_id` FOREIGN KEY (`user_id`) REFERENCES `user` (`id`)  
    9. )   

      

       建立实体类User,代码如下:

    Java代码  收藏代码
    1. package com.xxt.ibatis.dbcp.domain;  
    2.   
    3. import java.util.Date;  
    4. import java.util.List;  
    5.   
    6. /** 
    7.  * @describe: User实体类 
    8.  * @author:    Nirvana 
    9.  * @version:   V1.0  2011-3-11下午06:06:49 create 
    10.  */  
    11.   
    12. public class User {  
    13.   
    14.     private long id;  
    15.   
    16.     private String name;  
    17.   
    18.     private String password;  
    19.   
    20.     private Date createTime;  
    21.   
    22.     private List<Group> group;  
    23.   
    24.     public Date getCreateTime() {  
    25.         return createTime;  
    26.     }  
    27.   
    28.     public void setCreateTime(Date createTime) {  
    29.         this.createTime = createTime;  
    30.     }  
    31.   
    32.     public long getId() {  
    33.         return id;  
    34.     }  
    35.   
    36.     public void setId(long id) {  
    37.         this.id = id;  
    38.     }  
    39.   
    40.     public String getName() {  
    41.         return name;  
    42.     }  
    43.   
    44.     public void setName(String name) {  
    45.         this.name = name;  
    46.     }  
    47.   
    48.     public String getPassword() {  
    49.         return password;  
    50.     }  
    51.   
    52.     public void setPassword(String password) {  
    53.         this.password = password;  
    54.     }  
    55.   
    56.     public List<Group> getGroup() {  
    57.         return group;  
    58.     }  
    59.   
    60.     public void setGroup(List<Group> group) {  
    61.         this.group = group;  
    62.     }  
    63. }  

      

        建立实体类Group,代码如下:

    Java代码  收藏代码
    1. package com.xxt.ibatis.dbcp.domain;  
    2.   
    3. import java.util.Date;  
    4. import java.util.List;  
    5.   
    6. /** 
    7.  * @describe: Group实体类 
    8.  * @author: Nirvana 
    9.  * @version: V1.0 2011-3-7下午08:10:29 create 
    10.  */  
    11. public class Group {  
    12.   
    13.     private long id;  
    14.   
    15.     private String name; // 组名  
    16.   
    17.     private Date createTime;  
    18.   
    19.     private int state; // 0可见状态 1不可见状态  
    20.   
    21.     private List<User> user;  
    22.   
    23.     public Date getCreateTime() {  
    24.         return createTime;  
    25.     }  
    26.   
    27.     public void setCreateTime(Date createTime) {  
    28.         this.createTime = createTime;  
    29.     }  
    30.   
    31.     public long getId() {  
    32.         return id;  
    33.     }  
    34.   
    35.     public void setId(long id) {  
    36.         this.id = id;  
    37.     }  
    38.   
    39.     public String getName() {  
    40.         return name;  
    41.     }  
    42.   
    43.     public void setName(String name) {  
    44.         this.name = name;  
    45.     }  
    46.   
    47.     public int getState() {  
    48.         return state;  
    49.     }  
    50.   
    51.     public void setState(int state) {  
    52.         this.state = state;  
    53.     }  
    54.   
    55.     public List<User> getUser() {  
    56.         return user;  
    57.     }  
    58.   
    59.     public void setUser(List<User> user) {  
    60.         this.user = user;  
    61.     }  
    62.   
    63. }  

        建立实体类UserGroupLink,用于描述User和Group之间的对应关系,代码如下:

    Java代码  收藏代码
    1. package com.xxt.ibatis.dbcp.domain;  
    2.   
    3. import java.util.Date;  
    4.   
    5. /** 
    6.  * @describe: 描述User和Group之间的映射关系 
    7.  * @author: Nirvana 
    8.  * @version: V1.0 2011-3-11下午02:57:52 create 
    9.  */  
    10. public class UserGroupLink {  
    11.   
    12.     private User user;  
    13.   
    14.     private Group group;  
    15.   
    16.     private Date createTime;  
    17.   
    18.     public Date getCreateTime() {  
    19.         return createTime;  
    20.     }  
    21.   
    22.     public void setCreateTime(Date createTime) {  
    23.         this.createTime = createTime;  
    24.     }  
    25.   
    26.     public Group getGroup() {  
    27.         return group;  
    28.     }  
    29.   
    30.     public void setGroup(Group group) {  
    31.         this.group = group;  
    32.     }  
    33.   
    34.     public User getUser() {  
    35.         return user;  
    36.     }  
    37.   
    38.     public void setUser(User user) {  
    39.         this.user = user;  
    40.     }  
    41. }  

        建立user实体类的映射文件user.map.xml,代码如下:

    Xml代码  收藏代码
    1. <?xml version="1.0" encoding="UTF-8" ?>  
    2. <!DOCTYPE mapper   
    3.     PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"   
    4.     "http://mybatis.org/dtd/mybatis-3-mapper.dtd">  
    5. <mapper namespace="com.xxt.ibatis.dbcp.domain.User">  
    6.     <resultMap type="User" id="userMap">  
    7.         <id property="id" column="id" />  
    8.         <result property="name" column="name" />  
    9.         <result property="password" column="password" />  
    10.         <result property="createTime" column="createtime" />  
    11.     </resultMap>  
    12.   
    13.     <resultMap type="User" id="userGroupMap" extends="userMap">  
    14.         <collection property="groups" ofType="Group">  
    15.             <id property="id" column="goupId" />  
    16.             <result property="name" column="groupName" />  
    17.             <result property="state" column="state" />  
    18.             <result property="createTime" column="groupCreateTime" />  
    19.         </collection>  
    20.     </resultMap>  
    21.   
    22.   
    23.     <!-- 根据user表中的id查询用户信息 -->  
    24.     <select id="selectUser" parameterType="long" resultMap="userMap">  
    25.         select * from user where id = #{id}  
    26.     </select>  
    27.   
    28.     <!-- 根据user表中的id查询用户和组信息 -->  
    29.     <select id="selectUserGroup" parameterType="long"  
    30.         resultMap="userGroupMap">  
    31.         select u.id,u.name,u.password,u.createtime, gi.id as  
    32.         goupId,gi.name as groupName, gi.createdate as groupCreateTime,  
    33.         gi.state from user u left join user_group ug on u.id=ug.user_id  
    34.         left join group_info gi on ug.group_id=gi.id where u.id = #{id}  
    35.     </select>  
    36.   
    37.     <!-- 插入用户信息 -->  
    38.     <insert id="saveUser" parameterType="User" keyProperty="id"  
    39.         useGeneratedKeys="true">  
    40.         insert into user(name,password) values(#{name},#{password})  
    41.     </insert>  
    42.   
    43.     <!-- 保存用户和组之间的关系信息 -->  
    44.     <insert id="saveRelativity" parameterType="UserGroupLink">  
    45.         insert into user_group(user_id,group_id)  
    46.         values(#{user.id},#{group.id})  
    47.     </insert>  
    48.   
    49.     <select id="selectAllUser" resultMap="userMap">  
    50.         select * from user  
    51.     </select>  
    52.   
    53. </mapper>  

         建立group实体类的映射文件group.map.xml,代码如下:

       

    Xml代码  收藏代码
    1. <?xml version="1.0" encoding="UTF-8"?>  
    2. <!DOCTYPE mapper   
    3.     PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"   
    4.     "http://mybatis.org/dtd/mybatis-3-mapper.dtd">  
    5. <mapper namespace="com.xxt.ibatis.dbcp.domain.Group">  
    6.     <resultMap type="Group" id="groupMap">  
    7.         <id property="id" column="id" />  
    8.         <result property="name" column="name" />  
    9.         <result property="createTime" column="createdate" />  
    10.     </resultMap>  
    11.   
    12.     <resultMap type="Group" id="groupUserMap" extends="groupMap">  
    13.         <collection property="users" ofType="User">  
    14.             <id property="id" column="userId" />  
    15.             <result property="name" column="userName" />  
    16.             <result property="password" column="password" />  
    17.             <result property="createTime" column="userCreateTime" />  
    18.         </collection>  
    19.     </resultMap>  
    20.   
    21.   
    22.     <!-- 根据Group表中的id或name查询组信息和组内用户信息 -->  
    23.     <select id="selectGroupUser" parameterType="Group"  
    24.         resultMap="groupUserMap">  
    25.         select u.id as userId,u.name as userName,  
    26.         u.password,u.createtime as userCreateTime,  
    27.         gi.id,gi.name,gi.createdate,gi.state from group_info gi left  
    28.         join user_group ug on gi.id=ug.group_id left join user u on  
    29.         uug.user_id=u.id  
    30.         <where>  
    31.             <!--当id为初始值0,不再使用id作为查询条件 -->  
    32.             <if test="id != 0  ">gi.id=#{id}</if>  
    33.             <!-- 当name为空或为空串时,不再使用name作为查询条件 -->  
    34.             <if test="name != null and name != ''">  
    35.                 or gi.name = #{name}  
    36.             </if>  
    37.         </where>  
    38.     </select>  
    39.   
    40.     <!-- 根据id查询group组信息 -->  
    41.     <select id="selectGroup" parameterType="Date"  
    42.         resultMap="groupMap">  
    43.         select * from group_info where id=#{group_id}  
    44.     </select>  
    45.   
    46.     <!--根据name查询group组信息  -->  
    47.     <select id="getGroupByName" parameterType="String"  
    48.         resultMap="groupMap">  
    49.         select * from group_info where name=#{name}  
    50.     </select>  
    51.   
    52.     <!-- 插入组信息 -->  
    53.     <insert id="saveGroup" parameterType="Group" keyProperty="id"  
    54.         useGeneratedKeys="true">  
    55.         insert into group_info(name) values(#{name})  
    56.     </insert>  
    57.   
    58.     <!-- 删除组与组内成员之间的对应关系 -->  
    59.     <delete id="deleteGroupUser" parameterType="UserGroupLink">  
    60.         delete from user_group  
    61.         <where>  
    62.             <if test="user.id != 0">user_id = #{user.id}</if>  
    63.             <if test="group.id != 0">and group_id = #{group.id}</if>  
    64.         </where>  
    65.     </delete>  
    66.   
    67.     <!--根据组id或者组name删除组信息 -->  
    68.     <delete id="deleteGroup" parameterType="Group">  
    69.         delete from group_info  
    70.         <where>  
    71.             <if test="id!=0">id=#{id}</if>  
    72.             <if test="name!=null || name!=''">and name=#{name}</if>  
    73.         </where>  
    74.     </delete>  
    75.   
    76.     <!-- 更新根据组id或者组name更新组状态 -->  
    77.     <update id="updateGroupState" parameterType="Group">  
    78.         update group_info set state=#{state}  
    79.         <where>  
    80.             <if test="id!=0">id=#{id}</if>  
    81.             <if test="name!=null || name!=''">and name=#{name}</if>  
    82.         </where>  
    83.     </update>  
    84. </mapper>  

        建立ibatis总配置文件salMapConfig.xml,代码如下:

      

    Xml代码  收藏代码
    1. <?xml version="1.0" encoding="UTF-8"?>  
    2. <!DOCTYPE configuration   
    3.     PUBLIC "-//mybatis.org//DTD Config 3.0//EN"   
    4.     "http://mybatis.org/dtd/mybatis-3-config.dtd">  
    5. <configuration>  
    6.     <properties resource="jdbc.properties" />  
    7.   
    8.     <typeAliases>  
    9.         <typeAlias type="com.xxt.ibatis.dbcp.domain.User" alias="User" />  
    10.         <typeAlias type="com.xxt.ibatis.dbcp.domain.Group"  
    11.             alias="Group" />  
    12.         <typeAlias type="com.xxt.ibatis.dbcp.domain.UserGroupLink"  
    13.             alias="UserGroupLink" />  
    14.     </typeAliases>  
    15.   
    16.     <environments default="development">  
    17.         <environment id="development">  
    18.             <transactionManager type="JDBC" />  
    19.             <dataSource type="UNPOOLED">  
    20.                 <property name="driver" value="${driver}" />  
    21.                 <property name="url" value="${url}" />  
    22.                 <property name="username" value="${username}" />  
    23.                 <property name="password" value="${password}" />  
    24.             </dataSource>  
    25.         </environment>  
    26.     </environments>  
    27.   
    28.     <mappers>  
    29.         <mapper resource="com/xxt/ibatis/dbcp/domain/user.map.xml" />  
    30.         <mapper resource="com/xxt/ibatis/dbcp/domain/group.map.xml" />  
    31.     </mappers>  
    32. </configuration>  

        测试用例,代码如下:

       

    Java代码  收藏代码
      1. package com.xxt.ibatis.dbcp.test;  
      2.   
      3. import java.io.Reader;  
      4. import java.text.SimpleDateFormat;  
      5. import java.util.List;  
      6.   
      7. import org.junit.AfterClass;  
      8. import org.junit.BeforeClass;  
      9. import org.junit.Test;  
      10.   
      11. import org.apache.ibatis.io.Resources;       
      12. import org.apache.ibatis.session.SqlSession;  
      13. import org.apache.ibatis.session.SqlSessionFactory;  
      14. import org.apache.ibatis.session.SqlSessionFactoryBuilder;  
      15.   
      16. import com.xxt.ibatis.dbcp.domain.Group;  
      17. import com.xxt.ibatis.dbcp.domain.User;  
      18. import com.xxt.ibatis.dbcp.domain.UserGroupLink;  
      19.   
      20. /** 
      21.  * @describe: 测试用例 
      22.  * @author:    Nirvana 
      23.  * @version:   V1.0  2011-3-4下午03:21:17 create 
      24.  */  
      25. public class IbatisUserTest {  
      26.   
      27.     private final static String IBATIS_CONFIG_XML  = "sqlMapConfig.xml";   
      28.     private static SqlSession session;  
      29.     private SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd k:mm:ss");  
      30.             
      31.     @BeforeClass  
      32.     public static void setUpBeforeClass() throws Exception {  
      33.          Reader reader = Resources.getResourceAsReader(IBATIS_CONFIG_XML);  //读取ibatis配置文件  
      34.          SqlSessionFactory sqlMapper = new SqlSessionFactoryBuilder().build(reader);  
      35.           session = sqlMapper.openSession(true);  
      36.           session.commit(false); //将默认提交事务属性设置为否  
      37.     }  
      38.       
      39.       
      40.     //保存用户信息  
      41.     @Test  
      42.     public void saveUserTest(){  
      43.         User user = new User();  
      44.         user.setName("张三");  
      45.         user.setPassword("123456");  
      46.         session.insert("com.xxt.ibatis.dbcp.domain.User.saveUser", user);  
      47.     }  
      48.      
      49.     //获取用户信息  
      50.     @Test  
      51.     public void getUserTest(){  
      52.         User user = (User) session.selectOne("com.xxt.ibatis.dbcp.domain.User.selectUser", 1L);  
      53.         System.out.println("用户名: "+user.getName());  
      54.         System.out.println("用户密码:  "+user.getPassword());  
      55.         System.out.println("用户创建日期:"+sdf.format(user.getCreateTime()));  
      56.     }  
      57.      
      58.     //获取用户和用户所在组信息  
      59.     @Test  
      60.     public void getUserAndGroupTest(){  
      61.          User  user =  (User)session.selectOne("com.xxt.ibatis.dbcp.domain.User.selectUserGroup", 4L);  
      62.            
      63.          System.out.println(user.getName() +"所属组信息:");  
      64.         for(Group group : user.getGroups() ){  
      65.             System.out.println("    组名:"+group.getName()+",组创建时间:"+sdf.format(group.getCreateTime()));  
      66.         }  
      67.           
      68.           
      69.     }  
      70.       
      71.     //保存用户和用户所在组信息  
      72.     //当用户所在组不存在时,创建该组,并生成映射关系  
      73.     @Test  
      74.     public void saveUserAndGroupTest(){  
      75.         User user = new User();  
      76.         user.setName("无常鬼");  
      77.         user.setPassword("wuchang");  
      78.         session.insert("com.xxt.ibatis.dbcp.domain.User.saveUser", user);  
      79.           
      80.         Group groupImpl = (Group)session.selectOne("com.xxt.ibatis.dbcp.domain.Group.getGroupByName","用户组4");//获取组实例  
      81.         UserGroupLink ugl = new UserGroupLink();//声明User和Group实体间映射关系实例  
      82.           
      83.         //查询到的组实例为空时的逻辑处理  
      84.         if(groupImpl == null){  
      85.              Group group = new Group();  
      86.              group.setName("用户组4");  
      87.             session.insert("com.xxt.ibatis.dbcp.domain.Group.saveGroup", group);//持久化创建好的组实例  
      88.               
      89.             //设置映射关系实例相关的属性  
      90.             ugl.setUser(user);  
      91.             ugl.setGroup(group);  
      92.             session.insert("com.xxt.ibatis.dbcp.domain.User.saveRelativity",ugl);//持久化映射关系实力  
      93.                       
      94.         }else{  
      95.             ugl.setGroup(groupImpl);  
      96.             ugl.setUser(user);  
      97.             session.insert("com.xxt.ibatis.dbcp.domain.User.saveRelativity",ugl);  
      98.         }  
      99.     }  
      100.       
      101.       
      102.     //删除组信息的同时,取消组内所有的成员与该组的关联关系  
      103.     @Test  
      104.     public void deleteGroupTest(){  
      105.         Group group = new Group();  
      106.         //group.setId(1L);  //以组id作为查询条件  
      107.         group.setName("用户组1"); //以组name作为查询条件  
      108.         Group groupImpl = (Group)session.selectOne("com.xxt.ibatis.dbcp.domain.Group.selectGroupUser",group);//获取组实例  
      109.           
      110.         //组实例存在时  
      111.         if(groupImpl != null){  
      112.               
      113.             List<User> users = groupImpl.getUsers();  
      114.               
      115.           //查看用户组1中是否存在用户  
      116.             if(users != null && users.size() > 0){  
      117.                   
      118.                 //存在用户时,先删除组与用户的对应关系  
      119.                 UserGroupLink ugl = new UserGroupLink();  
      120.                 for(User user : users){  
      121.                    ugl.setUser(user);  
      122.                    ugl.setGroup(groupImpl);  
      123.                    session.delete("com.xxt.ibatis.dbcp.domain.Group.deleteGroupUser",ugl );  
      124.                 }   
      125.             }  
      126.             //删除组信息  
      127.             session.delete("com.xxt.ibatis.dbcp.domain.Group.deleteGroup", groupImpl);  
      128.               
      129.         }else{  
      130.             throw new RuntimeException("查询的组不存在!!");  
      131.         }  
      132.           
      133.           
      134.     }  
      135.       
      136.       
      137.     //更新组状态,当组状态由可见状态变成不可见时,取消该组下的用户与该组的映射关系  
      138.     @Test  
      139.     public void updateGroupStateTest(){  
      140.         Group group = new Group();  
      141.         group.setName("用户组2");  
      142.         Group groupImpl = (Group) session.selectOne("com.xxt.ibatis.dbcp.domain.Group.selectGroupUser",group);  
      143.           
      144.         if(groupImpl != null){  
      145.             int state = groupImpl.getState() == 1 ? 0 : 1;  
      146.               
      147.               
      148.             //组状态由0变成1时,即由可见变为不可见  
      149.             if(state == 1){  
      150.                 List<User> users = groupImpl.getUsers();  
      151.            //查看用户组2中是否存在用户  
      152.                 if(users != null && users.size() > 0){  
      153.                       
      154.                     //存在用户时,删除组与用户的对应关系  
      155.                     UserGroupLink ugl = new UserGroupLink();  
      156.                     for(User user : users){  
      157.                        ugl.setUser(user);  
      158.                        ugl.setGroup(groupImpl);  
      159.                        session.delete("com.xxt.ibatis.dbcp.domain.Group.deleteGroupUser",ugl );  
      160.                     }   
      161.                 }  
      162.             }   
      163.               
      164.             //更新组状态  
      165.             groupImpl.setState(state);  
      166.         }  
      167.         else{  
      168.             throw new RuntimeException("查询的组不存在!!");  
      169.         }  
      170.            
      171.     }  
      172.       
      173.     @AfterClass  
      174.     public static void tearDownAfterClass() throws Exception {  
      175.       if(session != null){  
      176.          session.commit(); //提交事务  
      177.          session.close(); //关闭连接  
      178.       }  
      179.     }   
  • 相关阅读:
    Houdini 快捷键使用说明
    在Houdini中创建自定义的Python函数
    用正则表达式校验QQ号码
    [Chatter] 看小说「数字风暴」有感
    [.NET] 当用System.Messaging.MessageQueue.Send传送数据遇到InvalidCastException、NullReferenceException
    [Visual Studio] 方案总管中,自定义档案与档案之间的父子关系
    [.NET] 子对象方法的参数,参考子对象型别做为输入型别
    [Chatter] 引用新技术的考虑
    [Architecture Pattern] Inversion of Logging
    [Architecture Design] DI Thread Tips
  • 原文地址:https://www.cnblogs.com/cj28-27/p/5657485.html
Copyright © 2011-2022 走看看