Content Providers are again one of the fundamental
building blocks of the Android Platform. So far, we have looked at Activities,
Services,
which are basic building blocks. We have also looked at intents,
notifications
and variations of the same. None
of these have dealt with stored data. Content Provider brings us to the concept
of how to deal with data stored in the Android mobile esp. if the data has to
be shared across applications.
Before we move on to shared data, let us
understand the basics of data storage support provided by Android.
There are 4
ways we can store data:
- 1. Preferences
- 2. Files
- 3. RDBMS (SQLite)
- 4. Network
Preferences
– Preferences are used to store user preferences for a single application or
across applications in a mobile. They are typically name-value pairs accessible
to the context.
Files
– Files can be stored directly on to the mobile or to extended storage mediums.
They are by default not accessible to applications other than the one that
created it.
Database
(RDBMS) – Android support creation of databases based on SQLite. These are
again private to the application that created it.
Network
– Android provides API support to store data over the network on to a server,
probably
Note that all these are various forms of storing
data and most often for a single application. Irrespective of how data is
stored, if it has to be shared across applications, Here comes the concept of
Content Providers.
Content Providers are the only way to share data
across Android applications. They store and retrieve data thus making it
accessible to all. Android platform provides default implementations of content
providers for data types like audio, video, images, contact information etc.
In the sample I would like to first show how to
work with existing content providers like the contact information. We will first
view the existing contacts on the phone. We will insert a new contact
(hardcoded name and phone number), update the same contact and delete the same
contact, in this example. Note that the update and delete will not work till we
create a contact through this example.
Introduction to Content Providers:
Irrespective of how the data is stored, Content
Providers give a uniform interface to access the data. Data is exposed as a
simple table with rows and columns where row is a record and column is a
particular data type with a specific meaning. Like a row could be about a
single person and the columns could be the person’s first name, number,
address, email id etc.
Each record is identified by a unique _ID field
which is the key to the record. Each content provider exposes a unique URI that
identifies its data set uniquely. This URI is equivalent to a table name in a
database. The URI consists of various parts: eg: content://com.colllabera.labs.sai/tasks/123
is a unique URI. content:// is a standard prefix. com.collabera.labs.sai
is the authority, tasks is the table name, 123 is the unique
_ID.
For the native content providers, these unique
URIs are declared as constants in an interface. So, in our program we will be
using constants like People.CONTENT_URI which
internally translates to content://contacts/people
Let us now look at the code to view all the
existing contacts:
//Here is the button to click for viewing the contacts
Button view =
(Button)findViewById(R.id.viewButton);
…
//The method
/ class that gets invoked when the View button is clicked
view.setOnClickListener(new OnClickListener() {
public void onClick(View v){
displayContacts();
Log.i("NativeContentProvider", "Completed Displaying Contact list");
}
});
…
//Here is the displayContacts()
method
private void displayContacts() {
String[]
columns = new String[] {People.NAME,People.NUMBER};
Uri
mContacts = People.CONTENT_URI;
Cursor
mCur = managedQuery(mContacts, // Contact URI
columns, // Which columns to return
null, //
Which rows to return
null, //
Where clause parameters
null //
Order by clause
);
if (mCur.moveToFirst()) {
String
name = null;
String
phoneNo = null;
do {
name =
mCur.getString(mCur.getColumnIndex(People.NAME));
phoneNo =
mCur.getString(mCur.getColumnIndex(People.NUMBER));
Toast.makeText(NativeContentProvider.this, name + " " + phoneNo, Toast.LENGTH_SHORT).show();
}
while (mCur.moveToNext());
}
}
Here we are using the Activity.managedQuery(..)
to create and execute a query against the provided URI. The comments against the
parameters in the code is self-explanatory. This returns a cursor
object that can be iterated using the two methods moveToFirst()
and moveToNext().
For simplicity sake, I have just toasted the contact name and phone number retrieved.
An advanced tutorial can start a new activity that can display this in a ListView.
Now, we can move on to creating a new contact.
While the button related code will be very similar to the above, let us look at
the actual createContact() method.
private void
createContact(String name, String phone) {
ContentValues
contact = new ContentValues();
contact.put(People.NAME, name);
insertUri = getContentResolver().insert(People.CONTENT_URI, contact);
Log.d(getClass().getSimpleName(),insertUri.toString());
Uri
phoneUri = Uri.withAppendedPath(insertUri, People.Phones.CONTENT_DIRECTORY);
contact.clear();
contact.put(People.Phones.TYPE, People.TYPE_MOBILE);
contact.put(People.NUMBER, phone);
updateUri = getContentResolver().insert(phoneUri,
contact);
Toast.makeText(NativeContentProvider.this, "Created a
new contact: " + name + " " + phone, Toast.LENGTH_SHORT).show();
Log.d(getClass().getSimpleName(),updateUri.toString());
}
Here we need to understand 2 new classes: ContentResolver
and ContentValues.
A ContentResolver
provides applications access to the content data / model. We can get a handle
to a ContentResolver
by calling the getContentResolver() method within
the Activity.
This provides methods to insert, update and delete data. In order to insert
data, we need to provide it through a ContentValues
object. A ContentValues Object is nothing but a name, value
pair where the name of the column is to be mentioned. So, we pass the URI and
the ContentValues
to insert()
method which returns a unique URI with the new ID created. Once we get the ID
of the new person/contact inserted, we insert his/her mobile phone details into
the related Phones table by using the returned insertUri.
The insertUri
which is unique to the new record is stored as a class variable to use it in
the delete method later. The phoneUri is also stored for
updating the same in the updateContact() method later.
Note that People
is a class that has implemented various interfaces like android.priovider.BaseColumns,
android.provider.Contacts.Phones,
android.provider.Contact.PeopleColumns
etc. These constants come from the interfaces.
With the above understanding let us see the update
and delete methods:
private void
updateContact(String phone) {
if (updateUri == null) {
Toast.makeText(NativeContentProvider.this, "There is
nothing to update, Please create a contact and then click update", Toast.LENGTH_LONG).show();
} else {
ContentValues
newPhone = new ContentValues();
newPhone.put(People.Phones.TYPE, People.TYPE_MOBILE);
newPhone.put(People.NUMBER, phone);
getContentResolver().update(updateUri, newPhone, null,null);
Toast.makeText(NativeContentProvider.this, "Updated the
phone number to: " + phone, Toast.LENGTH_SHORT).show();
Log.i(getClass().getSimpleName(),
"Updated the phone number");
}
}
private void deleteContact() {
if (updateUri == null) {
Toast.makeText(NativeContentProvider.this, "Please
create a contact by clicking create button, then I can delete the same", Toast.LENGTH_LONG).show();
} else {
getContentResolver().delete(insertUri, null, null);
Toast.makeText(NativeContentProvider.this, "Deleted
contact at: " + insertUri.toString(), Toast.LENGTH_SHORT).show();
updateUri = null;
insertUri = null;
Log.i(getClass().getSimpleName(),"Deleted the contact inserted by this program");
}
}
These methods only manipulate the freshly created record,
for simplicity sake. They call upon the update() and delete() method on the ContentResolver.
The complete code for this example is available here.
Please note that you must add the following permissions
to the AndroidManifest.xml file to
be able to access the contacts.
<uses-permission android:name="android.permission.READ_CONTACTS"></uses-permission>
<uses-permission android:name="android.permission.WRITE_CONTACTS"></uses-permission>
Otherwise you get a SecurityException.
UPDATE: Please note that the article talks about the Contacts API before SDK 2.0. For the newer updated version, please check this article on New Content Provider
Hi Sai Geetha,
ReplyDeleteI've tried your tutorial program and everything seems to work perfectly.
But when I went to "Contacts" which is built in the Android Emulator, I didn't see "Sample Name" in the contact list. The only way I could see "Sample Name" is through Menu->Search Contacts.
Is there something missing?
Hi MSW,
ReplyDeleteThere are various options or groups to view the contacts in Android. By default, "My Contacts" group alone is shown. Hence the newly added contact which is not added to the "My Contacts" group does not show up.
If you go the the menu in contacts and click on "Display Group" and select "All Contacts" you will be able to see the just added "Sample Name" in the contact list.
Hi Sai Geetha,
ReplyDeleteI understand now.Thanks for the explanation.
Could you please give tutorial about sending and receiving chat message using GTalk service?
I always love your tutorial. :)
Your tutorials hav been a great help to me...
ReplyDeleteAs a beginner...i find these very useful......Thank you once again..
I am using android 2.0....which suggests to use android.provider.ContactsContract instead of android.provider.Contacts.People(which is deprecated in this version..)
so could u please help me to develop an app which can View,Create,Edit and Modify the contact list of android 2 ....
Thanks in advance..
This comment has been removed by the author.
ReplyDeleteHi Vishnu,
ReplyDeleteI will update it to the last API and post it. But it will take a while as I am help up with other things.
In the meantime, if you do crack it, kindly share the same.
Hi Sai,
ReplyDeleteHow to use HttpConnections in Android.
Can u plz give any tutorial for this?
Sai,
ReplyDeleteI read your 10 introductory tutorials and they are excellent! Well done!
hi,
ReplyDeleteyour tutorials were extremely helpful in understanding android as a beginner.
im just repeating the request that vishnu made, can you please update some of the posts with the new API because some parts of it such as contacts.people are now deprecated.
Thanks a lot,
Shoikat
update tutorial (content provider) SDK 2.1??
ReplyDeletethx
Hi Sai Geeta,
ReplyDeleteI have some scenarios to work out by using sqlite3.If you can give me your mail ID i can mail you the things .Please help me.
my mail ID is prasanth.shaker@gmail.com
ReplyDeleteHi Geetha,
ReplyDeleteCan you please explain how to create our own contentProvider with all the utilites and READ/WRITE Permission for other application to use it.
Hi,
ReplyDeletei am developing application for send email with image attachment.i have write code for image first store in sd card and then send email,so i have memory problem accrued,so i want to image will not store in sdcard and then send email with attachment.how is it possible,please give sample code for me..
Thanks..
Hi Sai,
ReplyDeleteCan you help me in setting permissions for the given example in android 2.2.
Hi,
ReplyDeleteI am tired of playing with content provider for calendar.I have to add a event in android calendar please help me with this I am using 2.2
Sam
This comment has been removed by the author.
ReplyDeleteHey sai,
ReplyDeletei am trying to use a custom content provider with a simple cursor adapter. I saw a while back you were going to write an article on how to get data from content provider and display it in a list view. was wondering if you can point me in the right direction.
is there have to make any change while we use this sample for api level 9...??
ReplyDeleteHey bhavana,
ReplyDeletethe contacts api is deprecated.. google introduced a new api quite some time ago.. you can look at http://blog.app-solut.com/2011/03/working-with-the-contactscontract-to-query-contacts-in-android for an introduction to the new api
Hi,
ReplyDeleteThank you for giving so many details and am not getting how to access from data base could you please help
Hi,
ReplyDeletei hav run the above code in my machine,
they are not run properly , its show only NAME,
not NUMBER
Nice tutorials, I really appreciate them.
ReplyDeleteI've been studying Android development for a while, haven't produced nothing commercial yet, hope to do it some day...
I think that you, being a professional, participated on some projects that weren't about building stand-alone apps... meaning that in some way, the app used the Cloud (sending a file by HTTP, getting some data from a server, etc.)
Hope you consider this domain enough "thought-provoking" to create a tutorial, I know that I and
Really great tutorial,
ReplyDeleteI am newer to the Android,& know my requirement is adding profile picture to the particular contact.
I am Trying following code it shows SQlite Error & some time it execute with out error but image not set to the contact.
plz help me,
i was passing personId which is getting from ContactsContract.Contacts._ID
Bitmap bitmap=BitmapFactory.decodeFile("/sdcard/Image.jpg");
ByteArrayOutputStream bytes = new ByteArrayOutputStream();
bitmap.compress(Bitmap.CompressFormat.JPEG, 90, bytes);
ContentValues values = new ContentValues();
values.put(ContactsContract.Data.RAW_CONTACT_ID, personId);
values.put(ContactsContract.CommonDataKinds.Photo.PHOTO,
bytes.toByteArray());
values.put(ContactsContract.Data.MIMETYPE,
ContactsContract.CommonDataKinds.Photo.CONTENT_ITEM_TYPE );
context.getContentResolver().update
(ContactsContract.Data.CONTENT_URI, values,
ContactsContract.Data.RAW_CONTACT_ID + " = " + personId, null);
fgfdgb
ReplyDeletehai sai geetha gaaru,
ReplyDeletecontent provider concept is very useful to me as beginer of android.
what is the differnce between emulator and simulator?
as apple company is using the name "simulator"
ReplyDeletegoogle used the name "Emulator" inorder to simulate our outputs's
Hi Sai,
ReplyDeleteI have checked into android database(Contacts2.db)
and I found that contact is not getting deleted from raw_contact and data table.
But if I delete contact form android contact application contact is getting deleted from raw_contact and data table.
Can you please explain why?
Hi,
ReplyDeleteI was wondering how to reverse this article, I want to share with the phonebook not the other way around. I have an application that downloads contacts from a webserivce. I would like to share this information with the phonebook but not insert or add it - I want the information to remain stored in the application database.
Your articles are always very useful I was wondering if you knew how to do this?
Thanks
can u plz,,, explain the contentObserver concept MAM,,,,
ReplyDeleteHello mam ,
ReplyDeleteYour tutorial is very good . I tried the first example of Content Provider which is running based on the People.Number and name i.e default property provided by the android itself.
I m able to get the name of the person saved in the contact successfully but Person.Number is returning null .. can u please provided me some solutions for this .....
Thanx n advance..
I this tutorial everything is working fine..but number is not displaying..will you please give the solution for that.
ReplyDeleteThank You.
Hi SaiGeetha,
ReplyDeleteThanks for your nice tutorial,im a begginer in android,i have one problem in my project,if you give me solution then it will be of great pleasure.my query is
Im doing for Turkish Sorting in ICS.
so i have added new java file TrCursor.java where the sorting rule is defined and used the RuleBasedCollator Concept in android Frameworks and this class i am making use in providers (Contactprovider2.java).but im getting error like
Error Parsing API.
i tried a lot but same error.
is this the limitation of android ICS?
because in ICS PeopleActivity has replaced contacts module so some new API has added in ICS.
So please solve my issue.waiting for your reply.
Thanks in advance
Regards,
Chandu
GREAT EXPLANATORY SKILLS !!!
ReplyDeleteThanks a Ton
Thanks...
ReplyDeleteHi..
ReplyDeletehow to retrieve the contact names and corresponding phone numbers and display it in the list.please give the hint how to solve this..
Thanks and Regards
Girish
excellent explanation on contents
ReplyDeleteHi Geetha, you are doing Very Great Job, Thanks , for much information,Keep sharing such a wonderful information..!
ReplyDeleteHow we can add photo in contact?
ReplyDeleteGood tutorial;
ReplyDeletereally good tutorial..... :)
ReplyDeletestore and retrieve data thus making it accessible to all. Android platform provides default implementations of content providers for data types like audio, video, images, contact information.thanks for it.
ReplyDeleteHiiiiiii Geetha This is Good. I want Google Maps and Location Based Services tutorial
ReplyDeletethanks, really good tutorial
ReplyDeletehiii geetha mam,
ReplyDeletei have develope one application in android.in that my mobile call, message,e-mails all are divert on my any friend number when i forgett my mobile in my home or anywhere, so for that i want to help me in designing ,or some layouts from you.this application develope for my last year project MCA.
also you can suggest me any subject.
great job thanks you..........
ReplyDeleteAm new to android , so that am not able to move forward with sqlite DB.
ReplyDeletefirst of all, how to configure sqlite db in our eclipse.
what are things i should so b4 starting sqlite in my android application.
how to code for
ReplyDeleteListing Calendar Events using content resolver in android.
Please help me i am new to android...
hi,
ReplyDeletethis is very well for us....
but , we have one problem regarding this...
can you show pics about its working...how is it working...
thanks...
Dear saigeetha, In the above example i couldn't see a class (content Provider).
ReplyDeletePls help out, Is it possible to share stored data with the help of activity?
Thanks