淺談Android Content Provider的使用

來源:互聯網
上載者:User

Content Provider:一個組件,必須放在應用的主包或應用的子包之下;

組件的配置需要在資訊清單檔中進行配置;content provider需要在application節點中進行配置;
內容提供者在應用中的作用是對外共用資料(任意類型的資料)使用的,別的程式可以對資料進行CRUD,如通訊錄;
如果採用檔案的方式對外共用資料,會因為檔案的類型不同而需要使用不同的api訪問方式導致訪問繁雜,而內容提供者提供了統一的api對資料進行操作;
<provider
  android:name=".PersonProvider"<!-- 內容提供者類的名稱 -->
  android:authorities="cn.wordtech.providers.personprovider"

  android:exported="false" ><!-- 解決 android Permission Denial error!,在監聽內容提供者資料發生變化時需要配置此項 -->
</provider>

另:
android:authorities:為內容提供者指定一個唯一的標識,這樣別的應用才可以唯一擷取此provider;

Uri 代表了要操作的資料;
Uri主要包含兩部分的資訊:1>>需要操作的ContentProvider,2>>對ContentProvider中的什麼資料進行操作

ContentProvider(內容提供者)的scheme已經由Android所規定,scheme為:content://
主機名稱(或Authority)用於唯一標識這個ContentProvider,外部調用者可以根據此標識來找到它,
路徑(path)可以用來表示我們要操作的資料,路徑的構建根據業務而定。
ex:
要操作person表中id為10的記錄,可以構建這樣的路徑:/person/10
要操作person表中id為10的記錄的name欄位,可以構建這樣的路徑:/person/10/name
要操作person表中的所有記錄,可以構建這樣的路徑:/person
要操作XXX表中的記錄,可以構建這樣的路徑:/XXX
要操作的資料不一定是資料庫中的檔案,也可以是檔案,xml或網路等其它方式
ex:
要操作xml檔案中person節點下的name節點,可以構建這樣的路徑:/person/name

