ContentProvider完整案例


ContentData类,提供数据常量:

/**
 * 提供ContentProvider对外的各种常量,当外部数据需要访问的时候,就可以参考这些常量操作数据。
 * @author HB
 *
 */
public class ContentData {
	public static final String AUTHORITY = "hb.android.contentProvider";
	public static final String DATABASE_NAME = "teacher.db";
	//创建 数据库的时候,都必须加上版本信息;并且必须大于4
	public static final int DATABASE_VERSION = 4;
	public static final String USERS_TABLE_NAME = "teacher";
	
	public static final class UserTableData implements BaseColumns {
		public static final String TABLE_NAME = "teacher";
		//Uri,外部程序需要访问就是通过这个Uri访问的,这个Uri必须的唯一的。
		public static final Uri CONTENT_URI = Uri.parse("content://"+ AUTHORITY + "/teacher");
		// 数据集的MIME类型字符串则应该以vnd.android.cursor.dir/开头  
		public static final String CONTENT_TYPE = "vnd.android.cursor.dir/hb.android.teachers";
		// 单一数据的MIME类型字符串应该以vnd.android.cursor.item/开头  
		public static final String CONTENT_TYPE_ITME = "vnd.android.cursor.item/hb.android.teacher";
		/* 自定义匹配码 */  
	    public static final int TEACHERS = 1;  
	    /* 自定义匹配码 */  
	    public static final int TEACHER = 2;  
	    
		public static final String TITLE = "title";
		public static final String NAME = "name";
		public static final String DATE_ADDED = "date_added";
		public static final String SEX = "SEX";
		public static final String DEFAULT_SORT_ORDER = "_id desc";
		
		public static final UriMatcher uriMatcher;  
	    static {  
	        // 常量UriMatcher.NO_MATCH表示不匹配任何路径的返回码  
	        uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);  
	        // 如果match()方法匹配content://hb.android.teacherProvider/teachern路径,返回匹配码为TEACHERS  
	        uriMatcher.addURI(ContentData.AUTHORITY, "teacher", TEACHERS);  
	        // 如果match()方法匹配content://hb.android.teacherProvider/teacher/230,路径,返回匹配码为TEACHER  
	        uriMatcher.addURI(ContentData.AUTHORITY, "teacher/#", TEACHER);  
	    }
	}
}

SQLite操作类DBOpenHelper

/**
 * 这个类继承SQLiteOpenHelper抽象类,用于创建数据库和表。创建数据库是调用它的父类构造方法创建。
 * @author HB
 */
public class DBOpenHelper extends SQLiteOpenHelper {

	// 在SQLiteOepnHelper的子类当中,必须有该构造函数,用来创建一个数据库;
	public DBOpenHelper(Context context, String name, CursorFactory factory,
			int version) {
		// 必须通过super调用父类当中的构造函数
		super(context, name, factory, version);
		// TODO Auto-generated constructor stub
	}

	// public DBOpenHelper(Context context, String name) {
	// this(context, name, VERSION);
	// }

	public DBOpenHelper(Context context, String name, int version) {
		this(context, name, null, version);
	}
	
	/**
	 * 只有当数据库执行创建 的时候,才会执行这个方法。如果更改表名,也不会创建,只有当创建数据库的时候,才会创建改表名之后 的数据表
	 */
	@Override
	public void onCreate(SQLiteDatabase db) {
System.out.println("create table");
		db.execSQL("create table " + ContentData.UserTableData.TABLE_NAME
				+ "(" + ContentData.UserTableData._ID
				+ " INTEGER PRIMARY KEY autoincrement,"
				+ ContentData.UserTableData.NAME + " varchar(20),"
				+ ContentData.UserTableData.TITLE + " varchar(20),"
				+ ContentData.UserTableData.DATE_ADDED + " long,"
				+ ContentData.UserTableData.SEX + " boolean)" + ";");
	}

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

	}

}


内容提供者类

/**
 * 这个类给外部程序提供访问内部数据的一个接口
 * @author HB
 *
 */
public class TeacherContentProvider extends ContentProvider {
	
