优发网页登录:详解android Content Provider6

创建一个ContentProvidercontentprovider治理对中央数据仓库的存取。你实现一个provider,便是在一个Android利用中实现一个或多个类,再加上manifest文件中的一些元素。你实现一个ContentProvide


当前位置: 主页 >优发网页登录


创建一个Content Provider

content provider治理对中央数据仓库的存取。你实现一个provider,便是在一个Android利用中实现一个或多个类,再加上manifest文件中的一些元素。你实现一个 ContentProvider的子类,它作为你的provider和其它应也之间的接口。只管content providers的目的是向其它利用供给数据,但当然也可以在你自己的利用中创建activity来容许用户来查询和改动你的provider所治理的数据。

创建之前的筹备事情

在创建一个provider之前,需做以下事情:

1. 确定你是否必要一个content provider。你假如必要供给一个或多个下列特点,你就需创建一个content provider:

你想向其它利用供给繁杂数据或文件。

你想让用护从你的利用复制繁杂的数据到其它利用。

你想应用搜索框架供给自定义的搜索建议。

假如完全是在你的利用内部应用,你的provider不需应用 SQLite数据库。

2. 假如你还未作出抉择,请涉猎主题 Content Provider Basics 来进一步懂得provider。

下一步,按以下步骤来创建你的provider:

1. 为你的数据设计原始存储要领。一个content provider以两种要领供给数据:

文件数据

指那存储在文件中的数据,比如图片,视频,音频等。把文件们存储在你的利用的私有空间。为相应从其它利用发来的对某个文件的哀求,你的provider可以为文件供给一个句柄。

"布局化" 数据

指那些存储于数据库中的数据、数组或小型布局。数据以兼容于表的形式存储。一行代表一条数据,就像一小我员或条款清单中的一条。一列代表一条数据中的一部分数据,比如人的名字或条款的价格。存储这些类型的数据的一个常用措施是应用SQLite数据库,然则你也可以应用其它形式。要懂得android 系统中更多的存储要领,见 设计数据存储一节。

2. 详细定义ContentProvider 类和它的措施。此类是你的数据与Android系统中其它器械的接口。要进一步懂得此类,见实现ContentProvider类 一节。

3. 定义provider的authority字符串,content URIs,和列的名字。假如你想让provider的利用场置惩罚intent,还要定义intent 的action、附加数据和标志。还要定义对那些要造访你的数据的利用所需具有的权限。你应该斟酌把优发网页登录这些值作为左券定义到别的一个零丁的左券类中。今后就可以向其它的开拓者展示这个类。更多关于content URI的信息,见 设计Content URI.一节。更多关于intent的信息,见Intent和数据操作一节。

4. 添加其它可选内容,比如样本数据或实现 AbstractThreadedSyncAdapter 以实现provider和基于云的数据之间的数据同步。

定义数据存储

一个content provider是一个布局化存储的数据接口。在你创建这个接口之前,你必须确定如若何存储数据。你可以以任何你爱好的要领存储数据,然后设计读写数据的接口。

下面是一些在android中可用的数据存储技巧:

1 Android系统中包孕一个 SQLite数据库API,Android自己的provider应用它来存储表格类的数据。SQLiteOpenHelper类赞助你优发网页登录创建数据库,而类SQLiteDatabase是操作数据库的根基类。

记着你不是必须应用一个数据库来实现你的数据仓库。一个 provider在外部的体现就像一个表的聚拢,类似于一个关系型数据库,然则provider的内部实现是可以与此不合的。

2 对付数据存储,Android具有各类各样的面向文件的API。要更多的懂得文件存储,请涉猎主题数据存储。假如你 设计的provider要供给媒体相关的数据,比如音频和视频,你可以在provider中将表数据和文件混杂来应用。

3 要处置惩罚收集数据,应应用java.net 和 android.net中的类。你也可以同步收集数据到本地数据存储中(比如数据库中),然后以表或文件的形式供给此数据。例子Sample Sync Adapter 演示了这种同步技巧。

思虑数据设计

下面是一些设计你的provider的数据布局的技术:

1 表数据应老是具有一个"主键"列,它被用于治理一个代表每各行的独一数值。你可以应用这个值链接某行到其它表中的相关行 (也便是"外键")。只管你可以为此列取任何名字,但应用BaseColumns._I优发网页登录D 才是最佳选择,由于当把一个provider的查询结果关联到一个 ListView 时,必要有一个列叫做 _ID。

2 假如你想供给位图图像或其它的异常大年夜的面向文件的数据,那么应把它存于文件中,然后间接的供给它,而不是直接把数据存储于一个表中。假如你这样做了,你还必要奉告你的provider的用户,他们必要应用一个ContentResolver 的文件措施来操作数据。

3用大年夜二进制工具 (BLOB)数据类型来存储大年夜小不定或没有固定布局的数据。例如,你可以应用一个 BLOB列来存储 协议缓冲 或 JSON 布局。

你也可以应用一个BLOB来实现一个自力模式的表。在此种表中,你定义一个主键列,一个MIME类型列,和一个或多个通俗的BLOB列。在 BLOB 列中的数据的意义由MIME列中的值所注解。这使你可以在一个表的各行中存储不合类型的数据。联系人Provider的"data"表ContactsContract.Data ,便是一个自力模式表的例子。

设计内容URIs

一个内容URI 标志一个provider中的数据。内容URI包孕了全部provider (他的 authority)的符号名和一个指向某个表或文件的名字。可选的id部分指向表中的一个自力的行。ContentProvider 的每个数据操作措施具有一个内容URI作为一个参数;这容许你抉摘要操作的表,行或文件。

