无法使用 Room 持久性获取查询结果

问题描述 投票:0回答:3

我正在使用 Room 持久性库开发 Android 应用程序。我有一个用户和一个汽车实体

@Entity(tableName = "users")
public class User {

    @PrimaryKey
    @NonNull
    private int id;
    private String name;

    public User(@NonNull int id, String name) {
        this.id = id;
        this.name = name;
    }
}

@Entity(tableName = "cars", foreignKeys = @ForeignKey(parentColumns  = 
"id", childColumns = "userId", entity = User.class))
public class Car {

    @PrimaryKey(autoGenerate = true)
    private int id;
    private int userId;
    private String brand;

    public Car(int userId, String brand) {
        this.userId = userId;
        this.brand = brand;
    }
}

我还创建了一个 UserWithCar 类,如下所示:

public class UserWithCar {

    @Embedded(prefix = "user_")
    public User user;

    @Embedded(prefix = "car_")
    public Car car;
}

正如您在 UserWithCar 中看到的,我使用了前缀,因为如果不这样做,我会收到以下错误:

多个字段具有相同的columnName:id。字段名称:用户 > id, 汽车 > id。

我想使用以下查询获取所有 UserWithCar:

@Query("SELECT * FROM users JOIN cars ON users.id = cars.userId")
List<UserWithCar> getUserWithCar();

使用此查询时出现以下错误:

查询返回一些列 [id, name, id, userId, Brand],它们是 com.roomdemo.data.models.UserWithCar 不使用。您可以使用 字段上的 @ColumnInfo 注释用于指定映射。 com.roomdemo.data.models.UserWithCar 有一些字段 [user_id, user_name, car_id, car_userId, car_brand] 未返回 查询。如果不应该从结果中读取它们,您 可以用@Ignore注解来标记它们。您可以抑制此警告 通过注释该方法 @SuppressWarnings(RoomWarnings.CURSOR_MISMATCH)。返回的列 查询:id、名称、id、userId、品牌。字段位于 com.foodtec.roomdemo.data.models.UserWithCar:用户 ID,用户名, 汽车 ID、汽车用户 ID、汽车品牌。

我可以帮忙吗?谢谢!

更新 使用@Wizard帮助,我从@Embeded中删除了前缀,并为用户的id添加了@ColumnInfo“uId”,为汽车的id添加了“cId”,以便不具有相同的id字段。通过这种方式,它可以工作!

android android-room
3个回答
12
投票

查询返回的列:id、name、id、userId、brand。字段位于 com.foodtec.roomdemo.data.models.UserWithCar:用户 ID,用户名, 汽车 ID、汽车用户 ID、汽车品牌。

错误表示查询返回的列与Pojo类不同。应该是一样的。或者,您可以使用

@ColumnInfo
注释将 Pojo 变量映射到列名称。

例如,

@PrimaryKey
@NonNull
@ColumnInfo(name = "user_id")
private int id;

这样,

id
将被映射到
user_id


3
投票

更改您的查询:

@Query("SELECT * FROM users JOIN cars ON users.id = cars.userId")

指定 POJO 类 UserWithCar 中的列。返回的列必须与所有列匹配,并且与您的 POJO 具有相同的列名。您可以使用 AS 更改查询中的列名称。

@Query("SELECT userId as userId , brand as brand FROM users JOIN cars ON users.id = cars.userId")

或者,您可以使用@ColumnInfo来指定列名称映射。


0
投票

修复了我的问题,如果您有机会在java项目中使用kapt,也可以修复您的问题! 兄弟说:

在 gradle 中对此进行了更改:kapt "androidx.room:room-compiler:$roomVersion" 对此:annotationProcessor“androidx.room:room-compiler:$ room_version”

© www.soinside.com 2019 - 2024. All rights reserved.