Android - コンテンツプロバイダー

1. はじめに

ContentProvider は、主に異なるアプリケーション間でのデータ共有機能を実現するために使用され、あるプログラムが別のプログラムのデータにアクセスできるようにし、アクセスされるデータのセキュリティを確保するための一連の仕組みを提供します。現在、ContentProvider を使用するのが、Android がプログラム間でデータを共有する標準的な方法です。ContentProvider は、プログラム内の個人データが漏洩する危険がないように、データのどの部分のみを共有するかを選択できます。

1.ContentResolverの基本的な使い方

各アプリケーションで、ContentProvider で共有されているデータにアクセスする場合は、ContentResolver クラスを使用する必要があります。このクラスのインスタンスは、 Context の getContentResolver() メソッドを通じて取得できます。ContentResolver は、データを追加、削除、変更、クエリするための一連のメソッドを提供します。insert() メソッドはデータの追加に使用され、update() メソッドはデータの更新に使用され、delete() メソッドはデータの削除に使用されます。 query() メソッド データのクエリに使用されます。既視感はありますか?そうです。これらのメソッドは SQLiteDatabase でも追加、削除、変更、クエリ操作を実行するために使用されますが、メソッド パラメーターが若干異なります。SQLiteDatabase とは異なり、ContentResolver の追加、削除、変更、クエリ メソッドはテーブル名パラメーターを受け入れませんが、代わりにコンテンツ URI と呼ばれる Uri パラメーターを使用します。コンテンツ URI は、ContentProvider 内のデータの一意の識別子を確立し、主に権限とパスの 2 つの部分で構成されます。権限は異なるアプリケーションを区別するために使用され、一般に競合を避けるためにアプリケーションのパッケージ名が命名に使用されます。たとえば、アプリケーションのパッケージ名が com.example.app の場合、アプリケーションに対応する権限は com.example.app.provider と名付けられます。パスは、同じアプリケーション内の異なるテーブルを区別するために使用され、通常は権限の後に追加されます。たとえば、アプリケーションのデータベースに table1 と table2 という 2 つのテーブルがあるとします。このとき、パスにそれぞれ /table1 と /table2 という名前を付け、権限とパスを組み合わせると、コンテンツ URI は com.example になります。 app.provider/table1 および com.example.app.provider/table2。ただし、これら 2 つの文字列を 2 つのコンテンツ URI として識別することは依然として困難であり、文字列の先頭にプロトコル ステートメントを追加する必要もあります。したがって、コンテンツ URI の最も標準的な形式は次のとおりです。

content://com.example.app.provider/table1 
content://com.example.app.provider/table2

コンテンツ URI 文字列を取得した後、パラメーターとして渡す前に、それを Uri オブジェクトに解析する必要があります。解析方法も非常に簡単で、コードは次のとおりです。

val uri = Uri.parse("content://com.example.app.provider/table1")

2.使用する

val cursor = contentResolver.query(
 uri,
 projection,
 selection,
 selectionArgs,
 sortOrder)

 クエリが完了した後も Cursor オブジェクトが返されるので、Cursor オブジェクトからデータを 1 つずつ読み取ることができます。読み取りの考え方は、やはりカーソルの位置を移動してカーソルのすべての行を走査し、各行の対応する列のデータをフェッチすることです。コードは次のとおりです。

 while (cursor.moveToNext()) { 
    val column1 = cursor.getString(cursor.getColumnIndex("column1")) 
    val column2 = cursor.getInt(cursor.getColumnIndex("column2")) 
} 
cursor.close()

最も難しいクエリ操作をマスターすると、残りの追加、変更、削除の操作はさらに簡単になります。まず、table1 にデータを追加する方法を見てみましょう。コードは次のとおりです。

val values = contentValuesOf("column1" to "text", "column2" to 1) contentResolver.insert(uri, values)

追加されるデータが引き続き ContentValues に組み立てられ、ContentResolver の insert() メソッドが呼び出され、Uri と ContentValues がパラメーターとして渡されることがわかります。

この新しく追加されたデータを更新して、column1 の値をクリアしたい場合は、ContentResolver の update() メソッドを使用できます。コードは次のとおりです。

val values = contentValuesOf("column1" to "") 
contentResolver.update(uri, values, "column1 = ? and column2 = ?", arrayOf("text", "1")) 

上記のコードでは、selection パラメーターとselectionArgs パラメーターを使用して更新されるデータを制約し、すべての行が影響を受けないようにすることに注意してください。最後に、ContentResolver の delete() メソッドを呼び出して、このデータ部分を削除できます。コードは次のとおりです。

