现在的位置: 首页 > 综合 > 正文

Android ContentProvider

2013年09月20日 ⁄ 综合 ⁄ 共 7747字 ⁄ 字号 评论关闭

创建StudentContentProvider项目

MyProvider类;

package com.mycontent;

import android.content.ContentProvider;
import android.content.ContentUris;
import android.content.ContentValues;
import android.content.UriMatcher;
import android.database.Cursor;
import android.database.SQLException;
import android.database.sqlite.SQLiteDatabase;
import android.net.Uri;
import android.text.TextUtils;
import android.util.Log;

public class MyProvider extends ContentProvider {
	//共享数据源
	private StudentData sd;
	//匹配器
	private static final UriMatcher sMatcher;
	
	/**
	 * 当类被加载时需要创建的类对象
	 */
	static {
		//其中authorities类似于域名或IP,用来标识操作哪个ContentProvider
		////创建一个URI匹配器,参数为不匹配时的返回值
		// 传入匹配码如果大于0表示匹配根路径或传入-1,即常量UriMatcher.NO_MATCH表示不匹配根路径
		// addURI()方法是用来增加其他URI匹配路径的:
		// 第一个参数代表传入标识ContentProvider的AUTHORITY字符串
		// 第二个参数是要匹配的路径,#代表任意数字,另外还可以用*来匹配任意文本
		// 第三个参数必须传入一个大于零的匹配码,用于match()方法对相匹配的URI返回相对应的匹配码
		sMatcher = new UriMatcher(UriMatcher.NO_MATCH);
		sMatcher.addURI(StudentData.AUTHORITY, "item", StudentData.ITEM);
		sMatcher.addURI(StudentData.AUTHORITY, "item/#", StudentData.ITEM_ID);
	}

	/*
	 * 每当ContentProvider启动时都会回调onCreate()方法。此方法主要执行一些ContentProvider初始化
	 * 的工作,返回true表示初始化成功,返回false则初始化失败。
	 */
	@Override
	public boolean onCreate() {
		sd = new StudentData(this.getContext());
		SQLiteDatabase sdb = sd.getWritableDatabase();
		ContentValues values = new ContentValues();  
		for(int i=1;i<=30;i++){
			 values.put("name", "hello"+i);  
			sdb.insert(StudentData.TABLE_NAME, StudentData.SID, values);
		}
		sdb.close();
		sdb=null;
		return true;
	}
	 /* 
     * 如果操作集合,则必须以vnd.android.cursor.dir开头 
     * 如果操作非集合,则必须以vnd.android.cursor.item开头 
     * */  
	// getType()是用来返回数据的MIME类型的方法。使用sMatcher对URI进行匹配,并返回相应的MIME类型字符串
	@Override
	public String getType(Uri uri) {
		switch (sMatcher.match(uri)) {
		case StudentData.ITEM:
			return StudentData.CONTENT_TYPE;
		case StudentData.ITEM_ID:
			return StudentData.CONTENT_ITEM_TYPE;
		default:
			throw new IllegalArgumentException("Unknown URI " + uri);
		}
	}

	/*
	 * 插入数据,返回新插入数据的URI,只接受数据集的URI,即指向表的URI
	 */
	@Override
	public Uri insert(Uri uri, ContentValues values) {
		SQLiteDatabase sdb = sd.getWritableDatabase();
		long rowId;
		if (sMatcher.match(uri) != StudentData.ITEM) {
			sdb.close();
			sdb=null;
			throw new IllegalArgumentException("Unknow URI " + uri);
		}
		rowId = sdb.insert(StudentData.TABLE_NAME, StudentData.SID, values);
		if (rowId > 0) {
			Uri noteUri = ContentUris.withAppendedId(StudentData.CONTENT_URI,
					rowId);
			this.getContext().getContentResolver().notifyChange(noteUri, null);
			return noteUri;
		}
		sdb.close();
		sdb=null;
		throw new SQLException("Failed to insert row into " + uri);
	}

