Grokking Android

Getting Down to the Nitty Gritty of Android Development

Android Tutorial: Content Provider Basics

By 26 Comments

This is the first part of a three part tutorial covering Android’s content providers. Here I’m going to introduce content providers and to cover the basic concepts you need to make use of existing ones or to write content providers on your own.

What are content providers?

Content providers are Android’s central mechanism that enables you to access data of other applications – mostly information stored in databases or flat files. As such content providers are one of Android’s central component types to support the modular approach common to Android. Without content providers accessing data of other apps would be a mess.

Content providers support the four basic operations, normally called CRUD-operations. CRUD is the acronym for create, read, update and delete. With content providers those objects simply represent data – most often a record (tuple) of a database – but they could also be a photo on your SD-card or a video on the web.

Android provides some standard content providers to access contacts, media files, preferences and so on. I am going to show you how to use these content providers in the second part of this tutorial.

In the third part I am going to explain the basics you need to write a content provider yourself. Your content provider makes accessing your data that much easier for developers of other apps. Furthermore using content providers also makes the development of widgets easier.

Content URIs

The most important concept to understand when dealing with content providers is the content URI. Whenever you want to access data from a content provider you have to specify a URI. URIs for content providers look like this:


They contain four parts: The scheme to use, an authority, an optional path and an optional id.

There are two types of URIs: directory- and id-based URIs. If no id is specified a URI is automatically a directory-based URI.

The path of content URIs can contain additional information to limit the scope. The MediaStore content provider for example distinguishes between audio and other types. In addition to this it offers URIs that limit its operations to albums only or others to genres only. Content providers normally have constants for the URIs they support. You will see some examples of URIs in part II and part III.

Content Types

Besides URIs another important concept to understand is the use of content types. Content types also have a standardized format which was first defined in RFC 1049 and refined in RFC 2045.

A content type consist of a media type and a subtype divided by a slash. A typical example is “image/png”. The media type “image” describes the content as an image file which is further specified to be of the Portable Network Graphic variety by the subtype “png”.

As with URIs there is also a standard for content types in Android. Table 2 lists the only two media types that Android accepts for content providers. As you can see, those two media types match the two types of URIs mentioned above.

The media types used for content providers
Type Usage Constant Used for single records ContentResolver.CURSOR_ITEM_BASE_TYPE Used for multiple records ContentResolver.CURSOR_DIR_BASE_TYPE

The subtype on the other hand is used for content provider specific details and should differ for all types your content provider supports. The naming convention for subtypes is vnd.yourcompanyname.contenttype. For our sample project the subtype is “vnd.cpsample.lentitems”.

Most content providers support multiple subtypes. In the case of a media player for example you might have subtypes for genre, band, titles, musicians and so on.

Which standard Content Providers are available?

A number of content providers are part of Android’s API. All these standard providers are defined in the package android.provider. The following table lists the standard providers and what they are used for.

The standard content providers of Android
Provider Since     Usage
Browser SDK 1 Manages your web-searches, bookmarks and browsing-history.
CalendarContract SDK 14 Manages the calendars on the user’s device.
CallLog SDK 1 Keeps track of your call history.
Contacts SDK 1 The old and deprecated content provider for managing contacts. You should only use this provider if you need to support an SDK prior to SDK 5!
ContactsContract SDK 5 Deals with all aspects of contact management. Supersedes the Contacts-content provider.
MediaStore SDK 1 The content provider responsible for all your media files like music, video and pictures.
Settings SDK 1 Manages all global settings of your device.
UserDictionary SDK 3 Keeps track of words you add to the default dictionary.

Please make use of the standard providers whenever you need data they provide. For example there are apps that ignore the UserDictionary (e.g. Swype). So the user might end up adding the same words in multiple apps – which is pretty annoying. Something like this will not help your rating in Android’s Market.

Of course you should always keep in mind that not all of the standard providers might be present on certain devices. E.g. a tablet might have no CallLog. Thus you should always test for availability. One way to do so is querying a content provider and checking if the returned cursor is null. That’s the return value when the provider doesn’t exist. The other CRUD-methods though throw an exception in case you pass in an unknown URI.

Lessons learned

In this part of this mini series you have learned all about the two types of URIs for content providers as well as about the two media types of content types. I have listed the standard providers that Android brings with it and that you can use in your projects. How to use them is the topic of the next part of this mini-series: Using content providers.

Wolfram Rittmeyer lives in Germany and has been developing with Java for many years.

In recent years he shifted his attention to Android and blogs about anything interesting that came up while developing for Android.

You can find him on Google+ and Twitter.

