يمكن الوصول إلى واجهات برمجة التطبيقات للأجهزة من خلال واجهات برمجة التطبيقات لمنزل Google على Android. يُرجى استيراد هذه الحِزم إلى تطبيقك:
import com.google.home.Home
import com.google.home.HomeDevice
import com.google.home.Id
لاستخدام أنواع أو سمات أجهزة معيّنة مع واجهات برمجة التطبيقات للأجهزة، يجب استيرادها بشكل فردي.
على سبيل المثال، لاستخدام سمة On/Off Matter ونوع الجهاز On/Off Plug-in Unit، استورِد الحِزم التالية إلى تطبيقك:
import com.google.home.matter.standard.OnOff
import com.google.home.matter.standard.OnOffPluginUnitDevice
لمزيد من المعلومات، يُرجى الاطّلاع على نموذج البيانات على Android.
معالجة الأخطاء
يمكن لأي طريقة في واجهات برمجة التطبيقات لمنزل Google طرح
HomeException، لذا ننصحك باستخدام كتلة try-catch لرصد
HomeException في جميع الطلبات.
عند معالجة HomeException، تحقَّق من الحقلَين
error.code و
error.message لمعرفة المشكلة. قد تكون هناك رموز أخطاء فرعية
أيضًا، لذا استدعِ طريقة
getSubErrorCodes() وتحقَّق من النتيجة.
ستؤدي أي استثناءات لم تتم معالجتها إلى تعطُّل تطبيقك.
لمزيد من المعلومات، يُرجى الاطّلاع على معالجة الأخطاء.
يمكنك الاطّلاع على إرسال أمر إلى جهاز للحصول على مثال.
نماذج الطلبات
الحصول على قائمة بالأجهزة
بعد الحصول على مرجع إلى مثيل Structure، يعرض طلب devices() عنصر Flow للأجهزة التي يمكنك الوصول إليها من هذا البنية:
// Get a flow of all devices accessible to the user val allDevicesFlow: HomeObjectsFlow<HomeDevice> = home.devices() // Calling list() on a HomeObjectsFlow returns the first Set of elements. val allDevices: Set<HomeDevice> = allDevicesFlow.list()
من هنا، يمكنك الوصول إلى حالات كل جهاز وإرسال أوامر إلى الأجهزة.
باستخدام الإصدار 1.8 من واجهات برمجة التطبيقات لمنزل Google، يمكنك أن تجعل واجهة برمجة التطبيقات تمثّل كل جهاز متعدد الأجزاء كجهاز واحد من خلال ضبط المعلمة enableMultipartDevices لطريقة devices() على true. لمزيد من
المعلومات، يُرجى الاطّلاع على
الأجهزة متعددة الأجزاء على Android.
قراءة حالة الجهاز
إليك مثال على التحقّق من سمة OnOff من سمة On/Off للجهاز. باستخدام نموذج بيانات سمة واجهات برمجة التطبيقات لمنزل Google، حيث يتم تحديد هذه السمة على أنّها OnOff، يمكنك استرداد بيانات السمة من خلال فئة standardTraits لنوع الجهاز:
// Assuming we have a device. val deviceFlow = home.devices().itemFlow(myDeviceId) val device = deviceFlow.first() // Get a flow of a standard trait on the type. distinctUntilChanged() is needed to only trigger // on the specific trait changes and not the whole type. val onOffTraitFlow: Flow<OnOff?> = device.type(DimmableLightDevice).map { it.standardTraits.onOff }.distinctUntilChanged() val onOffTrait: OnOff = onOffTraitFlow.first()!!
لمزيد من المعلومات عن دالة Kotlin flow، يُرجى الاطّلاع على
distinctUntilChanged.
إبطال حالة في اشتراك سمة
توفر واجهة TraitStateInvalidation إمكانية إبطال حالة تم استردادها من خلال الاشتراكات في جهاز الاختبار في الحالات التي لا يتم فيها الإبلاغ عن الحالة بشكل صحيح.
تشمل الأمثلة على الحالات التي قد لا يتم فيها الإبلاغ عن الحالة بشكل صحيح استخدام السمات في سمات Matter بجودة "C" أو بسبب تنفيذ الجهاز الذي يؤدي بشكل غير متوقّع إلى حدوث المشكلة.
تُصدر واجهة برمجة التطبيقات هذه قراءة إجبارية لحالة السمة الحالية وتعرض النتيجة من خلال تدفقات السمات الحالية.
احصل على السمة، ثم شغِّل forceRead على السمة:
val onOffTrait = device.?type(DimmableLightDevice)?.map{it.trait(OnOff)}.first()
onOffTrait.forceRead()
الحصول على قائمة بسمات نوع الجهاز
يجب استخدام أنواع الأجهزة كنقطة دخول لقراءة السمات، لأنّها تقسم الجهاز إلى أجزائه الوظيفية (مثل نقاط النهاية في Matter).
تأخذ أنواع الأجهزة أيضًا في الاعتبار تعارضات السمات في حال كان الجهاز يتضمّن نوعَي جهاز، قد يكون لكل منهما السمة نفسها. على سبيل المثال، إذا كان الجهاز مكبّر صوت ومصباحًا قابلاً للتعتيم، سيكون له سمتان On/Off وسمتان للتحكّم في المستوى.
للحصول على قائمة بالسمات المتاحة لنوع الجهاز Dimmable Light:
// Get all types available on this device. Requires the types to be part of the registry during // SDK initialization. val typesFlow: Flow<Set<DeviceType>> = device.types() // Get a snapshot of all types. val types: Set<DeviceType> = typesFlow.first() // Get the DimmableLightDevice instance from the set of types. val dimmableLightDevice = types.filterIsInstance<DimmableLightDevice>().firstOrNull() // Get all traits in the type + traits registered val allTraits: Set<Trait> = dimmableLightDevice!!.traits()
يمكن أن يحدث نوع آخر من تعارض السمات عندما يكون للجهاز سمتان بالاسم نفسه. على سبيل المثال، يمكن أن يشير onOff إلى مثيل من سمة OnOff العادية، أو يمكن أن يشير إلى مثيل من سمة OnOff التي يحدّدها المصنّع. لإزالة أي غموض محتمل بشأن السمة المقصودة، يجب أن يكون مثيل Trait الذي تتم الإشارة إليه من خلال جهاز مسبوقًا بمساحة اسم مؤهِّلة. بالنسبة إلى السمات العادية، أي تلك المشابهة لـ
Matter المجموعات العادية، استخدِم standardTraits. بالنسبة إلى سمات Google، استخدِم googleTraits:
// Accessing standard traits on the type. val onOffTrait: OnOff? = dimmableLightDevice.standardTraits.onOff val levelControlTrait: LevelControl? = dimmableLightDevice.standardTraits.levelControl
للوصول إلى سمة خاصة بالمصنّع، أشِر إليها مباشرةً:
// Accessing a custom trait on the type. val customTrait = dimmableLightDevice.trait(MyCustomTrait)
الحصول على قائمة بالأجهزة التي تتضمّن سمة معيّنة
يمكن استخدام دالة
filter
في Kotlin لزيادة تحسين طلبات واجهة برمجة التطبيقات. على سبيل المثال، للحصول على قائمة بالأجهزة في المنزل التي تتضمّن جميعها سمة On/Off:
// Get all devices that support OnOff val onOffDevices: Flow<List<HomeDevice>> = home.devices().map { devices -> devices.filter { it.has(OnOff) } }
يُرجى الاطّلاع على واجهة Trait للحصول على قائمة كاملة بالسمات المتاحة في واجهات برمجة التطبيقات لمنزل Google.
الحصول على قائمة بالأجهزة التي تتضمّن أنواع أجهزة مماثلة
للحصول على قائمة بالأجهزة التي تمثّل جميع المصابيح في المنزل:
// Get a list of devices with similar device types (lights) val lightDevices = home.devices().map { devices -> devices.filter { it.has(DimmableLightDevice) || it.has(OnOffLightDevice) || it.has(ColorTemperatureLightDevice) || it.has(ExtendedColorLightDevice) } }
تتوفّر أنواع أجهزة متعددة في واجهات برمجة التطبيقات لمنزل Google يمكن أن تمثّل نوع جهاز أساسي. على سبيل المثال، لا يتوفّر نوع الجهاز "Light". بدلاً من ذلك، تتوفّر أربعة أنواع أجهزة مختلفة يمكن أن تمثّل مصباحًا، كما هو موضّح في المثال السابق. للحصول على عرض شامل لنوع الجهاز ذي المستوى الأعلى في المنزل، يجب تضمين أنواع أجهزة متعددة في التدفقات التي تم فلترتها.
يُرجى الاطّلاع على واجهة DeviceType للحصول على قائمة كاملة بأنواع الأجهزة المتاحة في واجهات برمجة التطبيقات لمنزل Google.
الحصول على رقم تعريف المورِّد أو رقم تعريف المنتج لجهاز
تتضمّن BasicInformation
السمة معلومات مثل رقم تعريف المورِّد ورقم تعريف المنتج واسم المنتج والرقم التسلسلي للجهاز:
// Get device basic information. All general information traits are on the RootNodeDevice type. val basicInformation = device.type(RootNodeDevice).first().standardTraits.basicInformation!! println("vendorName ${basicInformation.vendorName}") println("vendorId ${basicInformation.vendorId}") println("productId ${basicInformation.productId}")
تحديد الأجهزة من السحابة الإلكترونية إلى السحابة الإلكترونية لمصنّعي الأجهزة
إذا كنت صانع أجهزة وتنشئ أجهزة Cloud-to-cloud،
لتحديد أجهزتك
Cloud-to-cloud من خلال السمة
BasicInformation، يمكنك تضمين حقول السلسلة هذه في
استجابة SYNC الخاصة بها:
رقم تعريف المورِّد الذي أصدره Connectivity Standards Alliance (Alliance)
"matterOriginalVendorId": "0xfff1",معرّف المنتج الذي يحدّد منتجًا فريدًا لأحد المورِّدين:
"matterOriginalProductId": "0x1234",معرّف فريد للجهاز، يتم إنشاؤه بطريقة خاصة بالمصنّع:
"matterUniqueId": "matter-device-id",
عند إدخال حقول السلسلة هذه، استخدِم أرقام تعريف Matter
المورِّد والمنتج إذا كانت متوفّرة لديك. إذا لم تكن عضوًا في
Alliance ولم يتم تخصيص أرقام التعريف هذه لك، يمكنك
ترك الحقلَين matterOriginalVendorId وmatterOriginalProductId فارغَين
وتقديم matterUniqueId كمعرّف.
يوضّح مثال استجابة SYNC استخدام هذه الحقول:
{
"requestId": "ff36a3cc-ec34-11e6-b1a0-64510650abcf",
"payload": {
"agentUserId": "1836.15267389",
"devices": [
{
"id": "456",
"type": "action.devices.types.LIGHT",
"traits": [
"action.devices.traits.OnOff",
"action.devices.traits.Brightness",
"action.devices.traits.ColorSetting",
],
"willReportState": true,
"deviceInfo": { ... },
"matterOriginalVendorId": "0xfff1",
"matterOriginalProductId": "0x1234",
"matterUniqueId": "matter-device-id",
"otherDeviceIds": [
{
"deviceId": "local-device-id",
}
]
}
]
}
}
لمزيد من المعلومات، يُرجى الاطّلاع على مستندات
Cloud-to-cloud SYNC.
البيانات الوصفية للجهاز والسمة
تحتوي الأجهزة والسمات في واجهات برمجة التطبيقات لمنزل Google على بيانات وصفية مرتبطة بها، ما يمكن أن يساعد في إدارة تجربة المستخدم في أحد التطبيقات.
تحتوي كل سمة في واجهات برمجة التطبيقات لمنزل Google على السمة
sourceConnectivity
التي تتضمّن معلومات عن حالة السمة على الإنترنت وموقعها الجغرافي
(التوجيه المحلي أو عن بُعد).
الحصول على النوع الأساسي للجهاز
قد تعرض بعض الأجهزة أنواع أجهزة متعددة من خلال واجهات برمجة التطبيقات لمنزل Google. لضمان عرض الخيارات المناسبة للمستخدمين في أحد التطبيقات (مثل التحكّم في الجهاز وعمليات التشغيل الآلي المقترَحة) لأجهزتهم، من المفيد التحقّق من نوع الجهاز الأساسي للجهاز.
أولاً، احصل على نوع(أنواع) الجهاز باستخدام
type(),
ثم حدِّد النوع(الأنواع) الأساسي:
val types = device.types().first() val primaryTypes = types.filter { it.metadata.isPrimaryType }
التحقّق ممّا إذا كانت السمة متصلة بالإنترنت
استخدِم طريقة connectivityState() للتحقّق من اتصال السمة:
val onOffConnectivity = onOffTrait?.metadata?.sourceConnectivity?.connectivityState
قد تظهر بعض السمات، وعادةً ما تكون سمات Google smart home، غير متصلة بالإنترنت إذا لم يكن الجهاز متصلاً بالإنترنت. يرجع ذلك إلى أنّ هذه السمات مستندة إلى السحابة الإلكترونية وليس لها توجيه محلي.
التحقّق من الاتصال بجهاز
يتم في الواقع التحقّق من الاتصال بجهاز على مستوى نوع الجهاز لأنّ بعض الأجهزة تتيح استخدام أنواع أجهزة متعددة. الحالة المعروضة هي مزيج من حالات الاتصال لجميع السمات على هذا الجهاز.
val lightConnectivity = dimmableLightDevice.metadata.sourceConnectivity.connectivityState
قد تظهر حالة PARTIALLY_ONLINE في حالة أنواع الأجهزة المختلطة عندما لا يكون هناك اتصال بالإنترنت.
قد تظل سمات Matter العادية متصلة بالإنترنت بسبب التوجيه المحلي
، ولكن ستكون السمات المستندة إلى السحابة الإلكترونية غير متصلة بالإنترنت.
الحصول على عنوان IP للجهاز
للعثور على عنوان IP للجهاز، استخدِم السمة networkInterfaces لـ
الـ
GeneralDiagnostics
سمة. يتم عرض العناوين كمصفوفات بايت، يمكنك تنسيقها كسلاسل IPv4 أو IPv6 عادية:
val ipAddresses =
trait.networkInterfaces?.flatMap { networkInterface ->
(networkInterface.ipv4Addresses + networkInterface.ipv6Addresses).mapNotNull { bytes ->
try {
java.net.InetAddress.getByAddress(bytes).hostAddress
} catch (e: java.net.UnknownHostException) {
null
}
}
} ?: emptyList()
التحقّق من توجيه الشبكة لسمة
يتوفّر أيضًا الموقع الجغرافي لسمة في واجهات برمجة التطبيقات لمنزل Google. تشير dataSourceLocality إلى ما إذا كانت السمة يتم توجيهها عن بُعد (من خلال السحابة الإلكترونية) أو محليًا (من خلال مركز محلي) أو من نظير إلى نظير (مباشرةً من جهاز إلى جهاز، بدون مركز).
يمكن أن تكون قيمة الموقع الجغرافي غير المعروف UNSPECIFIED ممكنة، على سبيل المثال، أثناء بدء تشغيل أحد التطبيقات ولم يصل بعد إلى مركز أو خادم للاتصال بالجهاز. لا يمكن الوصول إلى هذه الأجهزة وستفشل طلبات التفاعل من الأوامر أو الأحداث. يقع على عاتق العميل تحديد كيفية التعامل مع هذه الأجهزة.
val onOffLocality = onOffTrait?.metadata?.sourceConnectivity?.dataSourceLocality
التحقّق من توجيه الشبكة لجهاز
على غرار الاتصال، يتم التحقّق من الموقع الجغرافي على مستوى نوع الجهاز. الحالة المعروضة هي مزيج من الموقع الجغرافي لجميع السمات على هذا الجهاز.
val lightLocality = dimmableLightDevice.metadata.sourceConnectivity.dataSourceLocality
قد تظهر حالة MIXED في سيناريو مشابه لحالة الاتصال PARTIALLY_ONLINE: بعض السمات مستندة إلى السحابة الإلكترونية بينما البعض الآخر محلي.
تغيير اسم الجهاز
استدعِ طريقة setName()
لتغيير اسم الجهاز:
mixerDevice.setName("Grendel")
سيتم اقتطاع الأسماء إذا تجاوزت الحدّ الأقصى لعدد نقاط رمز Unicode (الأحرف) البالغ 60 ولن يتم عرض أي أخطاء. يكون المطوّرون مسؤولين عن التعامل مع الأسماء الطويلة، ويمكنهم مثلاً تحديد ما إذا كانوا يريدون إبلاغ المستخدمين بأنّه سيتم اقتطاع الأسماء.