Android的ContentProvider(二)

接下来是getType方法,此方法参数是URI,根据Uri返回不同的MimeType:

@Override
public String getType(Uri uri) {

	switch (uriMatcher.match(uri)) {
	case COLL_TYPE_URI_MATCHER: {
		return Book.ContentType.COLL_TYPE;
	}
	case ITEM_TYPE_URI_MATCHER: {
		return Book.ContentType.ITEM_TYPE;
	}
	default: {
		throw new SQLException("Unknown URI:" + uri);
	}
	}

}

接下来是insert方法,参数是Uri及ContentValues,较为简单:

@Override
public Uri insert(Uri uri, ContentValues values) {

	if (uriMatcher.match(uri) != COLL_TYPE_URI_MATCHER) {
		throw new SQLException("Unknown URI:" + uri);
	}

	Long now = System.currentTimeMillis();

	if (!values.containsKey(Book.Columns.NAME)) {
		throw new SQLException(Book.Columns.NAME.concat(" 的值不得为空!"));
	}

	if (!values.containsKey(Book.Columns.AUTHOR)) {
		values.put(Book.Columns.AUTHOR, "Unknown Author");
	}

	if (!values.containsKey(Book.Columns.CREATE_TIME)) {
		values.put(Book.Columns.CREATE_TIME, now);
	}

	SQLiteDatabase db = dbHelper.getWritableDatabase();
	Long rowId = db.insert(Book.TABLE_NAME, Book.Columns.NAME, values);

	if (rowId > 0) {
		Uri insertedBookUri = ContentUris.withAppendedId(Book.CONTENT_URI,
				rowId);
		getContext().getContentResolver().notifyChange(insertedBookUri,
				null);
		return insertedBookUri;
	}

	throw new SQLException("添加图书失败,URI:" + uri);
}

前文说过,最好都加上notifyChange。

delete和update也没什么特别的:

@Override
public int delete(Uri uri, String selection, String[] selectionArgs) {

	int count = 0;

	SQLiteDatabase db = dbHelper.getWritableDatabase();
	switch (uriMatcher.match(uri)) {
	case COLL_TYPE_URI_MATCHER: {
		count = db.delete(Book.TABLE_NAME, selection, selectionArgs);
		break;
	}
	case ITEM_TYPE_URI_MATCHER: {

		selection = Book.Columns._ID
				.concat("=")
				.concat(uri.getPathSegments().get(1))
				.concat(TextUtils.isEmpty(selection) ? "" : " AND ("
						.concat(selection).concat(")"));
		count = db.delete(Book.TABLE_NAME, selection, selectionArgs);

		break;
	}
	default: {
		throw new SQLException("Unknown URI:" + uri);
	}
	}

	getContext().getContentResolver().notifyChange(uri, null);

	return count;
}

@Override
public int update(Uri uri, ContentValues values, String selection,
		String[] selectionArgs) {

	int count = 0;
	SQLiteDatabase db = dbHelper.getWritableDatabase();

	switch (uriMatcher.match(uri)) {
	case COLL_TYPE_URI_MATCHER: {
		count = db
				.update(Book.TABLE_NAME, values, selection, selectionArgs);
		break;
	}
	case ITEM_TYPE_URI_MATCHER: {

		selection = Book.Columns._ID
				.concat("=")
				.concat(uri.getPathSegments().get(1))
				.concat(TextUtils.isEmpty(selection) ? "" : " AND ("
						.concat(selection).concat(")"));

		count = db
				.update(Book.TABLE_NAME, values, selection, selectionArgs);

		break;
	}
	default: {
		throw new SQLException("Unknown URI:" + uri);
	}
	}

	getContext().getContentResolver().notifyChange(uri, null);

	return count;
}

至此已实现BookProvider,全部代码如下所示:

/**
 * 
 * Dec 22, 2014 3:43:47 PM
 * @Geloin
 *
 */
package com.geloin.baseopera.provider;

import java.util.HashMap;
import java.util.Map;

import android.content.ContentProvider;
import android.content.ContentUris;
import android.content.ContentValues;
import android.content.Context;
import android.content.UriMatcher;
import android.database.Cursor;
import android.database.SQLException;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.database.sqlite.SQLiteQueryBuilder;
import android.net.Uri;
import android.text.TextUtils;

/**
 * 
 * Dec 22, 2014 3:43:47 PM
 * 
 * @Geloin
 * 
 */
public class BookProvider extends ContentProvider {