26 thoughts on “Android Tutorial: Content Provider Basics”

  1. Hi
    This is good and simple.thanks

  2. thanks for a great tutorial
    its helps me as a beginner alot

  3. Thanx for tutorial

  4. Nice!

  5. this is simply one of the most brilliant tutorial i came across, just studied basic of content provider, going for part,

    You are good, everything is nice and so well explained.

    1. Thanks! I always strive to explaing things thoroughly.

  6. well explained! thank you so much

  7. Thanks for this & related tutorials. Still I am a little bit confused about the following:

    ContentProvider’s CRUD methods are basically running on the UI thread. I have seen examples making use of CursorLoader to run a ContentProvider query on the background, producing data for a ListView for example; but I have not come across an example using a ContentProvider’s insert, update or delete method on the background thread. Does it make any sense to use a ContentProvider’s insert, update or delete method together with a CursorLoader or any other object that places these operations in the background thread?

    I could adapt a background use of ContentProvider for an insert operation as well (with CursorLoader, actually) – it worked, but looking at the debugger I found that it opened up several new threads that would not cease after the insert operation was over. It just does not seem a neat solution…

  8. Hi Wolfram,
    I just wanted to say Thanks. Your ContentProvider tutorials are just what I needed to complete my project.

    Best Wishes,

  9. I am using content providers in a simulation under Eclipse ADT, i.e. , I am using the emulator. Where are data corresponding to an URL like content://course.labs.contentproviderlab.provider/badges physically stored? In a directory on my PC?

    Actually, using this URL I get a crash
    03-12 07:42:31.438: E/AndroidRuntime(1285): java.lang.IllegalArgumentException: Unknown URL content://course.labs.contentproviderlab.provider/badges

    What does it exactly mean?

    1. Wolfram Rittmeyer

      Your emulator image file is stored on your pc. Where the data of your provider can be found within the file system of the emulator is dependent on the kind of content provider you use. Most likely you se an SQLite backed content provider. In that case the data could be found in /data/data/ Here you can find a file containing your database. How to create the database and what to name it is up to you.

      The exception though is caused by the URL not being registered. You have to register your content provider in the AndroidManifest.xml file. You can find all the necessary information on how to do that in my tutorial on writing a content provider.

  10. You are writing great tuorials, although I am a little bit confused about ID-based and Directory based URI’s.
    I am trying to update one record in a table and to approach that record I use ContentUris.withAppendedId. The Uri that I use is for a table called ‘categeories’ and the id is ’21’.
    But when I use that new Uri in the update method I get an error because the system only sees the ID in the URI and no longer the table in the original Uri: SQLiteException: while compiling: SELECT category from 21…..
    It should select category with id ’21’ from table ‘categories’.
    What am I doing wrong?

    1. Wolfram Rittmeyer

      What you are doing as a client sounds about right. I assume the problem lies within your ContentProvider subclass. See my tutorial on writing a content provider.

      Did you correctly set up your UriMatcher entries and used your UriMatcher object to parse the uri in the update method? Those two are the most likely problems.

      If this is not sufficient to get you on track again, I suggest to post a question on SO (you can ping me via the contact form with a link to your question, when you have done so). Add your client code together with the UriMatcher part and the update() method of your provider to your question, so that anyone willing to help can understand what’s going on.

      1. Thank you very much for your reply, because I am back on track again now.
        My problem was indeed caused by a malfunctioning UriMatcher in the update method of the provider.

        1. Wolfram Rittmeyer

          Glad to hear that. Happy coding!

  11. nice article helpful with me thanks for sharing.

  12. Hi Wolfram,
    Thanks for the awesome post as always. In my app, I want to delete all the images, videos and all thumbnails. I am able to do that using the MediaStore Provider. What query I’ve is if there are a lot of images and videos, then the delete operation takes much time. So, I was looking for a handler kind of thing that will notify if the operation is completed. Meanwhile the operation, I’ll show a progress dialog. How can I accomplish this. Thanks in advance for any help.

  13. How can I use content provider to determine total number and total amount of memory consumed by images, videos and audio files individually. Thanx in advance

  14. Very nice tutorial! Thanks!

  15. Hi.. Thanks for the tutorial.. 🙂

    I have one doubt. How to insert the values from one app to another app(Content provider extents app).

  16. Outstanding Tutorial!

    1. Thanks a lot! Be very careful when deciding to use a ContentProvider. Ask yourself what are the benifits you gain with a ContentProvider. And what are the downsides of using one.

      Ask your self as a client: Is there really no better alternative (like activities that you might start via implicit intents)?

      Also when you plan to create your own ContentProvider, I nowadays recommend only to do so, if you really plan on sharing your data with other apps. There’s not much to be gained by using them in your own app.

  17. Good tutorial! I have a loader to get audio file but I can’t get audio in Zing MP3 file and files of system. I read document and research document and I know that loader to get data in content provider by Context(). I want get all audio file. Help me! Please!!!

    1. First of all: That’s a question too specific and should be asked on StackOverflow. If you do so, please add way more information. Most important: What’s the contract of the called ContentProvider? Most likely you’re getting a URI that you have to use to load binary data.

      Still: I have written a post about how to deal with binary data. But you first need to know how to get the correct URI. And for that you need to understand the contract of the exporting ContentProvider.

  18. superb explanation. waiting for other post like recycler view and java 8 features.

Leave a Reply

Your email address will not be published. Required fields are marked *