Android 如何处理房间中嵌套的1对1对象中的关系数据(将ForeignKey转换为Object)

Android 如何处理房间中嵌套的1对1对象中的关系数据(将ForeignKey转换为Object),android,android-room,android-architecture-components,android-jetpack,Android,Android Room,Android Architecture Components,Android Jetpack,假设我有一个订单和一个用户实体,类似如下: User.java: @Entity public class User { @PrimaryKey public long id; @NonNull public String username; } @Entity(foreignKeys = @ForeignKey(entity = User.class, parentColumn

假设我有一个
订单
和一个
用户
实体
,类似如下:

User.java

@Entity
public class User {
    @PrimaryKey    
    public long id;
    @NonNull    
    public String username;
}
@Entity(foreignKeys = @ForeignKey(entity = User.class,
                                  parentColumns = "id",
                                  childColumns = "user_id",
                                  onDelete = ForeignKey.CASCADE,
                                  onUpdate = ForeignKey.CASCADE),
        indices = @Index("user_id"))
public class Order {
    @PrimaryKey
    public long id;
    public String description;

    @ColumnInfo(name = "user_id")
    public long userId;
    @Ignore
    private User user;
}
Order.java

@Entity
public class User {
    @PrimaryKey    
    public long id;
    @NonNull    
    public String username;
}
@Entity(foreignKeys = @ForeignKey(entity = User.class,
                                  parentColumns = "id",
                                  childColumns = "user_id",
                                  onDelete = ForeignKey.CASCADE,
                                  onUpdate = ForeignKey.CASCADE),
        indices = @Index("user_id"))
public class Order {
    @PrimaryKey
    public long id;
    public String description;

    @ColumnInfo(name = "user_id")
    public long userId;
    @Ignore
    private User user;
}
这样,我就有了一个
订单
,里面有一个
用户
,在数据库上,我只把这个与用户id的关系保存为
外键
,而不是对象本身(它是
@忽略
d),因此,一切都是好的和相关的,并且可以扩展为以几种不同的方式和查询等与其他类型一起使用

现在的问题是,如何通过
用户
对象自动填充
订单?

如果我使用
@Embedded
,那么
Order
User
将位于同一个表中,这不利于类型之间的关系分离。我可以将它们与
JOIN
一起返回,但这仍然只适用于具有不同名称的数据类型(可能它们都有一个名为“description”的列),此外,在
Order
中插入一个
用户
顺序对于
JOIN
来说并不简单
@Relation
只适用于一对多,它需要一个
列表
,这不是我的情况

我认为在
long
User
之间进行转换时,
@TypeConverter
可能是最好的选择,但这也很棘手。
@TypeConverter
需要一个对
DAO
的引用,这样它就可以查询
用户
,而
@TypeConverter
是一个静态方法,由Room调用,因此传递
DAO
可能会很棘手,并导致许多代码气味,此外,对每个
用户的额外查询将触发不在同一
@事务中的多个搜索

我不熟悉Room,但我敢打赌有一个合适的方法来解决这个问题,将Room与预期使用的关系类型一起使用,我只是不知道如何简单、良好地工作,也无法在任何文档中找到它

现在,问题是,我如何获得一个订单,其中的用户对象由其内部的房间自动填充

我认为没有现成的解决方案


IMHO,实体模型(即,
订单
将FK与
用户id
映射)不应传播到上层类似的域/表示层,提供一个
数据映射器
将实体模型转换为域模型(即,
用户
包含一个
订单
)对于上层可能是更好的选择。

IMHO,使用
@Embedded
是进行1:1映射的最简单方法。大部分的time Room数据库就像服务器响应的快照一样,很少对其执行业务逻辑,这是服务器的责任,那么为什么我们需要这样的关系分离呢?因为有时相同的数据会出现在不同的服务器响应中,所以如果我们为每个响应创建一个表,我们将浪费存储空间,例如,
Order
中可能有一个
User
,但
Shopping Cart
中也可能有
User
。那么我们将在两个不同的表上使用相同的
用户
?如果
用户
更改了他的名字,我们在应用程序的购物车页面上得到了更新,但是用户离线了怎么办?我们将在订单页面中以旧名称显示用户。如果我们试图手动同步,没有关系分离,他会变得一团糟吗?这是有道理的!我现在看到的唯一选择是使用@embedded并分离查询中的对象,以便它们从单独的表中进行更新、插入和选择,这样至少我认为我们可以依靠关系隔离,并在数据不正确时从房间中自动更新(尽管对于复杂查询,我们不确定这一点),您必须传播FK,否则,如果您偶然发现它的任何值,如何将该实体再次保存回数据库?如果删除FK,则删除与数据库的链接我不理解
传播FK
的含义。您说必须从数据库返回的对象中删除FK,对吗?不,我的意思是保留当前建模,并使用@Relation为查询结果创建另一个pojo,然后将此pojo转换为上层所需的内容。当使用Room返回
DataSource.Factory
时,这会变得更加复杂。您必须自行转换这些值,而不是使用框架提供的值。。。。更多的麻烦,没有更多的回报