	/*
	 * 用于数据的删除,返回的是所影响数据的数目,首先利用数据库辅助对象获取一个SQLiteDatabase对象
	 * 然后根据传入Uri用sMatcher进行匹配,对单个数据或数据集进行删除或修改。notifyChange()方法
	 * 用来通知注册在次URI上的观察者(observer)数据发生了改变。
	 */
	@Override
	public int delete(Uri uri, String selection, String[] selectionArgs) {
		SQLiteDatabase sdb = sd.getWritableDatabase();
		int count;
		switch (sMatcher.match(uri)) {
		case StudentData.ITEM:
			count = sdb.delete(StudentData.TABLE_NAME, selection, selectionArgs);
			break;
		case StudentData.ITEM_ID:
			//String id = uri.getPathSegments().get(1);
			long id = ContentUris.parseId(uri);  
			count = sdb.delete(StudentData.TABLE_NAME, StudentData.SID
					+ "="
					+ id
					+ (!TextUtils.isEmpty(selection) ? " AND (" + selection
							+ ")" : ""), selectionArgs);
			break;
		default:
			throw new IllegalArgumentException("Unknown URI " + uri);
		}
		sdb.close();
		sdb=null;
		this.getContext().getContentResolver().notifyChange(uri, null);
		return count;
	}

	/*
	 * 查询数据,将数据装入一个Cursor对象并返回
	 */
	@Override
	public Cursor query(Uri uri, String[] projection, String selection,
			String[] selectionArgs, String sortOrder) {
		SQLiteDatabase sdb = sd.getReadableDatabase();
		Cursor c;
		switch (sMatcher.match(uri)) {
		case StudentData.ITEM:
			c = sdb.query(StudentData.TABLE_NAME, projection, selection,
					selectionArgs, null, null, sortOrder);
			break;
		case StudentData.ITEM_ID:
		//	String id = uri.getPathSegments().get(1);
			long id = ContentUris.parseId(uri);  
			c = sdb.query(StudentData.TABLE_NAME, projection, StudentData.SID
					+ "="
					+ id
					+ (!TextUtils.isEmpty(selection) ? " AND (" + selection
							+ ")" : ""), selectionArgs, null, null, sortOrder);
			break;
		default:
			Log.i("sMatcher.match(uri)", String.valueOf(sMatcher.match(uri)));
			throw new IllegalArgumentException("Query with unknown URI: " + uri);
		}
		sdb.close();
		sdb=null;
		c.setNotificationUri(getContext().getContentResolver(), uri);
		return c;
	}

	// 更新,与删除类方法类似
	@Override
	public int update(Uri uri, ContentValues values, String selection,
			String[] selectionArgs) {
		SQLiteDatabase sdb = sd.getWritableDatabase();
		int count;
		switch (sMatcher.match(uri)) {
		case StudentData.ITEM:
			count = sdb.update(StudentData.TABLE_NAME, values, selection,
					selectionArgs);
			break;
		case StudentData.ITEM_ID:
			String id = uri.getPathSegments().get(1);
			count = sdb.update(StudentData.TABLE_NAME, values, StudentData.SID
					+ "="
					+ id
					+ (!TextUtils.isEmpty(selection) ? " AND (" + selection
							+ ")" : ""), selectionArgs);
			break;
		default:
			throw new IllegalArgumentException("Unknown URI " + uri);
		}
		sdb.close();
		sdb=null;
		this.getContext().getContentResolver().notifyChange(uri, null);
		return count;
	}
	
}

数据共享对象StudentData

package com.mycontent;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.net.Uri;

