ContentProviderを継承する新しいクラスを作成して、独自のコンテンツプロバイダーを作成します。
ContentProviderクラスには6つの抽象メソッドがあります。サブクラスを使用して継承する場合は、これら6つのメソッドすべてを書き直す必要があります。
- 新しいMyProviderはContentProviderから継承します。いくつかのメソッドをコピーします。
```handlebars
public class MyProvider extends ContentProvider {
@Override
public boolean onCreate() {
return false;
}
@Override
public Cursor query(Uri uri, String[] projection, String selection,
String[] selectionArgs, String sortOrder) {
return null;
}
@Override
public Uri insert(Uri uri, ContentValues values) {
return null;
}
@Override
public int update(Uri uri, ContentValues values, String selection,
String[] selectionArgs) {
return 0;
}
@Override
public int delete(Uri uri, String selection, String[] selectionArgs) {
return 0;
}
@Override
public String getType(Uri uri) {
return null;
}
}
1. onCreate()
これは、コンテンツプロバイダーが初期化されるときに呼び出されます。通常、ここでデータベースの作成やアップグレードなどの操作を完了します
。trueを返すと、コンテンツプロバイダーは正常に初期化され、falseは失敗したことを意味します。
コンテンツプロバイダーは、プログラム内のデータにアクセスしようとしているContentResolverがある場合にのみ初期化されることに注意してください。
2. query()
コンテンツプロバイダーからデータをクエリします。
uriパラメーターを使用してクエリするテーブルを決定し、projectionパラメーターを使用してクエリする列を決定し、selectionおよびselectionArgsパラメーターを使用してクエリする行を制約し、sortOrderパラメーターを使用して結果を並べ替えます。
クエリの結果はCursorオブジェクトに格納され、返されます。
3. insert()
コンテンツプロバイダーにデータを追加します。
uriパラメーターを使用して、追加するテーブルを決定します。追加するデータは、valuesパラメーターに格納されます。
追加が完了したら、この新しいレコードを表すURIを返します。
4. update()
コンテンツプロバイダーの既存のデータを更新します。
uriパラメーターを使用して、更新するテーブルのデータを決定します。新しいデータはvaluesパラメーターに格納されます。selectionパラメーターとselectionArgsパラメーターは、更新する行を制限するために使用されます。
影響を受ける行の数が戻り値として返されます。
5. delete()
コンテンツプロバイダーからデータを削除します。
uriパラメーターを使用して、削除するテーブルのデータを決定し、selectionおよびselectionArgsパラメーターを使用して、削除する行を制限します。
削除された行の数が戻り値として返されます。
6. getType()
着信コンテンツURIに従って、対応するMIMEタイプを返します。
コンテンツURIに対応するMIME文字列は、主に3つの部分で構成され
ています。vndで始まる必要があります。
コンテンツURIがパスで終わる場合は、android.cursor.dir /が続き、コンテンツURIがIDで終わる場合は、android.cursor.item /が続きます。
最後に、vndを接続します。
content://com.example.app.provider/table1の場合、対応するMIMEタイプは次の
とおりです。vnd.android.cursor.dir/ vnd.com.example.app.provider.table1
content://com.example.appの場合.provider / table1 / 1、対応するMIMEタイプは次の
とおりです。vnd.android.cursor.item/ vnd.com.example.app.provider.table1
getType()ロジックを実装します。
public class MyProvider extends ContentProvider {
......
@Override
public String getType(Uri uri) {
switch (uriMatcher.match(uri)) {
case TABLE1_DIR:
return "vnd.android.cursor.dir/vnd.com.example.app.provider.table1";
case TABLE1_ITEM:
return "vnd.android.cursor.item/vnd.com.example.app.provider.table1";
case TABLE2_DIR:
return "vnd.android.cursor.dir/vnd.com.example.app.provider.table2";
case TABLE2_ITEM:
return "vnd.android.cursor.item/vnd.com.example.app.provider.table2";
default:
break;
}
return null;
}
}
- UriMatcherを使用してコンテンツURIを照合することで、着信Uriオブジェクトがどのテーブルのどのデータにアクセスしたいかがわかります。
任意のテーブルに一致する可能性のあるコンテンツURI:
content://com.example.app.provider/ *テーブル1
のデータの任意の行に一致する可能性のあるコンテンツURI :
content://com.example.app.provider/table1/#
UriMatcherは、3つのパラメーターを受け取り、それぞれパーミッション、パス、およびカスタムコードを渡すことができるaddURI()メソッドを提供します。
UriMatcherのmatch()メソッドが呼び出されると、Uriオブジェクトを渡すことができ、戻り
値はこのUriオブジェクトに一致するカスタムコードです。
このコードを使用して、呼び出し元がアクセスすることを期待しているデータのテーブルまたは行を判別できます。
public static final int TABLE1_DIR = 0;
public static final int TABLE1_ITEM = 1;
public static final int TABLE2_DIR = 2;
public static final int TABLE2_ITEM = 3;
private static UriMatcher uriMatcher;
static {
uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
uriMatcher.addURI("com.example.app.provider", "table1", TABLE1_DIR);
uriMatcher.addURI("com.example.app.provider ", "table1/#", TABLE1_ITEM);
uriMatcher.addURI("com.example.app.provider ", "table2", TABLE2_ITEM);
uriMatcher.addURI("com.example.app.provider ", "table2/#", TABLE2_ITEM);
}
- スイッチを使用して、MyProviderのいくつかのメソッドでuriMatcher.match(uri)を判断し、さまざまなUriの目的に応じて、対応するテーブルまたは行に目的を配置します。
public class MyProvider extends ContentProvider {
public static final int TABLE1_DIR = 0;
public static final int TABLE1_ITEM = 1;
public static final int TABLE2_DIR = 2;
public static final int TABLE2_ITEM = 3;
private static UriMatcher uriMatcher;
static {
uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
uriMatcher.addURI("com.example.app.provider", "table1", TABLE1_DIR);
uriMatcher.addURI("com.example.app.provider ", "table1/#", TABLE1_ITEM);
uriMatcher.addURI("com.example.app.provider ", "table2", TABLE2_ITEM);
uriMatcher.addURI("com.example.app.provider ", "table2/#", TABLE2_ITEM);
}
......
@Override
public Cursor query(Uri uri, String[] projection, String selection,
String[] selectionArgs, String sortOrder) {
switch (uriMatcher.match(uri)) {
case TABLE1_DIR:
// 查询table1表中的所有数据
break;
case TABLE1_ITEM:
// 查询table1表中的单条数据
break;
case TABLE2_DIR:
// 查询table2表中的所有数据
break;
case TABLE2_ITEM:
// 查询table2表中的单条数据
break;
default:
break;
}
......
}
......
}
- 目的が明確になった後、SQLiteDatabaseに対して特定の操作を実行して、追加、削除、および変更のチェックを完了します。
public class DatabaseProvider extends ContentProvider {
public static final int BOOK_DIR = 0;
public static final int BOOK_ITEM = 1;
public static final int CATEGORY_DIR = 2;
public static final int CATEGORY_ITEM = 3;
public static final String AUTHORITY = "com.example.databasetest.provider";
private static UriMatcher uriMatcher;
private MyDatabaseHelper dbHelper;
static {
uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
uriMatcher.addURI(AUTHORITY, "book", BOOK_DIR);
uriMatcher.addURI(AUTHORITY, "book/#", BOOK_ITEM);
uriMatcher.addURI(AUTHORITY, "category", CATEGORY_DIR);
uriMatcher.addURI(AUTHORITY, "category/#", CATEGORY_ITEM);
}
@Override
public boolean onCreate() {
dbHelper = new MyDatabaseHelper(getContext(), "BookStore.db", null, 2);
return true;
}
@Override
public Cursor query(Uri uri, String[] projection, String selection,
String[] selectionArgs, String sortOrder) {
// 查询数据
SQLiteDatabase db = dbHelper.getReadableDatabase();
Cursor cursor = null;
switch (uriMatcher.match(uri)) {
case BOOK_DIR:
cursor = db.query("Book", projection, selection, selectionArgs, null, null, sortOrder);
break;
case BOOK_ITEM:
String bookId = uri.getPathSegments().get(1);
cursor = db.query("Book", projection, "id = ?", new String[]{
bookId }, null, null, sortOrder);
break;
case CATEGORY_DIR:
cursor = db.query("Category", projection, selection, selectionArgs, null, null, sortOrder);
break;
case CATEGORY_ITEM:
String categoryId = uri.getPathSegments().get(1);
cursor = db.query("Category", projection, "id = ?", new String[] {
categoryId }, null, null, sortOrder);
break;
default:
break;
}
return cursor;
}
@Override
public Uri insert(Uri uri, ContentValues values) {
// 添加数据
SQLiteDatabase db = dbHelper.getWritableDatabase();
Uri uriReturn = null;
switch (uriMatcher.match(uri)) {
case BOOK_DIR:
case BOOK_ITEM:
long newBookId = db.insert("Book", null, values);
uriReturn = Uri.parse("content://" + AUTHORITY + "/book/" + newBookId);
break;
case CATEGORY_DIR:
case CATEGORY_ITEM:
long newCategoryId = db.insert("Category", null, values);
uriReturn = Uri.parse("content://" + AUTHORITY + "/category/" + newCategoryId);
break;
default:
break;
}
return uriReturn;
}
@Override
public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {
// 更新数据
SQLiteDatabase db = dbHelper.getWritableDatabase();
int updatedRows = 0;
switch (uriMatcher.match(uri)) {
case BOOK_DIR:
updatedRows = db.update("Book", values, selection, selectionArgs);
break;
case BOOK_ITEM:
String bookId = uri.getPathSegments().get(1);
updatedRows = db.update("Book", values, "id = ?", new String[] {
bookId });
break;
case CATEGORY_DIR:
updatedRows = db.update("Category", values, selection, selectionArgs);
break;
case CATEGORY_ITEM:
String categoryId = uri.getPathSegments().get(1);
updatedRows = db.update("Category", values, "id = ?", new String[] {
categoryId });
break;
default:
break;
}
return updatedRows;
}
@Override
public int delete(Uri uri, String selection, String[] selectionArgs) {
// 删除数据
SQLiteDatabase db = dbHelper.getWritableDatabase();
int deletedRows = 0;
switch (uriMatcher.match(uri)) {
case BOOK_DIR:
deletedRows = db.delete("Book", selection, selectionArgs);
break;
case BOOK_ITEM:
String bookId = uri.getPathSegments().get(1);
deletedRows = db.delete("Book", "id = ?", new String[] {
bookId });
break;
case CATEGORY_DIR:
deletedRows = db.delete("Category", selection, selectionArgs);
break;
case CATEGORY_ITEM:
String categoryId = uri.getPathSegments().get(1);
deletedRows = db.delete("Category", "id = ?", new String[] {
categoryId });
break;
default:
break;
}
return deletedRows;
}
@Override
public String getType(Uri uri) {
switch (uriMatcher.match(uri)) {
case BOOK_DIR:
return "vnd.android.cursor.dir/vnd.com.example.databasetest. provider.book";
case BOOK_ITEM:
return "vnd.android.cursor.item/vnd.com.example.databasetest. provider.book";
case CATEGORY_DIR:
return "vnd.android.cursor.dir/vnd.com.example.databasetest. provider.category";
case CATEGORY_ITEM:
return "vnd.android.cursor.item/vnd.com.example.databasetest. provider.category";
}
return null;
}
}
getPathSegments()メソッドは
、コンテンツURI権限の後の部分を「/」記号で分割し、分割の結果を文字列リストに入れます。このリストの0番目の位置はパスで、1番目のこの場所はIDを格納します。
- AndroidManifest.xmlに登録します。
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.databasetest"
android:versionCode="1"
android:versionName="1.0" >
......
<application
android:allowBackup="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme" >
......
<provider
android:name="com.example.databasetest.DatabaseProvider"
android:authorities="com.example.databasetest.provider" >
</provider>
</application>
</manifest>