Download as pptx, pdf, or txt
Download as pptx, pdf, or txt
You are on page 1of 38

Mobile Computing

Lecture #09
Content Providers
Content Providers
 A content provider manages access to a central
repository of data
 A provider is part of an Android application,
which often provides its own UI for working with
the data
 Main intention of a content provider is to be used
by other applications
 Content Providers provide a consistent API to
access data repositories that are actually stored in
different resources
Content Providers
 A content provider presents the data to an application as if it was available in a
table (or few tables) of a relational database
 External application uses a method similar to one that is used to query an SQLite
database to fetch data from a content provider
Content Providers
 Sharing access to your application data
with other applications
 Sending data to a widget
 Returning custom search suggestions
for your application through the search
framework using
SearchRecentSuggestionsProvider
 Synchronizing application data with
your server using an implementation of
AbstractThreadedSyncAdapter
 Loading data in your UI using a
CursorLoader
Accessing a Provider
 When an application wants to access data
in a content provider, it uses the
ContentResolver object in its context to
communicate with the provider as a client
 The ContentResolver object
communicates with the provider object
 The ContentResolver methods provide the
basic "CRUD" (create, retrieve, update,
and delete) operations of persistent
storage
 One of the built-in providers in the
Android platform is the user dictionary,
which stores the spellings of non-
standard words that the user wants to
keep
Retrieving data from the provider
To read data from a content provider
1. An application must request the read access permission for the provider

2. It must define the code that sends a query to the provider

 Read permisions cannot be asked for at run-time; instead. It must asked using
manifest, using the <uses-permission> element and the exact permission name
defined by the provider

 For example, An application must define the permission


android.permission.READ_USER_DICTIONARY in its manifest file, so an
application that wants to read from the provider must request this permission

 <uses-permission
android:name="android.permission.READ_USER_DICTIONARY">
Read Query:
mCursor = getContentResolver().query(
UserDictionary.Words.CONTENT_URI, // The content URI of the words table
mProjection, // The columns to return for each row
mSelectionClause // Selection criteria
mSelectionArgs, // Selection criteria
mSortOrder // The sort order for the returned rows
);
Inserting, updating, and deleting data
 To insert data into a provider, you call the ContentResolver.insert() method. This
method inserts a new row into the provider and returns a content URI for that
row.
 To update a row, you use a ContentValues object with the updated values just as
you do with an insertion, and selection criteria just as you do with a query. The
client method you use is ContentResolver.update()
 Deleting rows is similar to retrieving row data: you specify selection criteria for
the rows you want to delete and the client method returns the number of deleted
rows. You use ContentResolver.delete()
ContentProvider … Implementation
 Implement the storage system for data (Files / Database etc)
 Decide the format of ContentURI for accessing the data (managed by content
provider)
 Implement the YourContentProvider class by subclassing ContentProvider
 Following methods must be implemented for a ContentProvider:
1. onCreate()

2. insert()

3. query()

4. update()

5. delete()

