SpringData-Operations on multiple tables

1. Create a package class corresponding to the database

User:

@Entity     //实体类
@Table(name = "sys_user")     //实体类对应数据库表名
public class User {

    @Id     //主键
    @GeneratedValue(strategy = GenerationType.IDENTITY)     //主键自增
    @Column(name="user_id")     //数据库对应列名
    private Long userId;

    @Column(name="user_name")
    private String userName;

    @Column(name="age")
    private Integer age;

    /**
     * 配置用户到角色的多对多关系
     *      配置多对多的映射关系
     *          1.声明表关系的配置
     *              @ManyToMany(targetEntity = Role.class)  //多对多
     *                  targetEntity:代表对方的实体类字节码
     *          2.配置中间表(包含两个外键)
     *                @JoinTable
     *                  name: 中间表的名称
     *                  joinColumns:配置当前对象在中间表的外键
     *                      @JoinColumn的数组
     *                          name:外键名
     *                          referencedColumnName:参照的主表的主键名
     *                  inverseJoinColumns:配置对方对象在中间表的外键
     */
    @ManyToMany(targetEntity = Role.class)
    @JoinTable(name = "sys_user_role",    //中间表
            //joinColumns, 当前对象在中间表中的外键
            joinColumns = {@JoinColumn(name = "sys_user_id", referencedColumnName = "user_id")},
            //inverseJoinColumns,对方对象在中间表的外键
            inverseJoinColumns = {@JoinColumn(name = "sys_role_id", referencedColumnName = "role_id")}
    )
    private Set<Role> roles = new HashSet();


    //getter setter 方法....

    //toString() 方法....

}

Role:

@Entity     //实体类
@Table(name = "sys_role")      //实体类对应数据库表名
public class Role {

    @Id     //主键
    @GeneratedValue(strategy = GenerationType.IDENTITY)     //主键自增
    @Column(name = "role_id")      //数据库对应列名
    private Long roleId;
    
    @Column(name = "role_name")
    private String roleName;

    @ManyToMany(targetEntity = User.class)
    @JoinTable(name = "sys_user_role",    //中间表
            //joinColumns, 当前对象在中间表中的外键
            joinColumns = {@JoinColumn(name = "sys_role_id", referencedColumnName = "role_id")},
            //inverseJoinColumns,对方对象在中间表的外键
            inverseJoinColumns = {@JoinColumn(name = "sys_user_id", referencedColumnName = "user_id")}
    )
    private Set<User> users = new HashSet();

    //getter setter 方法....

    //toString() 方法....

}

2. Create a dao layer interface specification that conforms to SpringDataJpa

UserDao:

public interface UserDao extends JpaRepository<User, Long>, JpaSpecificationExecutor<User> {

}

RoleDao:

public interface RoleDao extends JpaRepository<Role, Long>, JpaSpecificationExecutor<Role> {

}

Three. Write the test class

Write a test framework:

@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:applicationContext.xml")
public class ManyToManyTest {

    @Autowired
    private UserDao userDao;
    @Autowired
    private RoleDao roleDao;


}

1. Save a user while saving the role associated with the user

@Test
@Transactional
@Rollback(false)
public void  testAdd() {
    //创建一个用户
    User user = new User();
    user.setUserName("小李");
    user.setAge(18);
    //用户关联的角色
    Role role = new Role();
    role.setRoleName("java程序员");
    //配置用户到角色关系,可以对中间表中的数据进行维护
    user.getRoles().add(role);
    //配置角色到用户的关系,可以对中间表的数据进行维护
    role.getUsers().add(user);

    userDao.save(user);
    roleDao.save(role);
}

At runtime, the intermediate table will be processed twice, causing an exception to be thrown. Here you need to give up the rights protection processing: the passive party (role) gives up.

Modify the Role package class:

*** The value of mappedBy is a member variable of Role defined in the User package class

@ManyToMany(mappedBy = "roles")      //配置多表关系
private Set<User> users = new HashSet();

2. Cascade add (add the user while adding the user's corresponding role)

Modify the User package class:

* Modify the annotation on the member attribute in the User package class:

(CascadeType.ALL is to cascade all operations)

(CascadeType.MERGE is a cascading update operation)

(CascadeType.PERSIST is a cascade save operation)

(CascadeType.REMOVE is a cascade delete operation)

@ManyToMany(targetEntity = Role.class, cascade = CascadeType.ALL)
@JoinTable(name = "sys_user_role",    //中间表
        //joinColumns, 当前对象在中间表中的外键
        joinColumns = {@JoinColumn(name = "sys_user_id", referencedColumnName = "user_id")},
        //inverseJoinColumns,对方对象在中间表的外键
        inverseJoinColumns = {@JoinColumn(name = "sys_role_id", referencedColumnName = "role_id")}
)

Define the method of cascading addition:

@Test
@Transactional
@Rollback(false)
public void  testCasCadeAdd() {
    //创建一个用户
    User user = new User();
    user.setUserName("小王");
    user.setAge(28);
    //用户关联的角色
    Role role = new Role();
    role.setRoleName("产品经理");
    //配置用户到角色关系,可以对中间表中的数据进行维护
    user.getRoles().add(role);
    //配置角色到用户的关系,可以对中间表的数据进行维护
    role.getUsers().add(user);

    userDao.save(user);
}

Define the method of cascading delete:

@Test
@Transactional
@Rollback(false)
public void  testCasCadeRemove() {
    //查询1号用户
    User user = userDao.findOne(1L);
    //删除1号用户
    userDao.delete(user);
}

 

Source code download:  https://pan.baidu.com/s/1lqRG8mPJet2IxbGZHsJcqg

 

Guess you like

Origin blog.csdn.net/weixin_42629433/article/details/84784713