	private DBOpenHelper dbOpenHelper = null;  
	// UriMatcher类用来匹配Uri,使用match()方法匹配路径时返回匹配码  
      
      
    /**
     * 是一个回调函数,在ContentProvider创建的时候,就会运行,第二个参数为指定数据库名称,如果不指定,就会找不到数据库;
     * 如果数据库存在的情况下是不会再创建一个数据库的。(当然首次调用 在这里也不会生成数据库必须调用SQLiteDatabase的 getWritableDatabase,getReadableDatabase两个方法中的一个才会创建数据库)
     */
    @Override  
    public boolean onCreate() { 
    	//这里会调用 DBOpenHelper的构造函数创建一个数据库;
        dbOpenHelper = new DBOpenHelper(this.getContext(), ContentData.DATABASE_NAME, ContentData.DATABASE_VERSION);
        return true;  
    }  
    /**
     * 当执行这个方法的时候,如果没有数据库,他会创建,同时也会创建表,但是如果没有表,下面在执行insert的时候就会出错
     * 这里的插入数据也完全可以用sql语句书写,然后调用 db.execSQL(sql)执行。
     */
    @Override  
    public Uri insert(Uri uri, ContentValues values){  
    	//获得一个可写的数据库引用,如果数据库不存在,则根据onCreate的方法里创建;
        SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
        long id = 0;  
        
        switch (uriMatcher.match(uri)) {  
        case TEACHERS:  
            id = db.insert("teacher", null, values);	// 返回的是记录的行号,主键为int,实际上就是主键值  
            return ContentUris.withAppendedId(uri, id);  
        case TEACHER:  
            id = db.insert("teacher", null, values); 
            String path = uri.toString();  
            return Uri.parse(path.substring(0, path.lastIndexOf("/"))+id); // 替换掉id  
        default:  
            throw new IllegalArgumentException("Unknown URI " + uri);  
        }
    }  
      
    @Override  
    public int delete(Uri uri, String selection, String[] selectionArgs) {  
        SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
        int count = 0;  
        switch (uriMatcher.match(uri)) {  
        case TEACHERS:  
            count = db.delete("teacher", selection, selectionArgs);  
            break;  
        case TEACHER:  
            // 下面的方法用于从URI中解析出id,对这样的路径content://hb.android.teacherProvider/teacher/10  
            // 进行解析,返回值为10  
            long personid = ContentUris.parseId(uri);  
            String where = "_ID=" + personid;	// 删除指定id的记录  
            where += !TextUtils.isEmpty(selection) ? " and (" + selection + ")" : "";	// 把其它条件附加上  
            count = db.delete("teacher", where, selectionArgs);  
            break;  
        default:  
            throw new IllegalArgumentException("Unknown URI " + uri);  
        }  
        db.close();  
        return count;  
    }  
  
    @Override  
    public int update(Uri uri, ContentValues values, String selection,  
            String[] selectionArgs) {  
        SQLiteDatabase db = dbOpenHelper.getWritableDatabase();  
        int count = 0;  
        switch (uriMatcher.match(uri)) {  
        case TEACHERS:  
            count = db.update("teacher", values, selection, selectionArgs);  
            break;  
        case TEACHER:  
            // 下面的方法用于从URI中解析出id,对这样的路径content://com.ljq.provider.personprovider/person/10  
            // 进行解析,返回值为10  
            long personid = ContentUris.parseId(uri);  
            String where = "_ID=" + personid;// 获取指定id的记录  
            where += !TextUtils.isEmpty(selection) ? " and (" + selection + ")" : "";// 把其它条件附加上  
            count = db.update("teacher", values, where, selectionArgs);  
            break;  
        default:  
            throw new IllegalArgumentException("Unknown URI " + uri);  
        }  
        db.close();  
        return count;  
    }  
      
    @Override  
    public String getType(Uri uri) {  
        switch (uriMatcher.match(uri)) {  
        case TEACHERS:  
            return CONTENT_TYPE;  
        case TEACHER:  
            return CONTENT_TYPE_ITME;  
        default:  
            throw new IllegalArgumentException("Unknown URI " + uri);  
        }  
    }  
  
    @Override  
    public Cursor query(Uri uri, String[] projection, String selection,  
            String[] selectionArgs, String sortOrder) {  
        SQLiteDatabase db = dbOpenHelper.getReadableDatabase();  
        switch (uriMatcher.match(uri)) {  
        case TEACHERS:  
            return db.query("teacher", projection, selection, selectionArgs, null, null, sortOrder);  
        case TEACHER:  
            // 进行解析,返回值为10  
            long personid = ContentUris.parseId(uri);  
            String where = "_ID=" + personid;// 获取指定id的记录  
            where += !TextUtils.isEmpty(selection) ? " and (" + selection + ")" : "";// 把其它条件附加上  
            return db.query("teacher", projection, where, selectionArgs, null, null, sortOrder);  
        default:  
            throw new IllegalArgumentException("Unknown URI " + uri);  
        }  
    }  
}