複製代碼 代碼如下:public class PersonProvider extends ContentProvider {// Content Provider需要繼承自ContentProvider類
// 刪改查中,都有兩種情況:
// person 對整個表進行操作
// person/id 對錶中的與id對應記錄進行操作
private DBOpenHelper dbOpenHelper;
private static final UriMatcher MATCHER = new UriMatcher(UriMatcher.NO_MATCH);// new UriMatcher(code);code即為匹配不成功時返回的值;
private static final int PERSONS = 1;
private static final int PERSON = 2;
// 設定匹配項
static {
MATCHER.addURI("cn.wordtech.providers.personprovider", "person",PERSONS);
MATCHER.addURI("cn.wordtech.providers.personprovider", "person/#",PERSON);// #號表示數字
}
// content://cn.wordtech.providers.personprovider/person
@Override
public boolean onCreate() {
// 由系統調用,當ContentProvider的執行個體被建立出來的時候被調用,Android開機後,當第一次有應用訪問ContentProvider時才建立ContentProvider;
dbOpenHelper = new DBOpenHelper(getContext(), 1);
return false;
}

// 可以供外部的應用查詢資料,返回查詢得到的遊標對象
@Override
public Cursor query(Uri uri, String[] projection, String selection,
String[] selectionArgs, String sortOrder) {
SQLiteDatabase db = dbOpenHelper.getWritableDatabase();
switch (MATCHER.match(uri)) {
case 1:
return db.query("person", projection, selection, selectionArgs,
null, null, sortOrder);
case 2:
long rowid = ContentUris.parseId(uri);// 返回要操作的id
String where = "personid=" + rowid;
if (selection != null && !"".equals(selection.trim())) {
where += "and" + selection;
}
return db.query("person", projection, where, selectionArgs, null,
null, sortOrder);

default:
throw new IllegalArgumentException("");
}
}

// 此方法用於返回目前Uri所代表的資料的MIME類型,
// 如果操作的資料屬於集合類型,則MIME字串就以"vnd.android.cursor.dir"開頭
// 如果操作的資料屬於非集合類型,則MIME字串就以"vnd.android.cursor.item"開頭
@Override
public String getType(Uri uri) {
switch (MATCHER.match(uri)) {
case 1:
return "vnd.android.cursor.dir/person";
case 2:
return "vnd.android.cursor.item/person";
default:
throw new IllegalArgumentException("");
}
}

// 此方法需要返回操作記錄對應的Uri
@Override
public Uri insert(Uri uri, ContentValues values) {
SQLiteDatabase db = dbOpenHelper.getWritableDatabase();
switch (MATCHER.match(uri)) {
case 1:
long rowid = db.insert("person", "", values);// 返回行號?主索引值
// Uri insertUri = Uri
// .parse("content://com.sqlite.PersonProvider/person/"
// + rowid);
Uri insertUri = ContentUris.withAppendedId(uri, rowid);
return insertUri;
default:
throw new IllegalArgumentException("this is Unknow Uri:" + uri);
}

}

// 返回受影響的行數
@Override
public int delete(Uri uri, String selection, String[] selectionArgs) {
SQLiteDatabase db = dbOpenHelper.getWritableDatabase();
int num = 0;
switch (MATCHER.match(uri)) {
case 1:
num = db.delete("person", selection, selectionArgs);// 清空整個表
break;
case 2:
long rowid = ContentUris.parseId(uri);// 返回要操作的id
String where = "personid=" + rowid;
if (selection != null && !"".equals(selection.trim())) {
where += "and" + selection;
}
num = db.delete("person", where, selectionArgs);
break;
default:
throw new IllegalArgumentException("");
}
return num;
}

@Override // 返回受影響的行數
public int update(Uri uri, ContentValues values, String selection,String[] selectionArgs) {
SQLiteDatabase db = dbOpenHelper.getWritableDatabase();
int num = 0;
switch (MATCHER.match(uri)) {
case 1:
num = db.update("person", values, selection, selectionArgs);
break;
case 2:
long rowid = ContentUris.parseId(uri);// 返回要操作的id
String where = "personid=" + rowid;
if (selection != null && !"".equals(selection.trim())) {
where += "and" + selection;
}
num = db.update("person", values, where, selectionArgs);
break;
default:
throw new IllegalArgumentException("");
}
return num;
}
}

下面是對前一個類進行測試
複製代碼 代碼如下:public class AccessContentProviderTest extends AndroidTestCase {
public void testinsert() {
Uri uri = Uri.parse("content://cn.wordtech.providers.personprovider/person");// 根據標識名得到內容提供者
ContentResolver cr = this.getContext().getContentResolver(); // This class provides applications access to the content model
ContentValues values = new ContentValues();
values.put("name", "Livingstone");
values.put("phone", "110");
values.put("amount", "1111111111");
cr.insert(uri, values);// 在cr的內部會調用內容提供者的值;
}

public void testdelete() {
Uri uri = Uri.parse("content://cn.wordtech.providers.personprovider/person/1");// 根據標識名得到內容提供者
ContentResolver cr = this.getContext().getContentResolver();
cr.delete(uri, null, null);
}

public void testupdate() {
Uri uri = Uri.parse("content://cn.wordtech.providers.personprovider/person/2");// 根據標識名得到內容提供者
ContentResolver cr = this.getContext().getContentResolver();
ContentValues values = new ContentValues();
values.put("name", "Livingstone11");
cr.update(uri, values, null, null);
}

public void testquery() {
Uri uri = Uri.parse("content://cn.wordtech.providers.personprovider/person");// 根據標識名得到內容提供者
ContentResolver cr = this.getContext().getContentResolver();
Cursor cursor = cr.query(uri, null, null, null, "personid asc");
while (cursor.moveToNext()) {
String name = cursor.getString(cursor.getColumnIndex("name"));
Log.i("Name", name);
}
}
}

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.