6. getType()
ContentProvider … ContentURI
ContentURI determines the data in ContentProvider.
ContentURI has different parts as:
1. Prefix
This is always set to content://
2. Authority
Fully qualified of entire provider. For example AUTHORITY = “com.provider.users”.
public static final Uri AUTHORITY_URI = Uri.parse(“content://”+AUTHORITY);
3. Type
Type specifies the type of data to be retrieved from ContentProvider. For example, if you want to
retrieve all the users from users table then the type can specify this fact:
public static final Uri CONTENT_URI = Uri.withAppendedPath(AUTHORITY_URI, “users”);
4. Id (optional)
This specifies the specific record requested. For example, if you are looking for user with id = 5 in
the above content provider then URI would look like this content:// com.provider.users /users/5.
ContentProvider … Creation
 First of all you need to create a Content Provider class that extends the
ContentProvider base class.
 Second, you need to define your content provider URI address which will be used
to access the content.
 Next you will need to create your own database to keep the content. Usually,
Android uses SQLite database and framework needs to override onCreate()
method which will use SQLite Open Helper method to create or open the
provider's database. When your application is launched, the onCreate() handler
of each of its Content Providers is called on the main application thread.
 Next you will have to implement Content Provider queries to perform different
database specific operations.
 Finally register your Content Provider in your activity file using <provider> tag.
ContentProvider … Methods
Here is the list of methods which you need to override in Content Provider class to
have your Content Provider working −
 onCreate() This method is called when the provider is started.
 query() This method receives a request from a client. The result is returned as a
Cursor object.
 insert()This method inserts a new record into the content provider.
 delete() This method deletes an existing record from the content provider.
 update() This method updates an existing record from the content provider.
 getType() This method returns the MIME type of the data at the given URI.
ContentProvider … Content Provider Example
 A project that uses content provider to populate, update, delete and create user
objects
ContentProvider Example … Manifest
<?xml version="1.0" encoding="utf-8"?>
<manifest
xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.contentproviderproject">

<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category
android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
ContentProvider Example … Manifest …
<activity android:name=".ViewAllUsers"></activity>
<activity android:name=".InsertUserActivity"></activity>
<activity android:name=".DeleteUserActivity"></activity>
<activity android:name=".UpdateUserActivity"></activity>
<provider
android:authorities="com.example.contentproviderproject.UserProvider"
android:name=".UserProvider"
android:exported="true"
android:readPermission="com.example.contentproviderproject.permission.READ"

android:writePermission="com.example.contentproviderproject.permission.WRITE“ />
</application>
<permission
android:name="com.example.contentproviderproject.permission.READ"
android:protectionLevel="signature“ />
<permission
android:name="com.example.contentproviderproject.permission.WRITE"
android:protectionLevel="signature“/>
</manifest>
ContentProvider Example … Project Structure
1. Activities
2. Layouts
3. ContentProvider
4. Underlying DB
5. Constants
ContentProvider Example … Activities
1. MainActivity.java
2. DeleteUserActivity.java
3. InsertUserActivity.java
4. UpdateUserActivity.java
5. ViewAllUsers.java
ContentProvider Example … MainActivity.java
Shows buttons with possible actions i.e.
1. List All Users
2. Add New User
3. Update Existing User
4. Delete Existing User
ContentProvider Example … DeleteUser.java

public void deleteUserData(View view){


String id = userIdInput.getText().toString();
getContentResolver().delete(DBConstants.CONTENT_URI,
"_id=?", new String[]{""+id});
Toast.makeText(this, "One record deleted", Toast.LENGTH_LONG).show();
}
ContentProvider Example … InsertUserActivity.java
public void addUserData(View view){
ContentValues values = new ContentValues();
values.put(DBConstants.USER_EMAIL, emailInput.getText().toString());
values.put(DBConstants.USER_NAME, nameInput.getText().toString());
values.put(DBConstants.USER_PHONE, phoneInput.getText().toString());
getContentResolver().insert(DBConstants.CONTENT_URI, values);
Toast.makeText(this, "One record inserted",
Toast.LENGTH_LONG).show();
}
ContentProvider Example … UpdateUserActivity.java

public void updateUserData(View view){


String id = idInput.getText().toString();
ContentValues values = new ContentValues();
values.put(DBConstants.USER_EMAIL, emailInput.getText().toString());
values.put(DBConstants.USER_NAME, nameInput.getText().toString());
values.put(DBConstants.USER_PHONE, phoneInput.getText().toString());
getContentResolver().update(DBConstants.CONTENT_URI, values, "_id = ?", new String[]{id});
Toast.makeText(this, "One record updated", Toast.LENGTH_LONG).show();
}
ContentProvider Example … ViewAllUsers.java
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.all_users_list);
helper = new DBHelper(this);
data = findViewById(R.id.all_users_list1);
Cursor cursor = getAllUsers();
UsersAdapter adapter = new UsersAdapter(this, cursor);
data.setAdapter(adapter);
}
public Cursor getAllUsers(){
Cursor cursor = getContentResolver().query(DBConstants.CONTENT_URI,
DBConstants.USER_ALL_COLUMNS, null, null, null);
return cursor;
}
ContentProvider Example … Activities Layouts
1. MainActivity
2. Delete User Activity
3. Insert User Activity
4. Update User Activity
5. View All Users
Activity Layouts… activity_main.xml
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
>
<Button
android:id="@+id/insert_user"
android:text="@string/add_user" />
<Button
android:id="@+id/list_user"
android:text="@string/add_user" />
<Button
android:id="@+id/update_user"
android:text="@string/add_user" />
<Button
android:id="@+id/list_user"
android:text="@string/add_user" /> Note: Set the remaining attributes yourself
</ RelativeLayout>
Activity Layouts… all_users_list.xml
<RelativeLayout>
<TextView
android:id="@+id/all_users_data_title"
android:layout_centerHorizontal="true"
android:textSize="20dp"
android:text="@string/all_user_data" />

<ListView
android:id="@+id/all_users_list1"
android:layout_below="@id/all_users_data_title"
android:textSize="20dp"/>

<Button
android:id="@+id/go_home"
android:layout_below="@id/all_users_list1"
android:text="@string/go_to_home"
android:textSize="20dp"
android:onClick="goToHome"
android:layout_centerHorizontal="true"
/>
</RelativeLayout>
Activity Layouts… delete_user.xml
<RelativeLayout> <Button
<TextView android:id="@+id/delete_user_button"
android:id="@+id/delete_user_text"/> android:textSize="20dp"
<TableLayout android:text="@string/delete_user"
android:id="@+id/delete_input_form" android:onClick="deleteUserData"
android:weightSum="3" android:layout_centerHorizontal="true"
/>
<Button
android:layout_below="@id/delete_user_text">
android:id="@+id/go_home"
<TableRow>
android:layout_below="@id/delete_user_button"
<TextView android:text="@string/go_to_home"
android:id="@+id/delete_user_id" android:textSize="20dp"
android:layout_weight="1" android:onClick="goToHome"
android:text="@string/user_id" /> android:layout_centerHorizontal="true"
<EditText />
android:id="@+id/delete_user_id_input" </RelativeLayout>
android:textSize="20dp"
android:layout_weight="2"/>
</TableRow>
</TableLayout>
Activity Layouts… Remaining Layouts

