Android 我可以在房间中添加支票约束吗?
在我的数据库中有3个表:问题、用户和角色。角色表有2个值:客户端和coach 数据库规则: 用户只有一个角色,即客户端角色或coach角色。 一个问题有一个教练和一个客户。 problems实体有两个指向users表的外键:coach_id和client_id。我可以使用Android Room添加检查约束以确保问题遵守此规则吗 我想避免一个问题有两个客户或两个教练的情况 数据库概念图Android 我可以在房间中添加支票约束吗?,android,sqlite,relational-database,android-room,Android,Sqlite,Relational Database,Android Room,在我的数据库中有3个表:问题、用户和角色。角色表有2个值:客户端和coach 数据库规则: 用户只有一个角色,即客户端角色或coach角色。 一个问题有一个教练和一个客户。 problems实体有两个指向users表的外键:coach_id和client_id。我可以使用Android Room添加检查约束以确保问题遵守此规则吗 我想避免一个问题有两个客户或两个教练的情况 数据库概念图 当前文件室不支持添加检查约束 但是,您可以通过删除表然后创建表来引入检查约束,这可能并不理想,因为这可能会带来
当前文件室不支持添加检查约束 但是,您可以通过删除表然后创建表来引入检查约束,这可能并不理想,因为这可能会带来持续的复杂性,例如在迁移时 然而,检查约束是有限的,不能包括子查询,我相信这会使问题复杂化,甚至可能排除存在合适/可用的检查约束 我相信您会看到类似于coach INTEGER CHECKSELECT authority FROM user JOIN role ON role.roleid=user.role=0的内容在更新级联的删除级联上引用useruserid,假设coach必须具有权限为0的角色,因为不清楚哪个列表示角色类型。但是,无法使用该检查,因为它将导致检查约束错误中禁止的子查询。 因此,在插入问题的过程中,以编程方式执行此类检查可能更简单。也就是说,对于每种类型,如果指定了错误的角色,coach/client从用户处获取角色,并拒绝实际插入到数据库中。这更类似于Room的OO状态,即表支持并根据对象创建 实例 也许根据你的问题考虑以下问题:- java角色表 java用户表 java问题表 UserWithRole.java POJO将用户与用户的角色结合起来 没有实际使用,但可以用于检查 java数据访问全部合并 IsuUserAcach是复制上面假定的检查约束的重要查询。 Database.java Room@Database java进行全面测试
当前文件室不支持添加检查约束 但是,您可以通过删除表然后创建表来引入检查约束,这可能并不理想,因为这可能会带来持续的复杂性,例如在迁移时 然而,检查约束是有限的,不能包括子查询,我相信这会使问题复杂化,甚至可能排除存在合适/可用的检查约束 我相信您会看到类似于coach INTEGER CHECKSELECT authority FROM user JOIN role ON role.roleid=user.role=0的内容在更新级联的删除级联上引用useruserid,假设coach必须具有权限为0的角色,因为不清楚哪个列表示角色类型。但是,无法使用该检查,因为它将导致检查约束错误中禁止的子查询。 因此,在插入问题的过程中,以编程方式执行此类检查可能更简单。也就是说,对于每种类型,如果指定了错误的角色,coach/client从用户处获取角色,并拒绝实际插入到数据库中。这更类似于Room的OO状态,即表支持并根据对象创建 实例 也许根据你的问题考虑以下问题:- java角色表 java用户表 java问题表 UserWithRole.java POJO将用户与用户的角色结合起来 没有实际使用,但可以用于检查 java数据访问全部合并 IsuUserAcach是复制上面假定的检查约束的重要查询。 Database.java Room@Database java进行全面测试
@Entity(tableName = "role")
public class Role {
public static final int AUTHORITY_COACH = 0;
public static final int AUTHORITY_CLIENT = 1;
@PrimaryKey
Long roleid;
String description;
int authority;
public Role(String description, int authority) {
this.description = description;
if ( authority >= AUTHORITY_CLIENT) {
this.authority = AUTHORITY_CLIENT;
} else {
this.authority = AUTHORITY_COACH;
}
}
public Long getRoleid() {
return roleid;
}
public void setRoleid(Long roleid) {
this.roleid = roleid;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public int getAuthority() {
return authority;
}
public void setAuthority(int authority) {
this.authority = authority;
}
}
@Entity(
tableName = "user",
foreignKeys = {
@ForeignKey(
entity = Role.class,
parentColumns = {"roleid"},
childColumns = {"role"},
onDelete = ForeignKey.CASCADE,
onUpdate = ForeignKey.CASCADE
)
},
indices = {
@Index("role")
}
)
public class User {
@PrimaryKey
Long userid;
String name;
String surname;
String username;
String email;
String password;
long role;
public User(String name, String surname, String username, String email, String password, long role) {
this.name = name;
this.surname = surname;
this.username = username;
this.email = email;
this.password = password;
this.role = role;
}
public Long getUserid() {
return userid;
}
public void setUserid(Long userid) {
this.userid = userid;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getSurname() {
return surname;
}
public void setSurname(String surname) {
this.surname = surname;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public long getRole() {
return role;
}
public void setRole(long role) {
this.role = role;
}
}
@Entity(
tableName = "problem",
foreignKeys = {
@ForeignKey(
entity = User.class,
parentColumns = {"userid"},
childColumns = {"coach"},
onDelete = ForeignKey.CASCADE,
onUpdate = ForeignKey.CASCADE
),
@ForeignKey(
entity = User.class,
parentColumns = {"userid"},
childColumns = {"client"},
onDelete = ForeignKey.CASCADE,
onUpdate = ForeignKey.CASCADE
)
},
indices = {
@Index(value = "coach"),
@Index(value = "client")
}
)
public class Problem {
@PrimaryKey
Long problemid;
String title;
String status;
long coach;
long client;
public Problem(){}
public Problem(String title, String status, User coach, User client) {
this.title = title;
this.status = status;
this.coach = coach.getUserid();
this.client = client.getUserid();
}
public Long getProblemid() {
return problemid;
}
public void setProblemid(Long problemid) {
this.problemid = problemid;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getStatus() {
return status;
}
public void setStatus(String status) {
this.status = status;
}
public long getCoach() {
return coach;
}
public void setCoach(long coach) {
this.coach = coach;
}
public long getClient() {
return client;
}
public void setClient(long client) {
this.client = client;
}
}
public class UserWithRole {
@Embedded
User user;
@Relation(entity = Role.class,entityColumn = "roleid",parentColumn = "role")
Role userrole;
public UserWithRole(){}
public User getUser() {
return user;
}
public Role getUserrole() {
return userrole;
}
}
@Dao
public interface AllDao {
@Insert
long insertRole(Role role);
@Insert
long insertUser(User user);
@Insert
long insertProblem(Problem problem);
@Query("SELECT (authority = " + Role.AUTHORITY_COACH + ") FROM user JOIN role ON role.roleid = user.role WHERE userid = :userid ")
boolean isUserACoach(long userid);
@Query("SELECT * FROM user WHERE userid = :userid")
User getUserById(long userid);
}
@androidx.room.Database(version = 1,entities = {Role.class,User.class,Problem.class})
public abstract class Database extends RoomDatabase {
abstract AllDao allDao();
}
public class MainActivity extends AppCompatActivity {
Database database;
AllDao allDao;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
database = Room.databaseBuilder(
this,
Database.class,
"mydb"
)
.allowMainThreadQueries()
.build();
allDao = database.allDao();
long coachRole = allDao.insertRole(new Role("Coach",Role.AUTHORITY_COACH));
long newClientRole = allDao.insertRole(new Role("New Client",Role.AUTHORITY_CLIENT));
long oldClientRole = allDao.insertRole(new Role("Old Client",Role.AUTHORITY_CLIENT));
long fredBloggs = allDao.insertUser(new User("Fred","Bloggs","fblog","fblog@mail.com","password",coachRole));
long marySmith = allDao.insertUser(new User("Mary","Smith","msmith","msmith@mail.com","password",newClientRole));
long anneWalker = allDao.insertUser(new User("Anne","Walker","awalker","awalkjer@mail.com","password",oldClientRole));
//<<<<<<<<<< SHOULD BE OK TO ADD >>>>>>>>>>
if (verifyAndAddProblem("Problem 1","new",allDao.getUserById(fredBloggs),allDao.getUserById(marySmith)) > 0) {
Log.d("PROBLEMADDRESULT","Problem Added");
} else {
Log.d("PROBLEMADDRESULT","Problem not added");
}
//<<<<<<<<<< SHOULD NOT BE ADDED (annWalker is NOT a coach) >>>>>>>>>>
if (verifyAndAddProblem("Problem 2","new",allDao.getUserById(anneWalker),allDao.getUserById(marySmith)) > 0) {
Log.d("PROBLEMADDRESULT","Problem Added");
} else {
Log.d("PROBLEMADDRESULT","Problem not added");
}
//<<<<<<<<<< SHOULD NOT BE ADDED (fredBloggs is a coach BUT is NOT a client) >>>>>>>>>>
if (verifyAndAddProblem("Problem 3","new",allDao.getUserById(fredBloggs),allDao.getUserById(fredBloggs)) > 0) {
Log.d("PROBLEMADDRESULT","Problem Added");
} else {
Log.d("PROBLEMADDRESULT","Problem not added");
}
}
//ALTERNATIVE TO CHECK CONSTRAINT DONE HERE
private long verifyAndAddProblem(String title, String status, User coach, User client) {
long rv = -1;
if (!allDao.isUserACoach(coach.getUserid()) || allDao.isUserACoach(client.getUserid())) return rv;
return allDao.insertProblem(new Problem(title,status,coach,client));
}
}
2020-01-02 08:47:33.647 D/PROBLEMADDRESULT: Problem Added
2020-01-02 08:47:33.658 D/PROBLEMADDRESULT: Problem not added
2020-01-02 08:47:33.661 D/PROBLEMADDRESULT: Problem not added