没有@PrimaryKey 的 RealmObject 无法更新

Kub*_*bik 5 android realm

我目前正在重构一些旧应用程序,并且正在尝试从 SQLite 迁移到 Realm。我以前用过 Realm,从来没有遇到过这样的问题。当我第一次启动我的应用程序时(安装后),我得到这个异常:

E/AndroidRuntime: FATAL EXCEPTION:
Process: xx.xxx.xxx.beta.realm, PID: 25947
java.lang.IllegalArgumentException: A RealmObject with no @PrimaryKey cannot be updated: class xx.xxx.xxx.realm.Vod
   at io.realm.Realm.checkHasPrimaryKey(Realm.java:1184)
   at io.realm.Realm.copyToRealmOrUpdate(Realm.java:713)
   at xx.xxx.xxx.services.VodService$4.run(VodService.java:232)
   at java.lang.Thread.run(Thread.java:818)
Run Code Online (Sandbox Code Playgroud)

我的 Vod 类看起来像这样,并且对象已正确创建,即具有 PrimaryKey 和所有其他字段的值:

public class Vod extends RealmObject {

    @PrimaryKey
    private String uuid;

    private String name;
    private Integer lengthMin;
    private Boolean hasTrailer;
    private String description;
    private String originalName;

    //etc...

    //getters & setters
Run Code Online (Sandbox Code Playgroud)

这将使应用程序崩溃。但是在第一次(以及每一次)之后,一切正常——使用相同的代码和相同的数据。但是当我再次卸载并重新安装应用程序时,我也会再次遇到此异常。有问题的代码部分在后台线程上运行。如果我将它移动到 UI 线程,即使是第一次也一切正常。但我想在后台线程而不是 UI 上解析网络响应。此外,它不是特定于 Vod 类的,如果我跳过 Vod 的数据并从例如 User 类开始,那么我会收到 User 类的“无@PrimaryKey”异常。

有时它也会抛出这个异常:

D/REALM: jni: ThrowingException 5, , .
D/REALM: Exception has been throw: File not found: .
E/AndroidRuntime: FATAL EXCEPTION:
   Process: xx.xxx.xxx.beta.realm, PID: 28555
   io.realm.exceptions.RealmIOException: File not found: .
       at io.realm.internal.SharedGroup.createNativeWithImplicitTransactions(Native Method)
       at io.realm.internal.SharedGroup.<init>(SharedGroup.java:67)
       at io.realm.internal.SharedGroupManager.<init>(SharedGroupManager.java:47)
       at io.realm.BaseRealm.<init>(BaseRealm.java:76)
       at io.realm.Realm.<init>(Realm.java:126)
       at io.realm.Realm.createAndValidate(Realm.java:246)
       at io.realm.Realm.createInstance(Realm.java:231)
       at io.realm.RealmCache.createRealmOrGetFromCache(RealmCache.java:114)
       at io.realm.Realm.getDefaultInstance(Realm.java:181)
       at xx.xxx.xx.services.RecordingService$9.run(RecordingService.java:317)
    at java.lang.Thread.run(Thread.java:818) 
Run Code Online (Sandbox Code Playgroud)

这让我想到,Realm 文件的初始化会有一些问题?我像这样创建它:

public class MainApplication extends Application {

  private static Context mContext;

  @Override
  public void onCreate() {
    super.onCreate(); 

    mContext = getApplicationContext();

    mRealmConfig = new RealmConfiguration.Builder(mContext).build();
    Realm.setDefaultConfiguration(mRealmConfig);
  }
}
Run Code Online (Sandbox Code Playgroud)

然后使用它在线程中获取实例:

Realm localRealm = Realm.getDefaultInstance();
Run Code Online (Sandbox Code Playgroud)

难道我做错了什么?有没有人遇到过这种类型的问题?我试图在网上搜索答案,但没有发现任何有用的信息。谢谢你的帮助。

(我正在使用 io.realm:realm-android:0.87.4)

编辑:我已经确认(通过 ADB),卸载后删除了我的应用程序包的内部存储文件夹。在检查时,我发现在第一次应用程序运行期间,路径 /data/data//files 中的文件夹是空的。这是正确的行为吗?此外,我无法通过 Stetho 在 Realm 中看到任何东西。

步骤: 1.我卸载应用程序

  1. 亚行说 cd: /data/data/xx.xxx.xxx.beta.realm: No such file or directory

  2. 我再次安装并运行应用程序

  3. ADB run-as xx.xxx.xxx.beta.realm -> cd files -> ls -> empty

  4. 通过 Stetho 检查,显示无数据

  5. 等待一分钟左右(给 Realm 时间来创建任何需要的东西)

  6. 启动网络请求和应用程序崩溃(“无@PrimaryKey”异常),第一个数据解析外部 UI 线程(在 UI 上解析工作正常)

  7. ADB -> 文件夹 -> ls -> 我可以看到一切,default.realm、default.realm.lock、default.realm.log、default.realm.log_a、default.realm.log_b

  8. 再次启动应用程序,一切正常,我什至可以通过 Stetho 查看领域数据。

我真的希望我犯了一些愚蠢的错误,最后一切都会好起来的。还有一件事,在应用程序启动时,我多次看到此日志:

Rejecting re-init on previously-failed class java.lang.Class<io.realm.rx.RealmObservableFactory$4>
Run Code Online (Sandbox Code Playgroud)

我读过这个:https : //github.com/realm/realm-java/issues/1990我不认为它与我的问题有关,但可以肯定。

小智 2

您的导入可能会被搞乱。确保导入io.realm.annotations.PrimaryKey,而不是androidx.room.PrimaryKey,这可能是一个常见问题。