contentResolver.delete(uri, "column2 = ?", arrayOf("1"))

使用

//<uses-permission android:name="android.permission.READ_CONTACTS" />

class MainActivity : AppCompatActivity() {
 private val contactsList = ArrayList<String>()
 private lateinit var adapter: ArrayAdapter<String>
 override fun onCreate(savedInstanceState: Bundle?) {
 super.onCreate(savedInstanceState)
 setContentView(R.layout.activity_main)
     adapter = ArrayAdapter(this, android.R.layout.simple_list_item_1, contactsList)
     contactsView.adapter = adapter
     if (ContextCompat.checkSelfPermission(this, Manifest.permission.READ_CONTACTS)
     != PackageManager.PERMISSION_GRANTED) {
     ActivityCompat.requestPermissions(this,
     arrayOf(Manifest.permission.READ_CONTACTS), 1)
 } else {
     readContacts()
 }
 }
 override fun onRequestPermissionsResult(requestCode: Int, permissions: Array<String>,
 grantResults: IntArray) {
 super.onRequestPermissionsResult(requestCode, permissions, grantResults)
     when (requestCode) {
     1 -> {
     if (grantResults.isNotEmpty()
     && grantResults[0] == PackageManager.PERMISSION_GRANTED) {
     readContacts()
 } else {
     Toast.makeText(this, "You denied the permission",
     Toast.LENGTH_SHORT).show()
 }
 }
 }
 }
 private fun readContacts() {
 // 查询联系人数据
     contentResolver.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI,
     null, null, null, null)?.apply {
     while (moveToNext()) {
     // 获取联系人姓名
     val displayName = getString(getColumnIndex(
     ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME))
     // 获取联系人手机号
     val number = getString(getColumnIndex(
     ContactsContract.CommonDataKinds.Phone.NUMBER))
     contactsList.add("$displayName\n$number")
 }
 adapter.notifyDataSetChanged()
     close()
 }
 }
}

 2 番目に、ContentProvider の使用

class MyProvider : ContentProvider() {
 override fun onCreate(): Boolean {
 return false
 }
 override fun query(uri: Uri, projection: Array<String>?, selection: String?,
 selectionArgs: Array<String>?, sortOrder: String?): Cursor? {
 return null
 }
 override fun insert(uri: Uri, values: ContentValues?): Uri? {
 return null
 }
 override fun update(uri: Uri, values: ContentValues?, selection: String?,
 selectionArgs: Array<String>?): Int {
 return 0
 }
 override fun delete(uri: Uri, selection: String?, selectionArgs: Array<String>?): Int {
 return 0
 }
 override fun getType(uri: Uri): String? {
 return null
 }
}

(1) onCreate()。ContentProvider が初期化されるときに呼び出されます。通常、データベースの作成やアップグレードなどの操作はここで完了します。true が返された場合は ContentProvider の初期化が成功したことを示し、false が返された場合は失敗したことを示します。

(2) クエリ()。ContentProvider からデータをクエリします。uri パラメータはクエリするテーブルを決定するために使用され、projection パラメータはクエリする列を決定するために使用され、selection パラメータとselectionArgs パラメータはクエリする行を制限するために使用され、sortOrder パラメータは結果を並べ替えるために使用されます。クエリ結果は Cursor オブジェクトに格納され、返されます。

(3) 挿入()。データを ContentProvider に追加します。uri パラメータは追加するテーブルを決定するために使用され、追加するデータはvaluesパラメータに格納されます。追加が完了すると、新しいレコードを表す URI が返されます。

(4) update()。ContentProvider 内の既存のデータを更新します。uri パラメータは、どのテーブルのデータを更新するかを決定するために使用されます。新しいデータは、values パラメータに保存されます。selection パラメータとselectionArgs パラメータは、更新する行を制約するために使用され、影響を受ける行の数が返されます。戻り値として。

(5) 削除()。ContentProvider からデータを削除します。uri パラメータは削除するテーブルのデータを決定するために使用され、selection パラメータとselectionArgs パラメータは削除する行を制限するために使用され、削除された行の数が戻り値として返されます。

(6) getType()。受信したコンテンツ URI に基づいて、対応する MIME タイプを返します。多くのメソッドにはパラメーター uri があり、このパラメーターは contentresolver の追加、削除、変更、およびクエリ メソッドを呼び出すときにも渡されます。次に、受信した URI パラメーターを解析し、呼び出し元がアクセスすると予想されるテーブルとデータを分析する必要があります。

おすすめ

転載: blog.csdn.net/m0_59482482/article/details/129718728