Remaining layout definitions in Content Provider


Example Files
ContentProvider Example … ContentProvider

1. UserProvider.java
ContentProvider Example … ContentProvider
public class UserProvider extends ContentProvider {
public static UriMatcher matcher;
public static final int allUsers = 1;
public static final int userId = 2;
private static HashMap<String, String> USERS_PROJECTION_MAP;
SQLiteDatabase db;
Context context;

static {
matcher = new UriMatcher(UriMatcher.NO_MATCH);
matcher.addURI(DBConstants.PROVIDER_NAME, "users", allUsers);
matcher.addURI(DBConstants.PROVIDER_NAME, "users/#", userId);
}
ContentProvider Example … ContentProvider

public boolean onCreate(){


context = getContext();
DBHelper helper = new DBHelper(context);
db = helper.getWritableDatabase();
return (db==null)?false:true;
}
ContentProvider Example … ContentProvider

public Uri insert(Uri uri, ContentValues values) {


long rowID = db.insert(DBConstants.USER_TABLE_NAME, "", values);

/* If record is added successfully */


if (rowID > 0) {
Uri _uri = ContentUris.withAppendedId(DBConstants.CONTENT_URI, rowID);
context.getContentResolver().notifyChange(_uri, null);
return _uri;
}

throw new SQLException("Failed to add a record into " + uri);


}
ContentProvider Example … ContentProvider
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) {
SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
qb.setTables(DBConstants.USER_TABLE_NAME);

switch (matcher.match(uri)) {
case allUsers:
qb.setProjectionMap(USERS_PROJECTION_MAP);
break;

case userId:
qb.appendWhere( "_id =" + uri.getPathSegments().get(1));
break;
default:
}

Cursor c = qb.query(db, projection, selection, selectionArgs, null, null, sortOrder);


c.setNotificationUri(getContext().getContentResolver(), uri);
return c;
}
ContentProvider Example … ContentProvider
public int delete(Uri uri, String where, String[] args) {
int count = 0;
switch (matcher.match(uri)){
case allUsers:
count = db.delete(DBConstants.USER_TABLE_NAME, where, args);
break;
case userId:
String id = uri.getPathSegments().get(1);
count = db.delete(DBConstants.USER_TABLE_NAME,
DBConstants.USER_ID+"=", new String[]{id});
break;
}
return count;
}
ContentProvider Example … ContentProvider
public int update(Uri uri, ContentValues values,String where, String[] args) {
int count = 0;
switch (matcher.match(uri)){
case allUsers:
count = db.update(DBConstants.USER_TABLE_NAME, values, where, args);
break;
case userId:
String id = uri.getPathSegments().get(1);
count = db.update(DBConstants.USER_TABLE_NAME, values,
DBConstants.USER_ID+"=", new String[]{id});
break;
}
return count;
}
ContentProvider Example … Underlying DB Handler

1. DBHelper.java
ContentProvider Example … Underlying DB Handler
public class DBHelper extends SQLiteOpenHelper {
public DBHelper(Context context){
super(context, DBConstants.DBNAME,null, 2);
}
public void onCreate(SQLiteDatabase db){
db.execSQL(DBConstants.USER_TABLE_CREATE);
Log.i("DBHelper", "onCreate()");
}
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion){
db.execSQL("DROP TABLE IF EXISTS "+DBConstants.USER_TABLE_NAME);
onCreate(db);
Log.i("DBHelper", "onUpgrade()");
}
}
ContentProvider Example … Constants

1. DBConstants.java
ContentProvider Example … Constants
public class DBConstants {
public static final String DBNAME="expense.db";
public static final String USER_TABLE_NAME = "users";
public static final String USER_NAME = "userName";
public static final String USER_EMAIL = "userEmail";
public static final String USER_PHONE = "userPhone";
public static final String USER_ID = "_id";
public static final String USER_TABLE_CREATE = "CREATE TABLE "+USER_TABLE_NAME+
"("+USER_ID+ " INTEGER PRIMARY KEY AUTOINCREMENT, " +
USER_NAME +" TEXT, "+ USER_EMAIL +" TEXT, " + USER_PHONE +" TEXT)";
public static final String []USER_ALL_COLUMNS={USER_ID, USER_NAME, USER_EMAIL, USER_PHONE};
public static final String PROVIDER_NAME="com.example.contentproviderproject.UserProvider";
public static final String URL = "content://"+PROVIDER_NAME+"/users";
public static final Uri CONTENT_URI = Uri.parse(URL);
}

You might also like