Android - CursorLoader & SQLite without Content Provider

I know this has been discussed, but I wanted to ask about the current state of affairs. Do I need to create a ContentProvider to use CursorLoader in connection with the sqlite database?

I found

Using CursorLoader without ContentProvider

Looks exactly what I was hoping for while commenting on Emmby

  • Users should be aware of one limitation, which is that it does not have a mechanism for updating when data changes (Loaders are supposed to be executed)

So another solution is mentioned

https://github.com/commonsguy/cwac-loaderex

again some flaw is indicated

  • However, to use automatic re-query, you need to use the same bootloader for the user interface as well as for updates, limiting its usability for background services.

Of course, when using LoaderManager, we want to get all the benefits for which it was introduced. So my question is, is there a way to use LoaderManager in connection with the sqlite database without the need to implement a content provider, but there are all the benefits.

thank

+54
android android-contentprovider sqlite android-loadermanager
Oct 13 '12 at 2:16
source share
2 answers

The two implementations that you mentioned in your post offer all the benefits of CursorLoader except the ability to receive notifications when the underlying content changes.

I have studied this question a lot recently, and I can confidently tell you that the Android API does not currently provide the means to do this only with raw SQLiteDatabase (it only provides ContentResolver#notifyChange() and Cursor#setNotificationUri() , which are used for notifications for all Cursor registered under a specific Uri notification).

However, your options right now:

  • Implementing the observer itself, which can receive notifications from SQLiteDatabase when content changes and somehow resolve these notifications for all existing Loader in your application. I wrote a fairly extensive blog post on how to implement Loader , which may come in handy if you want to take on this issue. Or...

  • Use the Mark Murphy LoaderEx and make database changes only with AsyncTask operations that its library provides. Note that the reason his tasks update Loader is because they call onContentChanged on the Loader right after the insert / update / delete, effectively telling Loader that the content has changed and that it should update its data.

  • Just use the ContentProvider with CursorLoader , and you can use the ContentResolver#notifyChange() method to notify CursorLoader that a content change has occurred.

I am trying to find a better solution, and I will report in the future if I ever find / implement it, but now it will need to be done.

+66
Oct 13
source share

Here is my solution, in my onCreateLoader

 { Uri u = Uri.parse("content://what_string_you_want"); return new CursorLoader(this, yourURI, projection, null, null, null) { private final ForceLoadContentObserver mObserver = new ForceLoadContentObserver(); @Override public Cursor loadInBackground() { Cursor c = YOUR_DATABASE.doYourQuery(...); if (c != null) { // Ensure the cursor window is filled c.getCount(); c.registerContentObserver(mObserver); } c.setNotificationUri(getContext().getContentResolver(), getUri()); return c; } }; } 

After the code that will change the database, add

  getContentResolver().notifyChange( Uri.parse("content://same_with_first_string"), null); 
+2
Dec 09 '14 at 17:25
source share



All Articles