أخبار المنتجات
أداة اختيار جهات الاتصال: مشاركة جهات الاتصال مع الحفاظ على الخصوصية
قراءة لمدة 4 دقائق
تظل الخصوصية وتحكّم المستخدم في صميم تجربة Android. وكما سهّلت أداة اختيار الصور مشاركة الوسائط بشكل آمن وسهل التنفيذ، فإنّنا نوفّر الآن مستوى الخصوصية والبساطة وتجربة المستخدم الرائعة نفسها عند اختيار جهات الاتصال.
معيار جديد لخصوصية جهات الاتصال
في السابق، كانت التطبيقات التي تتطلّب الوصول إلى جهات اتصال مستخدم معيّن تعتمد على إذن READ_CONTACTS العام. وعلى الرغم من أنّ هذا الأسلوب كان فعّالاً، إلا أنّه غالبًا ما كان يمنح التطبيقات بيانات أكثر من اللازم. تغيّر ميزة "منتقي جهات الاتصال في Android" الجديدة، التي تم طرحها في الإصدار 17 من نظام التشغيل Android، هذه الديناميكية من خلال توفير واجهة موحّدة وآمنة وقابلة للبحث لاختيار جهات الاتصال.
تتيح هذه الميزة للمستخدمين منح التطبيقات إذن الوصول إلى جهات الاتصال المحدّدة التي يختارونها فقط، ما يتوافق مع التزام Android بشفافية البيانات وتقليل آثار الأذونات.
طريقة العمل
يمكن للمطوّرين دمج "أداة اختيار جهات الاتصال" باستخدام الغرض Intent.ACTION_PICK_CONTACTS. توفّر واجهة برمجة التطبيقات المحدَّثة هذه العديد من الإمكانات الفعّالة:
- طلبات البيانات التفصيلية: يمكن للتطبيقات تحديد الحقول التي تحتاج إليها بالضبط، مثل أرقام الهواتف أو عناوين البريد الإلكتروني، بدلاً من تلقّي سجل جهة الاتصال بالكامل.
- إتاحة اختيار عناصر متعددة: يتيح لك المنتقي اختيار جهة اتصال واحدة أو عدة جهات، ما يمنح المطوّرين المزيد من المرونة في ميزات مثل دعوات المجموعات.
- حدود الاختيار: يمكن للمطوّرين وضع حدود مخصّصة لعدد جهات الاتصال التي يمكن للمستخدم اختيارها في المرة الواحدة.
- الوصول المؤقت: عند تحديد هذا الخيار، يعرض النظام معرّف موارد منتظم لجلسة يوفّر إذن وصول مؤقتًا للقراءة إلى البيانات المطلوبة، ما يضمن عدم استمرار الوصول لفترة أطول من اللازم.
- الوصول إلى الملفات الشخصية الأخرى: عند استخدام هذا الغرض الجديد، ستسمح الواجهة للمستخدمين باختيار محتوى من ملفات شخصية أخرى، مثل ملف العمل أو الملف المستنسخ أو المساحة الخاصة.
-
الأداء المحسّن: تعرض "أداة اختيار جهات الاتصال" Uri واحدًا يتيح طلب البحث عن النتائج بشكل جماعي، ما يغني عن الحاجة إلى طلب البحث عن Uri كل جهة اتصال على حدة كما هو مطلوب في
ACTION_PICK. تؤدي هذه الكفاءة إلى تقليل الحمل الزائد للنظام بشكل أكبر من خلال استخدام معاملةBinderواحدة.
التوافق مع الأنظمة القديمة والتنفيذ
بالنسبة إلى الأجهزة التي تعمل بالإصدار 17 من نظام التشغيل Android أو الإصدارات الأحدث، يرقّي النظام تلقائيًا الأغراض القديمة ACTION_PICK التي تحدّد أنواع بيانات جهات الاتصال إلى الواجهة الجديدة الأكثر أمانًا. ومع ذلك، للاستفادة الكاملة من الميزات المتقدّمة، مثل التحديد المتعدد، ننصح المطوّرين بتعديل رمز التنفيذ واستخدام ContentResolver للاستعلام عن معرّف الموارد المنتظم (URI) للجلسة الذي تم عرضه.
دمج "أداة اختيار جهات الاتصال" لدمج "أداة اختيار جهات الاتصال"، يستخدم المطوّرون الغرض ACTION_PICK_CONTACTS. في ما يلي مثال على الرمز البرمجي يوضّح كيفية تشغيل أداة الاختيار وطلب حقول بيانات معيّنة، مثل البريد الإلكتروني وأرقام الهواتف.
// State to hold the list of selected contacts var contacts by remember { mutableStateOf<List>(emptyList()) } // Launcher for the Contact Picker intent val pickContact = rememberLauncherForActivityResult(StartActivityForResult()) { if (it.resultCode == Activity.RESULT_OK) { val resultUri = it.data?.data ?: return@rememberLauncherForActivityResult // Process the result URI in a background thread coroutine.launch { contacts = processContactPickerResultUri(resultUri, context) } } } // Define the specific contact data fields you need val requestedFields = arrayListOf( Email.CONTENT_ITEM_TYPE, Phone.CONTENT_ITEM_TYPE, ) // Set up the intent for the Contact Picker val pickContactIntent = Intent(ACTION_PICK_CONTACTS).apply { putExtra(EXTRA_PICK_CONTACTS_SELECTION_LIMIT, 5) putStringArrayListExtra( EXTRA_PICK_CONTACTS_REQUESTED_DATA_FIELDS, requestedFields ) putExtra(EXTRA_PICK_CONTACTS_MATCH_ALL_DATA_FIELDS, false) } // Launch the picker pickContact.launch(pickContactIntent)
بعد أن يحدّد المستخدم خيارًا، يعالج التطبيق النتيجة من خلال طلب عنوان URI للجلسة الذي تم عرضه لاستخراج معلومات الاتصال المطلوبة.
// Data class representing a parsed Contact with selected details data class Contact(val id: String, val name: String, val email: String?, val phone: String?) // Helper function to query the content resolver with the URI returned by the Contact Picker. // Parses the cursor to extract contact details such as name, email, and phone number private suspend fun processContactPickerResultUri( sessionUri: Uri, context: Context ): List<Contact> = withContext(Dispatchers.IO) { // Define the columns we want to retrieve from the ContactPicker ContentProvider val projection = arrayOf( ContactsContract.Contacts._ID, ContactsContract.Contacts.DISPLAY_NAME_PRIMARY, ContactsContract.Data.MIMETYPE, // Type of data (e.g., email or phone) ContactsContract.Data.DATA1, // The actual data (Phone number / Email string) ) val results = mutableListOf<Contact>() // Note: The Contact Picker Session Uri doesn't support custom selection & selectionArgs. context.contentResolver.query(sessionUri, projection, null, null, null)?.use { cursor -> // Get the column indices for our requested projection val contactIdIdx = cursor.getColumnIndex(ContactsContract.Contacts._ID) val mimeTypeIdx = cursor.getColumnIndex(ContactsContract.Data.MIMETYPE) val nameIdx = cursor.getColumnIndex(ContactsContract.Contacts.DISPLAY_NAME_PRIMARY) val data1Idx = cursor.getColumnIndex(ContactsContract.Data.DATA1) while (cursor.moveToNext()) { val contactId = cursor.getString(contactIdIdx) val mimeType = cursor.getString(mimeTypeIdx) val name = cursor.getString(nameIdx) ?: "" val data1 = cursor.getString(data1Idx) ?: "" // Determine if the current row represents an email or a phone number val email = if (mimeType == Email.CONTENT_ITEM_TYPE) data1 else null val phone = if (mimeType == Phone.CONTENT_ITEM_TYPE) data1 else null // Add the parsed contact to our results list results.add(Contact(contactId, name, email, phone)) } } return@withContext results }
يمكنك الاطّلاع على المستندات الكاملة هنا.
أفضل الممارسات للمطوّرين
لتقديم أفضل تجربة للمستخدم والحفاظ على معايير الأمان العالية، ننصحك بما يلي:
- تقليل البيانات: لا تطلب سوى حقول البيانات المحدّدة التي يحتاجها تطبيقك (مثل البريد الإلكتروني).
- الاحتفاظ الفوري بالبيانات: الاحتفاظ بالبيانات المحدّدة على الفور، لأنّ إذن الوصول إلى معرّف الموارد المنتظم للجلسة مؤقت.
متابعة القراءة
-
أخبار المنتجات
"أداة اختيار الصور المضمّنة": طريقة أكثر سلاسة لطلب الصور والفيديوهات بشكل خاص في تطبيقك
Roxanna Aliabadi Walker, Yacine Rezgui • مدة القراءة: 8 دقائق
-
أخبار المنتجات
أصبح الإصدار 4 من استوديو Android Panda ثابتًا وجاهزًا للاستخدام في الإنتاج. يتضمّن هذا الإصدار "وضع التخطيط" و"توقّع التعديل التالي" والمزيد، ما يسهّل إنشاء تطبيقات Android عالية الجودة أكثر من أي وقت مضى.
Matt Dyor • مدة القراءة: 5 دقائق
-
أخبار المنتجات
إذا كنت من مطوّري تطبيقات Android وتتطلّع إلى دمج ميزات مبتكرة تستند إلى الذكاء الاصطناعي في تطبيقك، أطلقنا مؤخرًا تحديثات جديدة وفعّالة.
Thomas Ezan • قراءة لمدة 3 دقائق
البقاء على اطّلاع على آخر التحديثات
يمكنك تلقّي أحدث الإحصاءات حول تطوير تطبيقات Android في بريدك الوارد أسبوعيًا.