	public class DBHelper extends SQLiteOpenHelper {

		public DBHelper(Context context) {
			super(context, Book.DB_FILE_NAME, null, Book.DB_VERSION);
		}

		@Override
		public void onCreate(SQLiteDatabase db) {

			StringBuilder builder = new StringBuilder();
			builder.append(" CREATE TABLE ");
			builder.append(Book.TABLE_NAME);
			builder.append(" ( ");
			builder.append(Book.Columns._ID);
			builder.append(" INTEGER PRIMARY KEY, ");
			builder.append(Book.Columns.NAME);
			builder.append(" TEXT, ");
			builder.append(Book.Columns.AUTHOR);
			builder.append(" TEXT, ");
			builder.append(Book.Columns.CREATE_TIME);
			builder.append(" INTEGER ");
			builder.append(" ); ");

			db.execSQL(builder.toString());
		}

		@Override
		public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {

			db.execSQL("DROP TABLE IF EXISTS ".concat(Book.TABLE_NAME));

			onCreate(db);
		}

	}

	private DBHelper dbHelper;

	private static UriMatcher uriMatcher;

	private static final int COLL_TYPE_URI_MATCHER = 1;
	private static final int ITEM_TYPE_URI_MATCHER = 2;

	private static Map<String, String> columnMap;

	static {
		uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
		uriMatcher.addURI(Book.AUTHORITY, "books", COLL_TYPE_URI_MATCHER);
		uriMatcher.addURI(Book.AUTHORITY, "books/#", ITEM_TYPE_URI_MATCHER);

		columnMap = new HashMap<String, String>();
		columnMap.put(Book.Columns._ID, Book.Columns._ID);
		columnMap.put(Book.Columns.NAME, Book.Columns.NAME);
		columnMap.put(Book.Columns.AUTHOR, Book.Columns.AUTHOR);
		columnMap.put(Book.Columns.CREATE_TIME, Book.Columns.CREATE_TIME);
	}

	@Override
	public boolean onCreate() {

		dbHelper = new DBHelper(getContext());

		return true;
	}

	@Override
	public Cursor query(Uri uri, String[] projection, String selection,
			String[] selectionArgs, String sortOrder) {

		SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
		switch (uriMatcher.match(uri)) {
		case COLL_TYPE_URI_MATCHER: {
			qb.setTables(Book.TABLE_NAME);
			qb.setProjectionMap(columnMap);
			break;
		}
		case ITEM_TYPE_URI_MATCHER: {

			qb.setTables(Book.TABLE_NAME);
			qb.setProjectionMap(columnMap);
			qb.appendWhere(Book.Columns._ID.concat("=").concat(
					uri.getPathSegments().get(1)));

			break;
		}
		default: {
			throw new SQLException("Unknown URI:" + uri);
		}
		}

		String orderBy = null;
		if (TextUtils.isEmpty(sortOrder)) {
			orderBy = Book.DEFAULT_ORDER;
		} else {
			orderBy = sortOrder;
		}

		SQLiteDatabase db = dbHelper.getReadableDatabase();
		Cursor c = db.query(Book.TABLE_NAME, projection, selection,
				selectionArgs, null, null, orderBy);
		// 通知数据库变化
		c.setNotificationUri(getContext().getContentResolver(), uri);

		return c;
	}

	@Override
	public String getType(Uri uri) {

		switch (uriMatcher.match(uri)) {
		case COLL_TYPE_URI_MATCHER: {
			return Book.ContentType.COLL_TYPE;
		}
		case ITEM_TYPE_URI_MATCHER: {
			return Book.ContentType.ITEM_TYPE;
		}
		default: {
			throw new SQLException("Unknown URI:" + uri);
		}
		}

	}

	@Override
	public Uri insert(Uri uri, ContentValues values) {

		if (uriMatcher.match(uri) != COLL_TYPE_URI_MATCHER) {
			throw new SQLException("Unknown URI:" + uri);
		}

		Long now = System.currentTimeMillis();

		if (!values.containsKey(Book.Columns.NAME)) {
			throw new SQLException(Book.Columns.NAME.concat(" 的值不得为空!"));
		}

		if (!values.containsKey(Book.Columns.AUTHOR)) {
			values.put(Book.Columns.AUTHOR, "Unknown Author");
		}

		if (!values.containsKey(Book.Columns.CREATE_TIME)) {
			values.put(Book.Columns.CREATE_TIME, now);
		}

		SQLiteDatabase db = dbHelper.getWritableDatabase();
		Long rowId = db.insert(Book.TABLE_NAME, Book.Columns.NAME, values);

		if (rowId > 0) {
			Uri insertedBookUri = ContentUris.withAppendedId(Book.CONTENT_URI,
					rowId);
			getContext().getContentResolver().notifyChange(insertedBookUri,
					null);
			return insertedBookUri;
		}

		throw new SQLException("添加图书失败,URI:" + uri);
	}

