级联更新
本文将指导您如何使用Kronos的级联更新功能。
1. 一对一级联关系
本节将介绍对于Kronos中定义的一对一级联关系的级联更新。
数据类定义
我们定义User和Profile两个实体类,User实体类中包含了一个Profile实体类的引用,Profile实体类中包含了一个User实体类的引用。
User.kt
data class User(
@PrimaryKey
var id: Long? = null,
var name: String? = null,
var profileName: String? = null,
@Cascade(["profileName"], ["name"])
var profile: Profile? = null
)Profile.kt
data class Profile(
@PrimaryKey
var id: Long? = null,
var name: String? = null,
var userName: String? = null,
@Cascade(["userName"], ["name"])
var user: User? = null
)级联更新
更新User或Profile实体都可以进行级联更新,级联更新会自动修改为级联创建的实体的引用属性(支持自增主键和多层级级联关系)。
User(
id = 1,
name = "user" //这里会级联更新Profile的userName字段
).update().by { it.id }.execute()或者:
Profile(
id = 1,
name = "profile" //这里会级联更新User的profileName字段
).update().by { it.id }.execute()2. 一对多级联关系
一对多关系和一对一关系的用法类似。
数据类定义
首先,我们定义以下的Parent和Child两个实体类,Parent实体类中包含了一个Child实体类的集合,Child实体类中包含了一个Parent实体类的引用。
Parent.kt
data class Parent(
@PrimaryKey(identity = true)
var id: Long? = null,
var name: String? = null,
var children: List<Child> = listOf()
)Child.kt
data class Child(
@PrimaryKey(identity = true)
var id: Long? = null,
var name: String? = null,
var parentName: String? = null,
@Cascade(["parentName"], ["name"])
var parent: Parent? = null
)级联更新
使用KPojo.update()方法,可以实现一对多级联关系的级联更新。
在Kronos中的一对多更新时,仅支持Parent -> Child方向的级联更新。
在级联更新时不需要指定Child实体的parentId,级联更新会自动修改为Child实体的parentId(支持自增主键和多层级级联关系)。
Parent(
id = 1,
name = "parent" //这里会级联更新Child的parentName字段
).update().by { it.id }.execute()以下是一个更加复杂的、层级更深的例子:
School.kt
data class School(
@PrimaryKey
var id: Long? = null,
var name: String? = null,
var groupClasses: List<GroupClass> = listOf()
)GroupClass.kt
data class GroupClass(
@PrimaryKey
var id: Long? = null,
var name: String? = null,
var schoolName: String? = null,
@Cascade(["schoolName"], ["name"])
var school: School? = null,
var students: List<Student> = listOf()
)Student.kt
data class Student(
@PrimaryKey
var id: Long? = null,
var name: String? = null,
var groupClassName: Name? = null,
var schoolName: String? = null,
@Cascade(["groupClassName", "schoolName"], ["name", "schoolName"])
var groupClass: GroupClass? = null
)School(
id = 1,
name = "school" //这里会级联更新GroupClass和Student的schoolName字段
).update().by { it.id }.execute()3. 多对多级联关系
通过manyToMany委托,Kronos简化多对多关系为一对多关系,并为您自动创建关联表记录,详见:📚级联关系定义 - 使用委托实现级联多对多跨中间表关系。
数据类定义
首先我们定义User、Role、Relation三个实体类,其中Relation实体类中包含了User和Role两个实体类的引用,User和Role通过manyToMany委托关联。
User.kt
data class User(
@PrimaryKey
var id: Long? = null,
var name: String? = null,
var relations: List<Relation> = listOf()
){
var roles: List<Role> by manyToMany(::relations)
}Role.kt
data class Role(
@PrimaryKey
var id: Long? = null,
var name: String? = null,
var relations: List<Relation> = listOf()
){
var users: List<User> by manyToMany(::relations)
}Relation.kt
data class Relation(
@PrimaryKey
var id: Long? = null,
var userName: String? = null,
var roleName: String? = null,
@Cascade(["userName", "roleName"], ["name", "name"])
var user: User? = null,
@Cascade(["userName", "roleName"], ["name", "name"])
var role: Role? = null
)级联更新
更新User或Role实体都可以进行级联更新,并自动更新级联创建的中间表实体的引用属性赋值。
这里我们并不会自动级联更新级联的另一端的实体,因为我们无法保证级联的另一端的实体是否被其他记录所引用,因此该功能属于业务层面的范畴,需要用户自行增加更新逻辑。
User(
id = 1,
name = "user" //这里会级联更新Relation的userName字段
).update().by { it.id }.execute()或者:
Role(
id = 1,
name = "role" //这里会级联更新Relation的roleName字段
).update().by { it.id }.execute()