首页 文章

RealmChangeListener有时不会被调用

提问于
浏览
0

我试图在非UI线程上更新数据库,但是在主线程上注册的changeListener(同时)有时不会被调用 . 每个Activity在调用onStart方法时添加该侦听器,并在onStop上取消注册 .

这是简单的应用程序流程:

Activity1包含已创建项目的列表 . 当用户想要添加新项目时,将启动Activity2 . 用户填写所有必填字段,然后按添加btn - >将创建的项目添加到具有临时ID的本地数据库中,并将作业添加到队列以在远程上创建该项目 . 在这两个操作之后,Activit2关闭(调用 finish() ),用户返回Activity1,其中包含所有已创建项目(包括新项目)的列表 . 同时,完成了在远程创建新项目的工作,并且在其 onRun() 方法中,创建的对象的tmpID被替换为从服务器检索的新对象 . 但是, at this point Activity1 do not get notified 关于数据库的更改 .

活动注册监听器如下:

public Activity extends AppCompatActivity {

      private Realm mRealm;
      private RealmChangeListener listener = element -> Log.d("Called");

      @Override
      protected void onStart() {
          super.onStart();
          mRealm = Realm.getDefaultInstance();
          mRealm.addChangeListener(realmChangeListener);
      }

      @Override
      protected void onStop() {
          super.onStop();
          mRealm.removeChangeListener(realmChangeListener);
          mRealm.close();
      }          
 }

这是作业方法,在工作线程上运行

@WorkerThread
 public void onRun() {

     Response<ItemResponse> response = mAPI.createItem(text).execute();
     if(response.isSuccessful){
         Realm realm = Realm.getDefaultInstance();
         realm.executeTransaction(r ->{
             Item i = r.where(Item.class).equalTo("id", tmpID).findFirst();
             if(i != null){
                 i.id = response.body().id;
             }
         });
         realm.close();
         // At this point onChange() method of realmChangeListener should be fired
     }
}

另一方面,如果我将继续使用Activity2(在将项目添加到本地数据库后不调用 finish() )并等到作业完成,则正确调用 onChange() RealmChangeListener方法...

两个线程都在同一进程上运行 .

我很感激任何建议

EDIT

Activity1附加了一个片段,该片段包含项目列表 . 片段然后根据onStart和onStop回调中的最佳实践Controlling the lifecycle of Realm instances为侦听器注册 .

@Override
public void onStart() {
    super.onStart();
    mRealm = Realm.getDefaultInstance();
    mRealm.addChangeListener(realmChangeListener);
}

@Override
public void onStop() {
    super.onStop();
    mRealm.removeChangeListener(realmChangeListener);
    mRealm.close();
}

片段的生命周期,当Activity2为:

Launched

  • onPause

Closed using back button or by calling finish()

  • onStart

  • onResume

出于某种原因,当手动关闭Activity2时,使用后退按钮调用 realmChangeListener . 但是,如果我使用finish()关闭它,没有任何反应......

1 回答

  • 1

    最后,几个小时后我发现了问题所在......

    Activity1有一个与项目列表相连的Fragment,该片段侦听realm数据库上的更改以更新UI . 当用户想要添加新项目时,Activity2已经启动,并且还有一个演示者,它正在从本地数据库中加载一些东西 . 那位主持人还在听Realm DB .

    And here is the problem: 当用户添加新项目且Activity2即将完成时,会在演示者上调用 close() 方法以清除资源 . 在 close() 方法中调用的命令之一是 mRealm.removeAllChangeListeners() . 这不会是一个问题,因为来自Activity1的片段在 onStart() 回调中再次注册其侦听器,但是在片段上,在演示者上的 close() 方法被称为 AFTER onStart() . 所以,基本上它从片段中删除了新注册的监听器 .

    再次,谢谢你们的意愿! @beeender,@ EpicPandaForce

相关问题