	@Override
	public int delete(Uri uri, String selection, String[] selectionArgs) {

		int count = 0;

		SQLiteDatabase db = dbHelper.getWritableDatabase();
		switch (uriMatcher.match(uri)) {
		case COLL_TYPE_URI_MATCHER: {
			count = db.delete(Book.TABLE_NAME, selection, selectionArgs);
			break;
		}
		case ITEM_TYPE_URI_MATCHER: {

			selection = Book.Columns._ID
					.concat("=")
					.concat(uri.getPathSegments().get(1))
					.concat(TextUtils.isEmpty(selection) ? "" : " AND ("
							.concat(selection).concat(")"));
			count = db.delete(Book.TABLE_NAME, selection, selectionArgs);

			break;
		}
		default: {
			throw new SQLException("Unknown URI:" + uri);
		}
		}

		getContext().getContentResolver().notifyChange(uri, null);

		return count;
	}

	@Override
	public int update(Uri uri, ContentValues values, String selection,
			String[] selectionArgs) {

		int count = 0;
		SQLiteDatabase db = dbHelper.getWritableDatabase();

		switch (uriMatcher.match(uri)) {
		case COLL_TYPE_URI_MATCHER: {
			count = db
					.update(Book.TABLE_NAME, values, selection, selectionArgs);
			break;
		}
		case ITEM_TYPE_URI_MATCHER: {

			selection = Book.Columns._ID
					.concat("=")
					.concat(uri.getPathSegments().get(1))
					.concat(TextUtils.isEmpty(selection) ? "" : " AND ("
							.concat(selection).concat(")"));

			count = db
					.update(Book.TABLE_NAME, values, selection, selectionArgs);

			break;
		}
		default: {
			throw new SQLException("Unknown URI:" + uri);
		}
		}

		getContext().getContentResolver().notifyChange(uri, null);

		return count;
	}

}

再把Book代码贴出来:

/**
 * 
 * Dec 22, 2014 3:42:39 PM
 * @Geloin
 *
 */
package com.geloin.baseopera.provider;

import android.net.Uri;
import android.provider.BaseColumns;

/**
 * 
 * Dec 22, 2014 3:42:39 PM
 * 
 * @Geloin
 * 
 */
public class Book {

	public static final String TABLE_NAME = "books";

	public static final String DB_FILE_NAME = "books.db";

	public static final Integer DB_VERSION = 1;

	public static final String AUTHORITY = "com.geloin.baseopera.provider.BookProvider";

	public static final String DEFAULT_ORDER = "createTime DESC";

	public static final Uri CONTENT_URI = Uri.parse("content://".concat(
			AUTHORITY).concat("/books"));

	/**
	 * 列名
	 * 
	 * Dec 22, 2014 3:52:25 PM
	 * 
	 * @Geloin
	 * 
	 */
	public class Columns implements BaseColumns {

		public static final String NAME = "name";

		public static final String AUTHOR = "author";

		public static final String CREATE_TIME = "createTime";
	}

	/**
	 * ContentType
	 * 
	 * Dec 22, 2014 3:53:40 PM
	 * 
	 * @Geloin
	 * 
	 */
	public class ContentType {

		/**
		 * 集合
		 */
		public static final String COLL_TYPE = "vnd.android.cursor.dir/vnd.androidbook.book";

		/**
		 * 单项
		 */
		public static final String ITEM_TYPE = "vnd.android.cursor.item/vnd.androidbook.book";
	}
}

定义ContentProvider后,必须在AndroidManifest.xml中注册:

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.geloin.baseopera"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="17"
        android:targetSdkVersion="21" />

    <permission
        android:name="com.geloin.permission.SayHello"
        android:protectionLevel="normal" >
    </permission>

    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
        <activity
            android:name=".activity.BooksActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>

        <provider
            android:name=".provider.BookProvider"
            android:authorities="com.geloin.baseopera.provider.BookProvider"
            android:exported="false" >
        </provider>
    </application>

</manifest>

接下来会讲述如何使用自定义的ContentProvider。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值