Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Android Room database RxAndroid, Exception : java.lang.IllegalStateException: Cannot access database on the main thread since

Currently, I am fetching data from Web API using RxAndroid and Retrofit, and want to store that Data in Room database but getting an exception

As I search and found that, room database operations won't work on UI thread so I added .subscribeOn(Schedulers.io()) in RXAndroid still it is throwing

java.lang.IllegalStateException: Cannot access the database on the main thread since it may potentially lock the UI for a long period of time.

public void onClickLogin(View view) {

             io.reactivex.Observable
             .zip(getLogin(Constants.EMAILID, Constants.PASSWORD),
             getUserInfo(Constants.EMAILID, Constants.PASSWORD),
            getProductDetails(Constants.EMAILID, Constants.PASSWORD).subscribeOn(Schedulers.io()),
                                .observeOn(AndroidSchedulers.mainThread())
                        new Function3<List<LoginModule>,
                                List<UserInfoModule>, ProductModule, AllZipData>() {
                            @Override
                            public AllZipData apply(List<LoginModule> loginModuleList, List<UserInfoModule> useerInfoModules, ProductModule productModule) throws Exception {

                                AllZipData allZipData = new AllZipData();
                                allZipData.setLoginModuleList(loginModuleList);
                                allZipData.setUserInfoModuleList(UserInfoModule);
                                allZipData.setProductModule(productModule);

                                return allZipData;
                            }
                        }).subscribe(new Observer<AllZipData>() {
            @Override
            public void onSubscribe(Disposable d) {
                compositeDisposable.add(d);
            }

            @Override
            public void onNext(AllZipData allZipData) {


                MyDatabase MyDatabase = MyDatabase.getInstance(context);

                for (int i = 0; i < allZipData.getUserInfoModuleList().size(); i++) {

                    UserInfoTable userInfoTable = new UserInfoTable();
                    userInfoTable.setValue1(allZipData.getUserInfoModuleList().get(i).getValue1());
                    userDatabase.userDao().insertUserInfo(userInfoTable);
                }

            }

            @Override
            public void onError(Throwable e) {
                Log.e(TAG, "onError: all zip data " + e.toString());
            }

            @Override
            public void onComplete() {
                Log.e(TAG, "onComplete: all data zipped");
            }
        });
}

how to solve this exception using RxAndroid.

How to add retryWhen();?

like image 240
Ronil Raut Avatar asked Oct 21 '25 11:10

Ronil Raut


1 Answers

Where does this exception happen? If it is in onNext, that's because you specified observeOn(mainThread()) thus the database access happens on the main thread.

Try this

Observable.zip(
    getLogin(Constants.EMAILID, Constants.PASSWORD)
        .subscribeOn(Schedulers.io()),  // <--------------------------------
    getUserInfo(Constants.EMAILID, Constants.PASSWORD)
        .subscribeOn(Schedulers.io()),  // <--------------------------------
    getProductDetails(Constants.EMAILID, Constants.PASSWORD)
        .subscribeOn(Schedulers.io())   // <--------------------------------
)
.observeOn(Schedulers.io())             // <--------------------------------
.doOnNext(allZipData -> {
    MyDatabase MyDatabase = MyDatabase.getInstance(context);

    for (int i = 0; i < allZipData.getUserInfoModuleList().size(); i++) {

         UserInfoTable userInfoTable = new UserInfoTable();

         userInfoTable.setValue1(
             allZipData.getUserInfoModuleList().get(i).getValue1()
         );

         userDatabase.userDao().insertUserInfo(userInfoTable);
    }
})
.observeOn(AndroidSchedulers.mainThread())
.subscribe(new Observer<AllZipData>() {
    @Override
    public void onSubscribe(Disposable d) {
        compositeDisposable.add(d);
    }

    @Override
    public void onNext(AllZipData allZipData) {
        // notify UI here?
    }

    @Override
    public void onError(Throwable e) {
        Log.e(TAG, "onError: all zip data " + e.toString());
    }

    @Override
    public void onComplete() {
        Log.e(TAG, "onComplete: all data zipped");
    }
});
like image 104
akarnokd Avatar answered Oct 23 '25 01:10

akarnokd



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!