【问题标题】:How to programatically delete a native contact using the contact number in android?如何使用android中的联系人号码以编程方式删除本机联系人?
【发布时间】:2020-06-23 08:19:26
【问题描述】:

我需要仅使用 MSISDN 从本地联系人列表中删除联系人。目前,我正在查看所有联系人并在号码上进行匹配以获取名称。有没有更有效的方法来做到这一点?

这是我的代码:

获取所有本地联系人:

override fun nativeContactList(): Single<List<NativeContact>> {
    val contacts = ArrayList<NativeContact>()
    val cursor = context.contentResolver.query(ContactsContract.CommonDataKinds.Phone.CONTENT_URI, projection, null,
            null, ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME + " ASC")
    val normalizedNumbersAlreadyFound = HashSet<String>();
    val indexOfNormalizedNumber = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NORMALIZED_NUMBER)
    val indexOfDisplayName = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.DISPLAY_NAME)
    val indexOfDisplayNumber = cursor.getColumnIndex(ContactsContract.CommonDataKinds.Phone.NUMBER)
    cursor.use { cursor ->
        while (cursor.moveToNext()) {
            val normalizedNumber = cursor.getString(indexOfNormalizedNumber)
            if (normalizedNumbersAlreadyFound.add(normalizedNumber)) {
                val displayName = cursor.getString(indexOfDisplayName)
                val displayNumber = cursor.getString(indexOfDisplayNumber)
                Timber.d("Existing contact: $displayName $displayNumber")
                contacts.add(NativeContact(displayName, displayNumber, null, null))
            }
        }
        cursor.close()
    }
    return Single.fromCallable {
        contacts
    }
}

获得本地联系人列表后,我会遍历该列表并查找匹配项以获取名称:

   Observable.fromIterable(nativeContacts)
            .subscribeOn(processScheduler)
            .subscribe(object : DisposableObserver<NativeContact>() {
                override fun onComplete() {
                    Timber.d("Finished going thorough contacts")
                }


                override fun onError(e: Throwable) {
                    Timber.d("Warning: exception occurred while looping through native contacts list")
                }

                override fun onNext(nativeContact: NativeContact) {
                    if (contactToDelete.number == nativeContact.phoneNumber) {
                        contactToDelete.firstName = nativeContact.name
                        deprovisionContact(contactToDelete)
                    }
                }

            })

在我有了姓名和号码后,我删除了联系人:

        public Completable deleteContact(final ContactToDelete contactToDelete) {
        return Completable.fromAction(new Action() {
            @Override
            public void run() throws Exception {
                Timber.d("Attempting to delete " + contactToDelete.getNumber() + " " + contactToDelete.getName());
                Uri contactUri = Uri.withAppendedPath(ContactsContract.PhoneLookup.CONTENT_FILTER_URI, Uri.encode(contactToDelete.getNumber()));
                Cursor cursor = context.getContentResolver().query(contactUri, null, null, null, null);
                try {
                    if (cursor.moveToFirst()) {
                        do {
String name = contactToDelete.getName();
  if (cursor.getString(cursor.getColumnIndex(ContactsContract.PhoneLookup.DISPLAY_NAME)).equalsIgnoreCase(name)) {
                                String lookupKey = cursor.getString(cursor.getColumnIndex(ContactsContract.Contacts.LOOKUP_KEY));
                                Uri uri = Uri.withAppendedPath(ContactsContract.Contacts.CONTENT_LOOKUP_URI, lookupKey);
                                context.getContentResolver().delete(uri, null, null);
                                Timber.d("deleted " + contactToDelete.getNumber() + " " + contactToDelete.getName());
                            }

                        } while (cursor.moveToNext());
                    }

                } catch (Exception e) {
                    Timber.e("Error while attempting to delete contact " + e.getMessage());
                } finally {
                    cursor.close();
                }
            }
        });
    }

有没有更有效的方法来做到这一点?即每次我们要删除联系人时不要循环访问联系人列表?提前谢谢你。

【问题讨论】:

    标签: android mobile android-contacts


    【解决方案1】:

    我在这里发现了一些问题。

    1. 首先您的要求不明确,您是要删除所有包含此电话号码的联系人吗?电话号码不是唯一标识符,它可以被多个联系人共享,您应该删除所有这些联系人吗?

    2. 您要遍历所有联系人只是为了获得姓名?为什么删除联系人需要一个名字,这也是一个非唯一标识符,可能有多个联系人具有相同的名字和相同的号码。

    3. 你在这里做了太多的步骤,我看你已经熟悉 PHONE_LOOKUP 表,你只需要使用它来删除具有请求电话号码的联系人。

    代码示例(未测试):

    // get all contact-ids of all deletion candidates
    Uri uri = Uri.withAppendedPath(PhoneLookup.CONTENT_FILTER_URI, Uri.encode(phoneNumber));
    String[] projection = new String[]{ PhoneLookup.CONTACT_ID };
    Cursor idsCursor = resolver.query(uri, projection, null, null, null); 
    
    // iterate the cursor and delete all the contact-ids one-by-one
    while (idsCursor != null && idsCursor.moveToNext()) {
        Long contactId = idsCursor.getLong(0);
        Uri contactUri = ContentUris.withAppendedId(ContactsContract.Contacts.CONTENT_URI, contactId);
        context.getContentResolver().delete(contactUri, null, null);
    }
    if (idsCursor != null) {
        idsCursor.close();
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-09-19
      • 2016-12-26
      • 2013-01-24
      • 2014-02-14
      相关资源
      最近更新 更多