内容URI的根基在标题Content Provider根基 中被描述。

设计一个authority

一个provider平日具有单个authority,这作为它的安卓内部名字。为了避免与其它provider冲突,你应该应用互联网域名要领取名 (不过是倒着的)来作为你的provider authority的根基名字。由于此种建议也用于Android包的名字,以是你可以定义你的provider authority作为包孕此provider的包名的扩展。 例如,假如你的Android包名是 com.example.,你应为你的provider authority命名为 com.example..provider。

定义一个路径布局

开拓者平日经由过程添加指向自力表的路径来从authority 创建content URI。例如,假如你具有两个表 table1和table2,你早年面例子中的authority 合并出来的内容 URI为 com.example..provider/table1 和com.example..provider/table2。路径中并不限定只有一个参数,并且路径的每一层也不是必须是一个表。

处置惩罚内容URI的 ID

为了方便,provider吸收把一行的ID放在URI的尾部来供给对表中某一行的造访。同样为了方便,provider对照此 ID和表的_ID列,然后履行对匹配行的操作哀求。.

这种方便性有助于在利用操作一个provider时应用一种通用的设计模式。利用向provider发出查询然后在一个ListView 中应用一个CursorAdapter 显示结果 Cursor 。CursorAdapter 的定义必要Cursor 中有一个列叫做 _ID 。

用户之后就可以在UI中显示的行中选择一行进行查看或改动数据。app之后从ListView 背后的Cursor 中得到响应的行,再得到行的 _ID值,把此值添加到内容URI上,再把操作哀求发送给provider。provider之后就履行查询或改动用户所指定的行。

内容URI的模式

为了帮你跟据到达的内容URI 选摘要履行的动作,provider API包孕了简便的类UriMatcher,它映射内容URI 的"模式" 到一个整数值。你可以在一个switch 语句中应用这个整数值来选择为匹配一种模式的某个内容URI或多个URI们履行某种动作。

一个内容 URI应用通配符来匹配其它内容URI们:

*: 匹配随意率性长度的随意率性有效字符串。

#: 匹配由数字组成的随意率性长度的字符串。

看一个设计和编码处置惩罚content URI的例子,假设一个provider其authority是 com.example.app.provider ,从它可以识别以下指向各表的内容URI:

1content://com.example.app.provider/table1: 一个叫table1 的表。

2content://com.example.app.provider/table2/dataset1: 一个叫dataset1 的表。

3content://com.example.app.provider/table2/dataset2: 一个叫dataset2 的表。

4content://com.example.app.provider/table3: 一个叫做table3 的表。

provider也识别那些具有一行的ID的内容URI,例如 content://com.example.app.provider/table3/1 指向表table3中的行1.

下面的内容 URI 模式也可能呈现:

conte优发网页登录nt://com.example.app.provider/*

匹配provider 中的义务内容URI。

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

匹配表dataset1和表dataset2中的一个内容URI,然则不匹配table1或table3中的内容URI。

content://com.example.app.provider/table3/#: 匹配表 table3 中的随意率性一行,比如content://com.example.app.provider/table3/6 指向行6.

下面的代码片段演示了UriMatcher 中的措施们若何事情。此代码经由过程应用内容URI模式content:///

指向表,用content:///

/ 指向一个零丁行,以不合的要领来处置惩罚指向全部表的 URI和指向单行的URI 。

措施addURI() 映射一个authority和路径到一个整数值。措施android.content.UriMatcher#match(Uri) match()} 返回一个URI对应的整数值。一个switch 语句从查询全部表和查询单笔记录之间作出选择:

public class ExampleProvider extends ContentProvider {

...// 创建一个UriMatcher工具

private static final UriMatcher sUriMatcher;...

/** 到这里,是对addURI()的调用。provider应能识别所有的内容URI的模式。

* 但在此片段中,只演示对表3的调用。*/

.../*

* 映射表3中的多行模式为1 。留意路径中没有用通配符。*/

sUriMatcher.addURI("com.example.app.provider", "table3", 1);/*

* 映射单行模式为2 。 此例中,通配符"#"被使也。* "content://com.example.app.provider/table3/3" 能匹配此模式,然则

* "content://com.example.app.provider/table3就不能了。*/

sUriMatcher.addURI("com.example.app.provider", "table3/#", 2);...

// 实现ContentProvider.query()public Cursor query(

Uri uri,String[] projection,

String selection,String[] selectionArgs,

String sortOrder) {...

/** 选择一个要查询的表并跟据为输入URI返回的代码来选择排序顺序。

* 这里也是只演示表3 。*/

switch (sUriMatcher.match(uri)) {// 假如输入URI指向全部表3

case优发网页登录 1:if (TextUtils.isEmpty(sortOrder)) sortOrder = "_ID ASC";

break;// 假如输入URI指向单行

case 2:/*

* 由于这个URI指向单行,以是_ID部分就呈现了。* 从URI获取着末着末面的路径段;它便是_ID值。

* 然后,添加这个值到查询语句的WHERE子语句中。*/

selection = selection + "_ID = " uri.getLastPathSegment();break;

default:...

// 假如URI不能被识别,你应该在此处做一些差错处置惩罚。}

// 调用进行实际查询的代码}

另一个类,ContentUris, 供给处置惩罚内容URI中的id部分的简便措施。类Uri 和 Uri.Builder 包孕了阐发已存在的Uri 工具和创建瓯新工具的简便措施。

转自:http://blog.csdn.net/nkmnkm/article/details/8088127

发表评论
加载中...

相关文章