public class StudentData extends SQLiteOpenHelper {
	/*
	 * 分别定义了数据库和表的名称、表中各个字段的名称、数据库的版本号
	 */
	private final static String DB_NAME = "student";
	public final static String TABLE_NAME = "hero";
	private final static String SNAME = "name";
//	public final static String Age = "age";
	public final static String SID = "_id";
	public final static int DB_VERSION = 1;
	/*
	 * AUTHORITY:定义了标识ContentProvider的字符串 ;
	 * ITEM和ITEM_ID分别用于UriMatcher(资源标识符匹配器)中对路径item和item/id的匹配号码
	 * CONTENT_TYPE和CONTENT_ITEM_TYPE定义了数据的MIME类型。需要注意的是: 单一数据的MIME 类型字符串应该以
	 * vnd.android.cursor.item/开头,数据集的MIME类型字符串应该以vnd.android.cursor.dir开头
	 * CONTENT_URI定义的是查询当前表数据的content://样式URI
	 */
	public static final String AUTHORITY = "com.myapp.provider.studentdata";
	public static final int ITEM = 1;
	public static final int ITEM_ID = 2;
	public static final String CONTENT_TYPE = "vnd.android.cursor.dir/hero";
	public static final String CONTENT_ITEM_TYPE = "vnd.android.cursor.item/hero";
	public static final Uri CONTENT_URI = Uri.parse("content://" + AUTHORITY
			+ "/item");

	public StudentData(Context context) {
		super(context, DB_NAME, null, DB_VERSION);
	}

	@Override
	public void onCreate(SQLiteDatabase db) {
		db.execSQL("CREATE TABLE " + TABLE_NAME + "(" + SID
				+ " INTEGER PRIMARY KEY AUTOINCREMENT," + SNAME + " VARCHAR NOT NULL);");
		
	}

	@Override
	public void onUpgrade(SQLiteDatabase db, int arg1, int arg2) {
		db.execSQL("DROP TABLE IF EXISTS " + TABLE_NAME);
	}
	
}

数据共享声明;

<provider
	android:name=".MyProvider"
	android:authorities="com.myapp.provider.studentdata"/>

创建测试工程TestStudentCon

package com.mycontent.test;

import com.mycontent.StudentData;

import android.content.ContentResolver;
import android.content.ContentValues;
import android.database.Cursor;
import android.net.Uri;
import android.test.AndroidTestCase;
import android.util.Log;

public class TestStuConPro extends AndroidTestCase {

	 public void testInsert()throws Exception{   //插入记录  
	        Uri uri = Uri.parse("content://" + "com.myapp.provider.studentdata"
	    			+ "/item");  
	        ContentResolver resolver = this.getContext().getContentResolver();  
	        ContentValues values = new ContentValues();  
	        values.put("name", "ddd1");  
	        values.put("name", "eee1");  
	        resolver.insert(uri, values);  
	    }  
	 
	 public void testUpdate()throws Exception{   //更新id=2的记录
		 Uri uri = Uri.parse("content://" + "com.myapp.provider.studentdata"
	    			+ "/item/2"); 
	        ContentResolver resolver = this.getContext().getContentResolver();  
	        ContentValues values = new ContentValues();  
	        values.put("name", "aaa");  
	        resolver.update(uri, values, null, null);  
	    }  
	 
	    public void testDelete()throws Exception{   //删除id=1的记录  
	    	Uri uri = Uri.parse("content://" + "com.myapp.provider.studentdata"
	    			+ "/item/1"); //删除id=1的记录  
	        ContentResolver resolver = this.getContext().getContentResolver();  
	        resolver.delete(uri, null, null);  
	    }  
	    
	    public void testQuery()throws Exception{    //插入全部记录并显示  
	    	 Uri uri = Uri.parse("content://" + "com.myapp.provider.studentdata"
		    			+ "/item");    //查询所有记录  
	        ContentResolver resolver = this.getContext().getContentResolver();  
	        Cursor cursor = resolver.query(uri, null, null, null, null);  
	        while(cursor.moveToNext()){  
	         //   StudentData person = new StudentData(cursor.getInt(cursor.getColumnIndex("id")),cursor.getString(cursor.getColumnIndex("name")),cursor.getInt(cursor.getColumnIndex("age")));  
	           Log.v("ContentProvider", cursor.getInt((cursor.getColumnIndex("_id")))+"");  
	        }  
	    }  
	    
}

ok,完事。

【上篇】
【下篇】

抱歉!评论已关闭.