【问题标题】:Using Realm with Gson将 Realm 与 Gson 一起使用
【发布时间】:2016-02-10 09:01:12
【问题描述】:

我有json 字段_id

 String json = "{ _id : 1, name : 'Alex', role: 'admin' }"

在我的 Realm 模型中,我使用 @SerializedName 属性:

public class User extends RealmObject {

    @SerializedName("_id")  
    @PrimaryKey
    private int id;
    private String name;
    private String comment;

    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getComment() {
        return comment;
    }

    public void setComment(String comment) {
        this.comment = comment;
    }

}  

如果尝试保存 json:

realm.createOrUpdateObjectFromJson(User.class, json)

字段 _id 无法解析并在数据库中创建了 id = 0 的记录

在使用@SerializedName 属性的文档中

  Gson gson = new GsonBuilder()
            .setExclusionStrategies(new ExclusionStrategy() {
                @Override
                public boolean shouldSkipField(FieldAttributes f) {
                    return f.getDeclaringClass().equals(RealmObject.class);
                }

                @Override
                public boolean shouldSkipClass(Class<?> clazz) {
                    return false;
                }
            }).create();


User user = gson.fromJson(json, User.class);
realm.beginTransaction();
realm.copyToRealmOrUpdate(user);

在这种情况下,json = "{ _id : 1, role: 'user' }" 只需从数据库中删除用户 name,因为 String 的默认值为 null。

所以,可能我错误地使用了该属性。在处理json的守恒方法(createOrUpdateObjectFromJson等)时如何考虑属性?

【问题讨论】:

    标签: java android json realm realm-java


    【解决方案1】:

    既然可以制作Gson,为什么还要编写所有这些自定义序列化程序? Realm 只与 一行代码 一起工作?

    IMO,为每个我们想要序列化的模型设置专有策略并不是最好的方法。正如您已经意识到的那样,这种方法需要编写大量样板代码,这容易出错,最糟糕的是,杀死了Gson 是关于(这让我们的生活不那么痛苦)。

    既然我们正在解决不兼容问题,您为什么不确保将未管理的 RealmObject 传递给您的 Gson 序列化程序?

    有史以来最简单的解决方案 (IMO)

    找到here。在内存中获取托管 RealmObject 的副本并将其传递给 Gson

    new Gson().toJson(realm.copyFromRealm(managedModel));
    

    就是这样!不用再写代码了!

    其他好的解决方案和解释是posted here.

    【讨论】:

      【解决方案2】:

      您可能需要一个混合解决方案才能完成这项工作。原因是@SerializedName 是一个 GSON 注释,而不是 Realm 知道的注释。因此,这意味着您已经发现了两种选择:

      1) 使用 GSON,这意味着最终结果是null 作为name 默认值的对象。

      2) 使用createOrUpdateObjectFromJson,这意味着_id 将被忽略,因为Realm 的JSON 解析器需要1:1 映射。

      由于这两种解决方案都无法正常工作,您可以通过以下方式对其进行修改:

      1) 使用 GSON,您可以手动搜索对象并更新角色,而不是 copyToRealmOrUpdate

      realm.beginTransaction();
      realm.where(User.class).equalTo("id", user.getId()).findFirst().setRole(user.getRole());
      realm.commitTransaction();
      

      2) 仅使用纯 JSON,您可以修改以匹配预期格式:

      JSONObject obj = new JSONObject(json);
      obj.put("id", obj.getString("_id"));
      obj.remove("_id");
      

      Realm 在跟踪自定义映射请求时存在问题,但它的优先级较低,因为 GSON、Jacokson 等框架通常会更好地覆盖该功能:https://github.com/realm/realm-java/issues/1470

      【讨论】:

      • 感谢克里斯蒂安。恕我直言,优先级必须更改为正常:)
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-11-12
      • 1970-01-01
      • 2023-03-12
      • 1970-01-01
      • 1970-01-01
      • 2016-09-24
      • 1970-01-01
      相关资源
      最近更新 更多