ContentProvider

来源:互联网 发布:淘宝商城童装男童装 编辑:程序博客网 时间:2024/06/08 15:36

简介

Content provider管理android以结构化方式存放的数据。他以相对安全的方式封装数据并且提供简易的处理机制。Content provider提供不同进程间数据交互的标准化接口。
当你准备取出content provider中的数据时,你需要获得一个和当前上下文相关的ContentResolver对象作为客户端。这个对象和一个继承至ContentProvider的provider对象相关联。provider从客户端接收请求并且返回结果。
如果你不准备和其他应用共享你的数据,你不需要自定义provider。但是,你需要实现provider以满足个性化搜索数据的需求。同时,当你拷贝和粘贴复杂数据或者文件到他人应用中时,也需要provider。
延伸阅读:

继承关系


当使用它时,需要实现如下方法:
  • onCreate() 初始化 provider
  • query(Uri, String[], String, String[], String) 返回数据给调用者
  • insert(Uri, ContentValues) 在 content provider中插入新的数据
  • update(Uri, ContentValues, String, String[]) 更新在content provider存在的数据
  • delete(Uri, String, String[]) 在content provider中删除数据
  • getType(Uri) 返回一个MIME类型的数据
    数据操作型方法可以在多线程中调用,并且是线程安全的。
    其他方法只在application的主线程中调用,并且要避免耗时操作。
    尽管必须实现这些方法,但你的代码没有做任何事情,除了返回预期的数据类型

什么情况下使用content provider

  • 提供复杂的数据或文件给其它应用程序
  • 允许使用者复制复杂的数据到其它app
  • 提供在搜索协议框架下的自定义搜索

建立provider

  • 为你的数据设计存储结构【文件类型||结构体类型】
  • 实现一个继承自ContentProvider的类和必要方法。此类作为数据与安卓系统之间的接口
  • 定义一个String【content URI】,它包含其内容的uri和列名。如果您希望供应商的应用程序来处理intents,还定义intents的actions, extras data, and flags.还需要声明权限。为此,应该用一个类来承载这些值

如何设计数据存储

content provider是一个存储结构化数据的接口,在创建接口它之前,你需要决定如何存储数据,你可以将数据存储为任何你想要的形式,还可以为其设计读写接口。
在安卓上可用的数据存储技术:SQLite、file
几点建议:
表格数据应该有主键(primary key)
如果需要存储图片或其他十分大的文件,将它的路径存入表中
Binary Large OBject (BLOB) 存储不同大小或结构的数据,例如protocol或json

设计content URI

content://<authority>/<path>/<id> 
content uri用于鉴别provider中的数据,它包括provider的名称和表名(文件名),可选的id部分指向表中单独的一行。在ContentProvider中的所有的数据访问函数都需要content uri作为参数,以便于确定访问的表、行、或者文件。
  • 所有者名称(authority):为避免冲突,命名规则遵循包名的命名规则,com.example.<appname>.provider.
  • 路径名(path):com.example.<appname>.provider/table1 and com.example.<appname>.provider/table2.
  • ID:加在uri的末尾content://com.example.app.provider/table3/1 
UriMatcher 或ContentUris提供类对uri更为方便的操作

实现ContentProvider

该ContentProvider的实例,管理结构化数据集,通过其他应用程序的处理请求。所有的访问形式最终都需要调用ContentResolver,然后调用的ContentProvider的具体方法来获取许可。
需覆盖开头所说的几个方法

实现query()

  • 必须返回一个游标对象(Cursor )或者抛出错误。
  • 使用了数据库存储数据,那么会很轻松的返回游标对象。
  • 查询结果为空也应该返回游标,同时在getCount() 中应该返回0。
  • 在查询过程中发生内部错误,返回null。
  • 如果不是使用数据库,使用一个Cursor的子类

实现insert()

  • 该方法主要用于向表中插入数据, 值由参数ContentValues提供。如果列名没有指定相应的值,则应该提供一个默认值。
  • 该方法返回一个content URI,该uri指向新添加的行

实现delete()

  • 该方法并没有在物理上删除数据。
  • 如果您使用了同步适配器,你应该考虑标记需要删除的行以“删除”标志,而不是真的删除的行。
  • 同步适配器可以检查删除的行,并在供应商删除之前从服务器上删除它们。

实现update() 

ContentValues 提供值,selectionselectionArgs选中和删除值,这可能会重用上面三个方法的代码。

实现onCreate()

安卓主线程直接调用,因此应该在此方法仅执行快速运转的初始化任务,并推迟数据库创建和数据加载,直到提供实际接收的数据的请求。

MIME Types

通过一个content uri来描述数据的类型
ContentProvider 中,有两个方法返回MIME types:getType()和getStreamTypes()
一些公共的MIME Types  http://www.iana.org/assignments/media-types/index.htm
构成:
类型:vnd
亚类型:单行 android.cursor.item/
              多行android.cursor.dir/
专用部分:vnd.<name>.<type>
name建议用公司名称或者包名,type建议用表名
一个完整的示例
vnd.android.cursor.dir/vnd.com.example.provider.table1

实现承载类

必须声明为public final
包含URIs, 列名, MIME types, 和其它属于provider 的元数据
官方示例 ContactsContract

provider标签元素

使用该标签在manifest 文件中声明一个provider,该标签包含以下信息
Authority (所有者名称)
Provider class name
Permissions
  • android:grantUriPermssions: 临时许可标志
  • android:permission: 单一provider读/写权限
  • android:readPermission: Provider读权限
  • android:writePermission: Provider写权限
启动和控制属性
  • android:enabled: Flag 允许系统启动provider
  • android:exported: Flag 允许其他 applications使用此 provider.
  • android:initOrder: The order in which this provider should be started, relative to other providers in the same process.
  • android:multiProcess: Flag allowing the system to start the provider in the same process as the calling client.
  • android:process:  运行provider的进程名称
  • android:syncable: Flag 该提供者的数据是与一个服务器上的数据进行同步的。
信息属性
  • android:icon:一个图标,该图标绘制在Settings > Apps > All的provider上
  • android:label: 一个label,显示在Settings > Apps > All的provider上
    来源: http://android-doc.com/guide/topics/providers/content-provider-creating.html#ProviderElement


Intents and Data Access

应用程序可以用一个Intent间接访问content provider,应用程序不调用任何ContentResolver的或ContentProvider的方法。相反,它会发送一个启动活动的intent,这往往是应用程序自己的provider。目标activity负责在ui上检索和显示数据。取决于在action中的intent,目标activity也可以提示用户更改provider提供的数据。在intent.extras方法中的数据会显示在ui界面上,用户可在provider修改这些数据之前修改它。
0 0
原创粉丝点击