android -- Contacts 保存联系人

       前些日子出于帮忙完成一个小小的需求,折腾下android 4.0 Contact的代码,正好也了解下Contact的业务流程。主要是联系人的增 删改查,很 眼熟是不,应用大部分的任务都是围绕怎么获取数据获取、如何显示数据和保存修改数据进行的,联系人也不例外,而且把握数据的 流向变化也算是分析应用的一个途 径吧,同时数据的变化也在一点程度上表现了业务的流程。其实联系人并不是复杂只是作为一个手机的核心级应用(手机本身还要用 来与人联系的,以此看来 手机就是一个移动名片库),与之交互的应用的多了些,导致需要考虑的东西琐碎了些。废话多了,还是看 代码吧,以保存联系人为例
当然是基于android 4.0的代码。

       Contacts应用对应的proivder是ContactsProivder2,数据库则是data/data/com.android.providers.contacts目录下 contacts2.db,里面的表不少 暂时们只关心三张表 raw_contacts表、 contacts表和data表。
       三张表的联系:raw_contacts表里用 contact_id字段关联 contacts表、 字段raw_contact_id 关联data表,
       三张表存储的主要内容:raw_contacts表存储了联系人的姓名、姓名的字母索引和帐户类型信息(区别是本机号码还是 SIM卡号码),
                                             data表存储了联系人的号码、邮件、IM等数据,
                                             contacts表存储联系人lookup(可以理解为类似Id的功能,查找联 系人的关键)。
      这里要补充下 Contacts应用的建表代码在ContactsDatabaseHelper.java,你 会在源码中发下面的语句,除了建表,还有创建对应视图和索引。
        createContactsViews(db);
        createGroupsView(db);
        createContactsTriggers(db);
        createContactsIndexes(db);
       实际查询中我们也是对视图进行操作的,在联系人的主界面PeopleActivity.java(在2.3的代码里是ContactlistActivity.java)所 用到数据就是从视图view_contacts查到的,这个视图view_contacts在createContactsViews(db)函数里创建。这就意味着如果想给 联系人数据库新增一个字段供界面使用,仅修改对应的表结构是不行,还要修改对应的视图才能得到想要的效果。     

       回到文章开始保存联系人,界面上的数据通过一个map集合传到provider执行插入insert,由于保存一个联系人信息需要写入多 张表,每次所使用的Uri不同所保存的值也不同,所以在上层应用采用了批量操作,类似下面的代码
ContentResolver resolver = getContext().getContentResolver();
        ArrayList<ContentProviderOperation> operations = new ArrayList<ContentProviderOperation>();
        ContentProviderOperation operations);= ContentProviderOperation.newInsert(uri)
            .withValue("account_name", null).build();
        operations.addoperations);
       resolver.applyBatch("com.android.contacts", operations);
        其实就是把所有动作放在一个事务里执行,先调用insertRawContact(),再insertData(),看网上大部分给出保存的例子一般就提到 这两个表对就应的uri,一个是 uri = Uri.parse("content://com.android.contacts/raw_contacts");一个是uri = Uri.parse ("content://com.android.contacts/data"); 不过通过前面的分析知道还有contacts表的信息没有写,它才是查询界面PeopleActivity.java的数据主角, 要是有个insertContacts函数就好了,没错还真有,不过看了代码就失望了。
    private long insertContact(ContentValues values) {
        throw new UnsupportedOperationException("Aggregate contacts are created automatically");
    }
     要是代码真走这里了,那就是一个异常,所以肯定不在这里了。真正的Contacts表写入在这里
   public long onRawContactInsert(
            TransactionContext txContext, SQLiteDatabase db, long rawContactId) {
        long contactId = insertContact(db, rawContactId);
        setContactId(rawContactId, contactId);
        mDbHelper.updateContactVisible(txContext, contactId);
        return contactId;
    }

   public long insertContact(SQLiteDatabase db, long rawContactId) {
        mSelectionArgs1[0] = String.valueOf(rawContactId);
        computeAggregateData(db, mRawContactsQueryByRawContactId, mSelectionArgs1, mContactInsert);//看这个函数就明白了
        return mContactInsert.executeInsert();
    }
       上面写入Contacts表的操作对应用层来说是透明的,所以应用层只需要知道raw_contacts表和data表对应的URI就好了,不过对于我们还是要弄清楚联系人保存的完整流程才好,网上大部分的文章对此并未说明,这也是写此文的一个原因,具体写contacts表的过程看看上面加粗的函数就清楚了,这里就不写了,短文也到此结束。有关contact的其它细节欢迎留言一起探讨。

  • 0
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值