文件清单:

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
      package="hb.android.contentProvider"
      android:versionCode="1"
      android:versionName="1.0">
    <uses-sdk android:minSdkVersion="8" />


    <application android:icon="@drawable/icon" android:label="@string/app_name">
        <activity android:name=".TeacherActivity"
                  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=".TeacherContentProvider"
			android:authorities="hb.android.contentProvider" />
    </application>
</manifest>

main.xml文件:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    >
<Button 
	android:id="@+id/insert"
	android:text="@string/insert"
	android:layout_width="fill_parent"
	android:layout_height="wrap_content"/>
<Button 
	android:id="@+id/query"
	android:text="@string/query"
	android:layout_width="fill_parent"
	android:layout_height="wrap_content"/>
<Button 
	android:id="@+id/querys"
	android:text="@string/querys"
	android:layout_width="fill_parent"
	android:layout_height="wrap_content"/>
<Button 
	android:id="@+id/update"
	android:text="@string/update"
	android:layout_width="fill_parent"
	android:layout_height="wrap_content"/>
<Button 
	android:id="@+id/delete"
	android:text="@string/delete"
	android:layout_width="fill_parent"
	android:layout_height="wrap_content"/>
</LinearLayout>


TeacherActivity内容提供者测试类

package hb.android.contentProvider;

import java.util.Date;

import android.app.Activity;
import android.content.ContentResolver;
import android.content.ContentValues;
import android.database.Cursor;
import android.net.Uri;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;

/**
 * 这个类用来测试ContentProvider是否可用。通过 给定的uri访问,数据库;
 * 
 * @author HB
 * 
 */
public class TeacherActivity extends Activity {
	Button insert;
	Button query;
	Button update;
	Button delete;
	Button querys;
	Uri uri = Uri.parse("content://hb.android.contentProvider/teacher");

	/** Called when the activity is first created. */
	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.main);

		insert = (Button) findViewById(R.id.insert);
		query = (Button) findViewById(R.id.query);
		update = (Button) findViewById(R.id.update);
		delete = (Button) findViewById(R.id.delete);
		querys = (Button) findViewById(R.id.querys);
		// 绑定监听器的两种方法一;
		insert.setOnClickListener(new InsertListener());
		query.setOnClickListener(new QueryListener());
		// 方法二
		update.setOnClickListener(new OnClickListener() {
			public void onClick(View v) {
				// TODO Auto-generated method stub
				ContentResolver cr = getContentResolver();
				ContentValues cv = new ContentValues();
				cv.put("name", "huangbiao");
				cv.put("date_added", (new Date()).toString());
				int uri2 = cr.update(uri, cv, "_ID=?", new String[]{"3"});
System.out.println("updated"+":"+uri2);
			}
		});

		delete.setOnClickListener(new OnClickListener() {
			
			public void onClick(View v) {
				ContentResolver cr = getContentResolver();
				cr.delete(uri, "_ID=?", new String[]{"2"});
			}
		});

		querys.setOnClickListener(new OnClickListener() {

			public void onClick(View v) {
				// TODO Auto-generated method stub
				ContentResolver cr = getContentResolver();
				// 查找id为1的数据
				Cursor c = cr.query(uri, null, null,null, null);
				System.out.println(c.getCount());
				c.close();
			}
		});
	}

	class InsertListener implements OnClickListener {

		public void onClick(View v) {
			// TODO Auto-generated method stub
			ContentResolver cr = getContentResolver();

			ContentValues cv = new ContentValues();
			cv.put("title", "jiaoshou");
			cv.put("name", "jiaoshi");
			cv.put("sex", true);
			Uri uri2 = cr.insert(uri, cv);
			System.out.println(uri2.toString());
		}

	}

	class QueryListener implements OnClickListener {

		public void onClick(View v) {
			// TODO Auto-generated method stub
			ContentResolver cr = getContentResolver();
			// 查找id为1的数据
			Cursor c = cr.query(uri, null, "_ID=?", new String[] { "1" }, null);
			//这里必须要调用 c.moveToFirst将游标移动到第一条数据,不然会出现index -1 requested , with a size of 1错误;cr.query返回的是一个结果集。
			if (c.moveToFirst() == false) {
				// 为空的Cursor
				return;
			}
			int name = c.getColumnIndex("name");
			System.out.println(c.getString(name));
			c.close();
		}
	}
}



运行结果为:


  • 6
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

IT人.阿标

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值