यह गाइड, Health Connect के 1.1.0-alpha12 वर्शन के साथ काम करती है.
इस गाइड में, Health Connect में डेटा सेव करने या अपडेट करने की प्रोसेस के बारे में बताया गया है.
शून्य वैल्यू को मैनेज करना
ऐसा हो सकता है कि कदमों की संख्या, दूरी या कैलोरी जैसे कुछ डेटा टाइप की वैल्यू 0 हो.
सिर्फ़ तब शून्य वैल्यू लिखें, जब उपयोगकर्ता ने डिवाइस पहना हो और वह किसी तरह की गतिविधि न कर रहा हो. अगर डिवाइस को नहीं पहना गया है, डेटा मौजूद नहीं है या बैटरी खत्म हो गई है, तो शून्य वैल्यू न लिखें. ऐसे मामलों में, गलत जानकारी से बचने के लिए रिकॉर्ड को शामिल न करें.
डेटा स्ट्रक्चर सेट अप करना
डेटा लिखने से पहले, हमें रिकॉर्ड सेट अप करने होंगे. 50 से ज़्यादा डेटा टाइप के लिए, हर डेटा टाइप का अपना स्ट्रक्चर होता है. उपलब्ध डेटा टाइप के बारे में ज़्यादा जानने के लिए, Jetpack का रेफ़रंस देखें.
बुनियादी रिकॉर्ड
Health Connect में कदम डेटा टाइप, यह जानकारी कैप्चर करता है कि किसी व्यक्ति ने दो रीडिंग के बीच कितने कदम चले. कदमों की संख्या, सेहत, फ़िटनेस, और वेलनेस प्लैटफ़ॉर्म पर एक सामान्य मेज़रमेंट होती है.
यहां दिए गए उदाहरण में, कदमों की संख्या का डेटा सेट करने का तरीका बताया गया है:
val zoneOffset = ZoneOffset.systemDefault().rules.getOffset(startTime) val stepsRecord = StepsRecord( count = 120, startTime = startTime, endTime = endTime, startZoneOffset = zoneOffset, endZoneOffset = zoneOffset, metadata = Metadata.autoRecorded( device = Device(type = Device.TYPE_WATCH) ) ) healthConnectClient.insertRecords(listOf(stepsRecord))
मेज़रमेंट की इकाइयों वाले रिकॉर्ड
Health Connect, वैल्यू को माप की इकाइयों के साथ सेव कर सकता है, ताकि सटीक जानकारी दी जा सके. पोषण डेटा टाइप इसका एक उदाहरण है. यह बहुत बड़ा और व्यापक है. इसमें पोषक तत्वों के कई वैकल्पिक फ़ील्ड शामिल हैं. इनमें कुल कार्बोहाइड्रेट से लेकर विटामिन तक शामिल हैं. हर डेटा पॉइंट, पोषक तत्वों के बारे में बताता है. ये पोषक तत्व, किसी खाने की चीज़ या खाने के हिस्से के तौर पर लिए गए हो सकते हैं.
इस डेटा टाइप में, सभी पोषक तत्वों को मास की इकाइयों में दिखाया जाता है. वहीं, energy को ऊर्जा की इकाई में दिखाया जाता है.
यहां दिए गए उदाहरण में, उस व्यक्ति के लिए पोषण का डेटा सेट करने का तरीका बताया गया है जिसने केला खाया है:
val endTime = Instant.now() val startTime = endTime.minus(Duration.ofMinutes(1)) val banana = NutritionRecord( name = "banana", energy = 105.0.kilocalories, dietaryFiber = 3.1.grams, potassium = 0.422.grams, totalCarbohydrate = 27.0.grams, totalFat = 0.4.grams, saturatedFat = 0.1.grams, sodium = 0.001.grams, sugar = 14.0.grams, vitaminB6 = 0.0005.grams, vitaminC = 0.0103.grams, startTime = startTime, endTime = endTime, startZoneOffset = ZoneOffset.UTC, endZoneOffset = ZoneOffset.UTC, metadata = Metadata.activelyRecorded( device = Device(type = Device.TYPE_PHONE) ) )
सीरीज़ के डेटा वाले रिकॉर्ड
Health Connect, सीरीज़ डेटा की सूची सेव कर सकता है. इसका एक उदाहरण, धड़कन की दर डेटा टाइप है. यह धड़कन के सैंपल की एक सीरीज़ को कैप्चर करता है. इन सैंपल का पता, रीडिंग के बीच लगाया जाता है.
इस डेटा टाइप में, पैरामीटर samples को दिल की धड़कन के सैंपल की सूची के तौर पर दिखाया जाता है. हर सैंपल में beatsPerMinute वैल्यू और time वैल्यू होती है.
यहां दिए गए उदाहरण में, धड़कन की दर सीरीज़ का डेटा सेट करने का तरीका बताया गया है:
val endTime = Instant.now() val startTime = endTime.minus(Duration.ofMinutes(5)) val heartRateRecord = HeartRateRecord( startTime = startTime, startZoneOffset = ZoneOffset.UTC, endTime = endTime, endZoneOffset = ZoneOffset.UTC, // records 10 arbitrary data, to replace with actual data samples = List(10) { index -> HeartRateRecord.Sample( time = startTime + Duration.ofSeconds(index.toLong()), beatsPerMinute = 100 + index.toLong(), ) }, metadata = Metadata.activelyRecorded( device = Device(type = Device.TYPE_WATCH) ))
उपयोगकर्ता से अनुमतियों का अनुरोध करना
क्लाइंट इंस्टेंस बनाने के बाद, आपके ऐप्लिकेशन को उपयोगकर्ता से अनुमतियों का अनुरोध करना होगा. उपयोगकर्ताओं के पास किसी भी समय अनुमतियां देने या अस्वीकार करने का विकल्प ज़रूर होना चाहिए. इसके लिए, ज़रूरी डेटा टाइप के लिए अनुमतियों का सेट बनाएं. पक्का करें कि सेट में मौजूद अनुमतियों का एलान, सबसे पहले आपके Android मेनिफ़ेस्ट में किया गया हो.
val permissions = setOf( HealthPermission.getReadPermission(HeartRateRecord::class), HealthPermission.getWritePermission(HeartRateRecord::class), HealthPermission.getReadPermission(StepsRecord::class), HealthPermission.getWritePermission(StepsRecord::class) )
getGrantedPermissions का इस्तेमाल करके देखें कि आपके ऐप्लिकेशन को ज़रूरी अनुमतियां पहले से मिली हुई हैं या नहीं. अगर ऐसा नहीं है, तो उन अनुमतियों का अनुरोध करने के लिए createRequestPermissionResultContract का इस्तेमाल करें. इससे Health Connect की अनुमतियों वाली स्क्रीन दिखती है.
val permissions = setOf( HealthPermission.getReadPermission(StepsRecord::class), HealthPermission.getWritePermission(StepsRecord::class), HealthPermission.getReadPermission(HeartRateRecord::class), HealthPermission.getWritePermission(HeartRateRecord::class) ) val requestPermissionsLauncher = rememberLauncherForActivityResult( contract = PermissionController.createRequestPermissionResultContract() ) { grantedPermissions -> if (grantedPermissions.containsAll(permissions)) { coroutineScope.launch { snackbarHostState.showSnackbar("Permissions granted!") } } else { coroutineScope.launch { snackbarHostState.showSnackbar("Permissions denied.") } } }
डेटा सेव करने की अनुमति दें
Health Connect में डेटा सेव करना एक सामान्य वर्कफ़्लो है. रिकॉर्ड जोड़ने के लिए, insertRecords का इस्तेमाल करें.
यहां दिए गए उदाहरण में, डेटा डालने के लिए कदमों की संख्या लिखने का तरीका बताया गया है:
val zoneOffset = ZoneOffset.systemDefault().rules.getOffset(startTime) val stepsRecord = StepsRecord( count = 120, startTime = startTime, endTime = endTime, startZoneOffset = zoneOffset, endZoneOffset = zoneOffset, metadata = Metadata.autoRecorded( device = Device(type = Device.TYPE_WATCH) ) ) healthConnectClient.insertRecords(listOf(stepsRecord))
डेटा अपडेट करना
अगर आपको एक या उससे ज़्यादा रिकॉर्ड में बदलाव करना है, तो अपने डेटा को अपडेट किया जा सकता है. ऐसा खास तौर पर तब करें, जब आपको अपने ऐप्लिकेशन के डेटा स्टोर को Health Connect के डेटा के साथ सिंक करना हो. मौजूदा डेटा को अपडेट करने के दो तरीके हैं. ये रिकॉर्ड ढूंढने के लिए इस्तेमाल किए गए आइडेंटिफ़ायर पर निर्भर करते हैं.
मेटाडेटा
सबसे पहले Metadata क्लास की जांच करना ज़रूरी है, क्योंकि डेटा अपडेट करते समय यह ज़रूरी होती है. Health Connect में हर Record बनाते समय, उसमें metadata फ़ील्ड होता है. सिंक करने के लिए, ये प्रॉपर्टी काम की हैं:
| प्रॉपर्टी | ब्यौरा |
|---|---|
id
|
Health Connect में मौजूद हर Record की एक यूनीक id वैल्यू होती है.नया रिकॉर्ड डालते समय, Health Connect इस फ़ील्ड में जानकारी अपने-आप भर देता है. |
lastModifiedTime
|
हर Record, रिकॉर्ड में पिछली बार किए गए बदलाव को भी ट्रैक करता है.Health Connect इस फ़ील्ड में डेटा अपने-आप भर देता है. |
clientRecordId
|
हर Record से एक यूनीक आईडी जुड़ा हो सकता है, ताकि आपके ऐप्लिकेशन के डेटास्टोर में उसे रेफ़रंस के तौर पर इस्तेमाल किया जा सके.
आपका ऐप्लिकेशन यह वैल्यू देता है. |
clientRecordVersion
|
जिस रिकॉर्ड में clientRecordId मौजूद है उसमें clientRecordVersion का इस्तेमाल किया जा सकता है. इससे डेटा को आपके ऐप्लिकेशन के डेटास्टोर में मौजूद वर्शन के साथ सिंक किया जा सकता है.आपका ऐप्लिकेशन यह वैल्यू देता है. |
समयसीमा के हिसाब से पढ़े जाने के बाद अपडेट करना
डेटा अपडेट करने के लिए, सबसे पहले ज़रूरी रिकॉर्ड तैयार करें. अगर ज़रूरी हो, तो रिकॉर्ड में कोई भी बदलाव करें. इसके बाद, बदलाव करने के लिए updateRecords को कॉल करें.
यहां दिए गए उदाहरण में, डेटा अपडेट करने का तरीका बताया गया है. इसके लिए, हर रिकॉर्ड में ज़ोन ऑफ़सेट वैल्यू को पीएसटी में अडजस्ट किया जाता है.
suspend fun updateSteps( healthConnectClient: HealthConnectClient, prevRecordStartTime: Instant, prevRecordEndTime: Instant ) { try { val request = healthConnectClient.readRecords( ReadRecordsRequest( recordType = StepsRecord::class, timeRangeFilter = TimeRangeFilter.between( prevRecordStartTime, prevRecordEndTime ) ) ) val newStepsRecords = arrayListOf<StepsRecord>() for (record in request.records) { // Adjusted both offset values to reflect changes val sr = StepsRecord( count = record.count, startTime = record.startTime, startZoneOffset = record.startTime.atZone(ZoneId.of("PST")).offset, endTime = record.endTime, endZoneOffset = record.endTime.atZone(ZoneId.of("PST")).offset, metadata = record.metadata ) newStepsRecords.add(sr) } healthConnectClient.updateRecords(newStepsRecords) } catch (e: Exception) { // Run error handling here } }
क्लाइंट रिकॉर्ड आईडी के ज़रिए अपसर्ट करना
अगर आपने Client Record ID और Client Record Version की वैल्यू का इस्तेमाल किया है, तो हमारा सुझाव है कि updateRecords के बजाय insertRecords का इस्तेमाल करें.
insertRecords फ़ंक्शन में डेटा को अपसर्ट करने की सुविधा होती है.
अगर दिए गए क्लाइंट रिकॉर्ड आईडी के सेट के आधार पर, Health Connect में डेटा मौजूद है, तो वह ओवरराइट हो जाता है. अगर ऐसा नहीं है, तो इसे नए डेटा के तौर पर लिखा जाता है.
यह तरीका तब काम आता है, जब आपको अपने ऐप्लिकेशन के डेटा स्टोर से Health Connect में डेटा सिंक करना हो.
यहां दिए गए उदाहरण में, ऐप्लिकेशन के डेटास्टोर से पुल किए गए डेटा पर अपसर्ट करने का तरीका बताया गया है:
fun pullStepsFromDatastore(startTime: Instant, endTime: Instant) : ArrayList<StepsRecord> { val appStepsRecords = arrayListOf<StepsRecord>() // Pull data from app datastore // ... // Make changes to data if necessary // ... // Store data in appStepsRecords // ... var sr = StepsRecord( metadata = Metadata.activelyRecorded( clientRecordId = "Your client record ID", clientRecordVersion = 0L, device = Device(type = Device.TYPE_WATCH) ), startTime = startTime, startZoneOffset = startTime.atZone(ZoneId.of("PST")).offset, endTime = endTime, endZoneOffset = endTime.atZone(ZoneId.of("PST")).offset, count = 120 ) appStepsRecords.add(sr) // ... return appStepsRecords } suspend fun upsertSteps( healthConnectClient: HealthConnectClient, newStepsRecords: ArrayList<StepsRecord> ) { try { healthConnectClient.insertRecords(newStepsRecords) } catch (e: Exception) { // Run error handling here } }
इसके बाद, इन फ़ंक्शन को अपनी मुख्य थ्रेड में कॉल किया जा सकता है.
upsertSteps(healthConnectClient, pullStepsFromDatastore( startTime = startTime, endTime = endTime ))
क्लाइंट रिकॉर्ड वर्शन में वैल्यू की जांच करना
अगर डेटा को अपडेट करने की प्रोसेस में क्लाइंट रिकॉर्ड वर्शन शामिल है, तो Health Connect, clientRecordVersion वैल्यू की तुलना करता है. अगर डाले गए डेटा का वर्शन, मौजूदा डेटा के वर्शन से ज़्यादा है, तो अपसर्ट होता है. ऐसा न होने पर, प्रोसेस में बदलाव को अनदेखा कर दिया जाता है और वैल्यू में कोई बदलाव नहीं होता.
अपने डेटा में वर्शनिंग शामिल करने के लिए, आपको Metadata.clientRecordVersion एट्रिब्यूट की वैल्यू के तौर पर Long सबमिट करना होगा. यह वैल्यू, वर्शनिंग के लॉजिक पर आधारित होनी चाहिए.
val endTime = Instant.now() val startTime = endTime.minus(Duration.ofMinutes(15)) val stepsRecord = StepsRecord( count = 100L, startTime = startTime, startZoneOffset = ZoneOffset.UTC, endTime = endTime, endZoneOffset = ZoneOffset.UTC, metadata = Metadata.activelyRecorded( clientRecordId = "Your supplied record ID", clientRecordVersion = 0L, // Your supplied record version device = Device(type = Device.TYPE_WATCH) ) )
अपसर्ट करने पर, बदलाव होने पर भी version अपने-आप नहीं बढ़ता. इससे डेटा को अनचाहे तरीके से ओवरराइट होने से रोका जा सकता है. इसलिए, आपको मैन्युअल तरीके से इसकी वैल्यू बढ़ानी होगी.
सामान्य दिशा-निर्देश
आपका ऐप्लिकेशन, पहले पक्ष (ग्राहक) के सभी डेटा को लिख सकता हो. आपके पास यह विकल्प होता है कि आपका ऐप्लिकेशन, तीसरे पक्ष के सोर्स से मिले डेटा को लिख सके. हालांकि, अगर आपके ऐप्लिकेशन ने Health Connect से डेटा ऐक्सेस किया है, तो उस डेटा को वापस Health Connect में सेव नहीं किया जाना चाहिए.
किसी दूसरे सोर्स से इंपोर्ट किए गए या उससे लिए गए डेटा को लिखते समय, आपको उसके ओरिजन और सोर्स डिवाइस के मेटाडेटा को सही तरीके से एट्रिब्यूट करना होगा. इसके लिए, आपको हर लिखित रिकॉर्ड के लिए यह मेटाडेटा देना होगा:
recordingMethod: अपने-आप या मैन्युअल तरीके से रिकॉर्ड किए गए डेटा के लिए, हम चाहते हैं कि रिकॉर्डिंग के तरीके को अपडेट किया जाए, ताकि रिकॉर्ड की गई गतिविधि का टाइप दिखे:RECORDING_METHOD_AUTOMATICALLY_RECORDED: अगर डेटा अपने-आप रिकॉर्ड हुआ है. उदाहरण के लिए, फ़िटनेस बैंड ने अपने-आप पता लगा लिया कि उपयोगकर्ता दौड़ने गया था.RECORDING_METHOD_ACTIVELY_RECORDED: अगर उपयोगकर्ता ने कोई नई गतिविधि शुरू की है, जैसे कि अपने पहने जाने वाले डिवाइस पर साइकल चलाना.RECORDING_METHOD_MANUAL_ENTRY: अगर उपयोगकर्ता ने डेटा मैन्युअल तरीके से डाला है.
device.type: आपकोDeviceके साथ काम करने वाले टाइप में से किसी एक टाइप का डिवाइस बताना होगा.device.manufacturer: डिवाइस बनाने वाली कंपनी का नाम. उदाहरण के लिए, "Fitbit".device.model: डिवाइस का मॉडल, जैसे कि "Charge 3".device.udi: (ज़रूरी नहीं) यह मेडिकल डिवाइस के यूनीक डिवाइस आइडेंटिफ़ायर (यूडीआई) का डिवाइस आइडेंटिफ़ायर (डीआई) वाला हिस्सा होता है. ज़रूरी अनुमति और निजता से जुड़े दिशा-निर्देशों के बारे में जानने के लिए, मेटाडेटा गाइड देखें.
मेटाडेटा को सही तरीके से सेट करना, डेटा की पारदर्शिता के लिए ज़रूरी है. इससे लोगों को यह समझने में मदद मिलती है कि उनकी सेहत से जुड़ी जानकारी कहां से मिलती है. पूरी जानकारी के लिए, Health Connect के मेटाडेटा की गाइड देखें.
अगर आपके ऐप्लिकेशन में मौजूद डेटा को किसी दूसरे ऐप्लिकेशन से इंपोर्ट किया गया है, तो Health Connect में अपना डेटा सेव करने की ज़िम्मेदारी उस दूसरे ऐप्लिकेशन की होगी.
ऐसा लॉजिक लागू करना भी एक अच्छा तरीका है जो लिखने से जुड़ी गड़बड़ियों को ठीक कर सके. जैसे, डेटा का तय सीमा से बाहर होना या सिस्टम में कोई गड़बड़ी होना. जॉब शेड्यूल करने के मेकेनिज़्म पर, बैकऑफ़ और फिर से कोशिश करने की रणनीतियां लागू की जा सकती हैं. अगर Health Connect में डेटा सेव नहीं हो पाता है, तो पक्का करें कि आपका ऐप्लिकेशन, एक्सपोर्ट के उस पॉइंट से आगे बढ़ सके. गड़बड़ियों का पता लगाने के लिए, उन्हें लॉग करना और उनकी शिकायत करना न भूलें.
डेटा ट्रैक करते समय, यहां दिए गए कुछ सुझावों का पालन किया जा सकता है. हालांकि, यह इस बात पर निर्भर करता है कि आपका ऐप्लिकेशन डेटा को कैसे सेव करता है.
टाइम ज़ोन मैनेज करना
समय के हिसाब से रिकॉर्ड लिखते समय, ऑफ़सेट को डिफ़ॉल्ट रूप से zoneOffset.UTC पर सेट न करें. ऐसा इसलिए, क्योंकि जब उपयोगकर्ता अन्य ज़ोन में होते हैं, तो इससे टाइमस्टैंप गलत हो सकते हैं. इसके बजाय, डिवाइस की मौजूदा जगह के हिसाब से ऑफ़सेट का हिसाब लगाएं. ZoneId.systemDefault() का इस्तेमाल करके, डिवाइस का टाइम ज़ोन वापस पाया जा सकता है.
val endTime = Instant.now() val startTime = endTime.minus(Duration.ofDays(1)) val stepsRecords = mutableListOf<StepsRecord>() var sampleTime = startTime val minutesBetweenSamples = 15L while (sampleTime < endTime) { // Get the default ZoneId then convert it to an offset val zoneOffset = ZoneOffset.systemDefault().rules.getOffset(sampleTime) stepsRecords += StepsRecord( startTime = sampleTime.minus(Duration.ofMinutes(minutesBetweenSamples)), startZoneOffset = zoneOffset, endTime = sampleTime, endZoneOffset = zoneOffset, count = Random.nextLong(1, 100), metadata = Metadata.activelyRecorded(device = Device(type = Device.TYPE_WATCH)), ) sampleTime = sampleTime.plus(Duration.ofMinutes(minutesBetweenSamples)) } healthConnectClient.insertRecords( stepsRecords )
ज़्यादा जानकारी के लिए, ZoneId के लिए दस्तावेज़ देखें.
फ़्रीक्वेंसी और जानकारी का स्तर
Health Connect में डेटा सेव करते समय, सही रिज़ॉल्यूशन का इस्तेमाल करें. सही रिज़ॉल्यूशन का इस्तेमाल करने से, स्टोरेज पर पड़ने वाले लोड को कम करने में मदद मिलती है. साथ ही, इससे सटीक और एक जैसा डेटा बनाए रखने में भी मदद मिलती है. डेटा रिज़ॉल्यूशन में दो चीज़ें शामिल होती हैं:
- डेटा सेव करने की फ़्रीक्वेंसी: आपका ऐप्लिकेशन, Health Connect में कितनी बार नया डेटा सेव करता है.
- नया डेटा उपलब्ध होने पर, डिवाइस की परफ़ॉर्मेंस को ध्यान में रखते हुए, डेटा को ज़्यादा से ज़्यादा बार लिखें.
- बैटरी लाइफ़ और अन्य परफ़ॉर्मेंस पर बुरा असर न पड़े, इसके लिए राइट के बीच ज़्यादा से ज़्यादा 15 मिनट का अंतराल होना चाहिए.
- लिखे गए डेटा की बारीकी: डेटा को कितनी बार सैंपल किया गया.
- उदाहरण के लिए, हर पांच सेकंड में धड़कन की दर के सैंपल लिखो.
- हर डेटा टाइप के लिए, एक जैसा सैंपल रेट ज़रूरी नहीं होता. हर सेकंड में कदमों की संख्या का डेटा अपडेट करने से कोई खास फ़ायदा नहीं होता. इसके बजाय, हर 60 सेकंड में अपडेट करने जैसे कम फ़्रीक्वेंसी वाले विकल्प का इस्तेमाल किया जा सकता है.
- सैंपल रेट ज़्यादा होने पर, उपयोगकर्ताओं को अपनी सेहत और फ़िटनेस के डेटा के बारे में ज़्यादा जानकारी मिल सकती है. सैंपल रेट फ़्रीक्वेंसी में, परफ़ॉर्मेंस और जानकारी के बीच संतुलन होना चाहिए.
दूसरे दिशा-निर्देश
डेटा लिखते समय इन दिशा-निर्देशों का पालन करें:
- हर सिंक के दौरान, सिर्फ़ नया डेटा और अपडेट किया गया वह डेटा लिखें जिसमें पिछले सिंक के बाद बदलाव किया गया है.
- हर अनुरोध में ज़्यादा से ज़्यादा 1,000 रिकॉर्ड शामिल करें.
- टास्क को सिर्फ़ तब चलाने की अनुमति दें, जब डिवाइस कुछ समय से इस्तेमाल में न हो और उसकी बैटरी कम न हो.
- बैकग्राउंड में होने वाले टास्क के लिए, WorkManager का इस्तेमाल करें. इससे, समय-समय पर होने वाले टास्क को शेड्यूल किया जा सकता है. हालांकि, इसके लिए ज़्यादा से ज़्यादा 15 मिनट की समयावधि तय की जा सकती है.
यहां दिए गए कोड में, WorkManager का इस्तेमाल करके बैकग्राउंड में टास्क शेड्यूल किए गए हैं. ये टास्क, ज़्यादा से ज़्यादा 15 मिनट की समयावधि पर चलेंगे. साथ ही, इनका फ़्लेक्स इंटरवल 5 मिनट का होगा. इस कॉन्फ़िगरेशन को PeriodicWorkRequest.Builder क्लास का इस्तेमाल करके सेट किया जाता है.
val constraints = Constraints.Builder()
.requiresBatteryNotLow()
.requiresDeviceIdle(true)
.build()
val writeDataWork = PeriodicWorkRequestBuilder<WriteDataToHealthConnectWorker>(
15,
TimeUnit.MINUTES,
5,
TimeUnit.MINUTES
)
.setConstraints(constraints)
.build()
ऐक्टिव ट्रैकिंग
इसमें ऐसे ऐप्लिकेशन शामिल हैं जो इवेंट के आधार पर ट्रैकिंग करते हैं. जैसे, कसरत और नींद. इसके अलावा, इसमें उपयोगकर्ता के मैन्युअल तरीके से दिए गए इनपुट को भी ट्रैक किया जाता है. जैसे, पोषण. ये रिकॉर्ड तब बनाए जाते हैं, जब ऐप्लिकेशन फ़ोरग्राउंड में हो. इसके अलावा, ये रिकॉर्ड उन खास मामलों में भी बनाए जाते हैं जब ऐप्लिकेशन का इस्तेमाल दिन में कुछ बार किया जाता है.
पुष्टि करें कि आपका ऐप्लिकेशन, इवेंट की पूरी अवधि के दौरान Health Connect को चालू नहीं रखता है.
डेटा को Health Connect में इन दो तरीकों में से किसी एक तरीके से सेव किया जाना चाहिए:
- इवेंट पूरा होने के बाद, Health Connect के साथ डेटा सिंक करें. उदाहरण के लिए, जब उपयोगकर्ता ट्रैक की गई कसरत का सेशन खत्म करता है, तब डेटा सिंक करना.
- डेटा को बाद में सिंक करने के लिए,
WorkManagerका इस्तेमाल करके, एक बार होने वाला टास्क शेड्यूल करें.
डेटा लिखने की फ़्रीक्वेंसी और ग्रेन्यूलैरिटी के लिए सबसे सही तरीके
Health Connect में डेटा सेव करते समय, सही रिज़ॉल्यूशन का इस्तेमाल करें. सही रिज़ॉल्यूशन का इस्तेमाल करने से, स्टोरेज पर पड़ने वाले लोड को कम करने में मदद मिलती है. साथ ही, इससे सटीक और एक जैसा डेटा बनाए रखने में भी मदद मिलती है. डेटा रिज़ॉल्यूशन में दो चीज़ें शामिल होती हैं:
डेटा लिखने की फ़्रीक्वेंसी: आपका ऐप्लिकेशन, Health Connect में कितनी बार नया डेटा भेजता है. नया डेटा उपलब्ध होने पर, उसे जितनी बार हो सके उतनी बार लिखें. हालांकि, डिवाइस की परफ़ॉर्मेंस का ध्यान रखें. बैटरी लाइफ़ और परफ़ॉर्मेंस के अन्य पहलुओं पर बुरा असर न पड़े, इसके लिए राइट के बीच का ज़्यादा से ज़्यादा इंटरवल 15 मिनट होना चाहिए.
लिखे गए डेटा की बारीकी: पुश किए गए डेटा को कितनी बार सैंपल किया गया. उदाहरण के लिए, हर पांच सेकंड में धड़कन की दर के सैंपल लिखो. हर डेटा टाइप के लिए, एक जैसा सैंपल रेट ज़रूरी नहीं होता. हर सेकंड में कदमों की संख्या का डेटा अपडेट करने से कोई खास फ़ायदा नहीं होता. इसके बजाय, इसे कम बार अपडेट किया जा सकता है. जैसे, हर 60 सेकंड में. हालांकि, ज़्यादा सैंपल रेट से उपयोगकर्ताओं को सेहत और फ़िटनेस से जुड़े डेटा के बारे में ज़्यादा जानकारी मिल सकती है. सैंपल रेट फ़्रीक्वेंसी में, बारीकी से जानकारी देने और परफ़ॉर्मेंस के बीच संतुलन होना चाहिए.
सीरीज़ के डेटा के लिए रिकॉर्ड स्ट्रक्चर करना
HeartRateRecord जैसे डेटा टाइप के लिए, सैंपल की सीरीज़ का इस्तेमाल किया जाता है. इसलिए, अपने रिकॉर्ड को सही तरीके से स्ट्रक्चर करना ज़रूरी है. पूरे दिन का एक ऐसा रिकॉर्ड बनाने के बजाय जिसे लगातार अपडेट किया जाता है, आपको कई छोटे-छोटे रिकॉर्ड बनाने चाहिए. हर रिकॉर्ड में एक तय समय अंतराल की जानकारी होनी चाहिए.
उदाहरण के लिए, धड़कन की दर के डेटा के लिए, आपको हर मिनट के लिए एक नया HeartRateRecord बनाना चाहिए. हर रिकॉर्ड में, उस मिनट के लिए शुरू और खत्म होने का समय होगा. साथ ही, उस मिनट के दौरान कैप्चर किए गए धड़कन की दर के सभी सैंपल शामिल होंगे.
Health Connect के साथ नियमित रूप से सिंक करने के दौरान (उदाहरण के लिए, हर 15 मिनट में), आपके ऐप्लिकेशन को एक मिनट के उन सभी रिकॉर्ड को सेव करना चाहिए जो पिछली बार सिंक करने के बाद बनाए गए हैं. इससे रिकॉर्ड को मैनेज किया जा सकता है. साथ ही, क्वेरी करने और डेटा को प्रोसेस करने की परफ़ॉर्मेंस को बेहतर बनाया जा सकता है.
यहां दिए गए उदाहरण में, एक मिनट के लिए HeartRateRecord बनाने का तरीका बताया गया है. इसमें कई सैंपल शामिल हैं:
val startTime = Instant.now().truncatedTo(ChronoUnit.MINUTES) val endTime = startTime.plus(Duration.ofMinutes(1)) val heartRateRecord = HeartRateRecord( startTime = startTime, startZoneOffset = ZoneOffset.UTC, endTime = endTime, endZoneOffset = ZoneOffset.UTC, // Create a new record every minute, containing a list of samples. samples = listOf( HeartRateRecord.Sample( time = startTime + Duration.ofSeconds(15), beatsPerMinute = 80, ), HeartRateRecord.Sample( time = startTime + Duration.ofSeconds(30), beatsPerMinute = 82, ), HeartRateRecord.Sample( time = startTime + Duration.ofSeconds(45), beatsPerMinute = 85, ) ), metadata = Metadata.activelyRecorded( device = Device(type = Device.TYPE_WATCH) ))
पूरे दिन मॉनिटर किए गए डेटा को लिखने की अनुमति दें
कदमों की संख्या जैसे लगातार इकट्ठा किए जाने वाले डेटा के लिए, जब नया डेटा उपलब्ध हो, तो आपके ऐप्लिकेशन को Health Connect में डेटा को ज़्यादा से ज़्यादा बार लिखना चाहिए. बैटरी लाइफ़ और परफ़ॉर्मेंस के अन्य पहलुओं पर बुरा असर न पड़े, इसके लिए राइट के बीच ज़्यादा से ज़्यादा 15 मिनट का अंतराल होना चाहिए.
डेटा टाइप |
यूनिट |
अनुमानित |
उदाहरण |
चरण |
कदम |
हर 1 मिनट में |
23:14 - 23:15 - 5 कदम 23:16 - 23:17 - 22 कदम 23:17 - 23:18 - 8 कदम |
StepsCadence |
कदम/मि॰ |
हर 1 मिनट में |
23:14 - 23:15 - 5 spm 23:16 - 23:17 - 22 एसपीएम 23:17 - 23:18 - 8 एसपीएम |
व्हीलचेयर पुश करने से जुड़ा डेटा |
पुश करता है |
हर 1 मिनट में |
23:14 - 23:15 - 5 पुश 23:16 - 23:17 - 22 पुश 23:17 - 23:18 - 8 पुश |
ActiveCaloriesBurned |
कैलोरी |
प्रत्येक 15 मिनट |
23:15 - 23:30 - 2 कैलोरी 23:30 - 23:45 - 25 कैलोरी 23:45 - 00:00 - 5 कैलोरी |
TotalCaloriesBurned |
कैलोरी |
प्रत्येक 15 मिनट |
23:15 - 23:30 - 16 कैलोरी 23:30 - 23:45 - 16 कैलोरी 23:45 - 00:00 - 16 कैलोरी |
दूरी |
कि॰मी॰/मि॰ |
हर 1 मिनट में |
23:14-23:15 - 0.008 कि॰मी॰ 23:16 - 23:16 - 0.021 कि॰मी॰ 23:17 - 23:18 - 0.012 कि॰मी॰ |
ElevationGained |
m |
हर 1 मिनट में |
20:36 - 20:37 - 3.048 मीटर 20:39 - 20:40 - 3.048 मीटर 23:23 - 23:24 - 9.144 मीटर |
FloorsClimbed |
फ़्लोर |
हर 1 मिनट में |
23:14 - 23:15 - 5 फ़्लोर 23:16 - 23:16 - 22 फ़्लोर 23:17 - 23:18 - 8 फ़्लोर |
HeartRate |
बीपीएम |
एक मिनट में चार बार |
सुबह 6:11:15 - 55 बीपीएम सुबह 6:11:30 बजे - 56 बीपीएम सुबह 6:11:45 बजे - 56 बीपीएम सुबह 6:12:00 बजे - 55 बीपीएम |
HeartRateVariabilityRmssd |
ms |
हर 1 मिनट में |
सुबह 6:11 बजे - 23 मि॰से॰ |
RespiratoryRate |
सांस/मिनट |
हर 1 मिनट में |
23:14 - 23:15 - 60 सांसें/मिनट 23:16 - 23:16 - 62 सांसें/मिनट 23:17 - 23:18 - 64 सांसें/मिनट |
OxygenSaturation |
% |
हर 1 घंटे में |
6:11 - 95.208% |
कसरत या नींद के सेशन के खत्म होने के बाद, डेटा को Health Connect में सेव किया जाना चाहिए. कसरत और नींद जैसी गतिविधियों को ट्रैक करने या पोषण जैसी जानकारी को मैन्युअल तरीके से डालने के लिए, ये रिकॉर्ड तब बनाए जाते हैं, जब ऐप्लिकेशन फ़ोरग्राउंड में हो. इसके अलावा, ये रिकॉर्ड कभी-कभी तब भी बनाए जाते हैं, जब ऐप्लिकेशन का इस्तेमाल दिन में कुछ बार किया जाता है.
पुष्टि करें कि आपका ऐप्लिकेशन, इवेंट की पूरी अवधि के दौरान Health Connect को चालू नहीं रखता है.
डेटा को Health Connect में इन दो तरीकों में से किसी एक तरीके से सेव किया जाना चाहिए:
- इवेंट पूरा होने के बाद, Health Connect के साथ डेटा सिंक करें. उदाहरण के लिए, जब उपयोगकर्ता ट्रैक की गई कसरत का सेशन खत्म करता है, तब डेटा सिंक करना.
- डेटा को बाद में सिंक करने के लिए, WorkManager का इस्तेमाल करके एक बार का टास्क शेड्यूल करें.
कसरत और नींद के सेशन
आपका आवेदन कम से कम, टेबल 2 के अनुमानित कॉलम में दिए गए दिशा-निर्देशों का पालन करता हो. जहां भी हो सके, सबसे सही कॉलम में दिए गए दिशा-निर्देशों का पालन करें.
यहां दी गई टेबल में, कसरत के दौरान डेटा लिखने का तरीका बताया गया है:
डेटा टाइप |
यूनिट |
अनुमानित |
धन्यवाद |
उदाहरण |
चरण |
कदम |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 5 कदम 23:16 - 23:17 - 22 कदम 23:17 - 23:18 - 8 कदम |
StepsCadence |
कदम/मि॰ |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 35 एसपीएम 23:16 - 23:17 - 37 एसपीएम 23:17 - 23:18 - 40 एसपीएम |
व्हीलचेयर पुश करने से जुड़ा डेटा |
पुश करता है |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 5 पुश 23:16 - 23:17 - 22 पुश 23:17 - 23:18 - 8 पुश |
CyclingPedalingCadence |
आरपीएम |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 65 आरपीएम 23:16 - 23:17 - 70 आरपीएम 23:17 - 23:18 - 68 आरपीएम |
पावर |
वॉट |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 250 वॉट 23:16 - 23:17 - 255 वॉट 23:17 - 23:18 - 245 वॉट |
स्पीड |
कि॰मी॰/मि॰ |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 0.3 कि॰मी॰/मिनट 23:16 - 23:17 - 0.4 कि॰मी॰/मिनट 23:17 - 23:18 -0.4 कि॰मी॰/मि॰ |
दूरी |
कि॰मी॰/मि॰ |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 0.008 कि॰मी॰ 23:16 - 23:16 - 0.021 कि॰मी॰ 23:17 - 23:18 - 0.012 कि॰मी॰ |
ActiveCaloriesBurned |
कैलोरी |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 20 कैलोरी 23:16 - 23:17 - 20 कैलोरी 23:17 - 23:18 - 25 कैलोरी |
TotalCaloriesBurned |
कैलोरी |
हर 1 मिनट में |
हर 1 सेकंड में |
23:14-23:15 - 36 कैलोरी 23:16 - 23:17 - 36 कैलोरी 23:17 - 23:18 - 41 कैलोरी |
ElevationGained |
m |
हर 1 मिनट में |
हर 1 सेकंड में |
20:36 - 20:37 - 3.048 मीटर 20:39 - 20:40 - 3.048 मीटर 23:23 - 23:24 - 9.144 मीटर |
ExerciseRoutes |
lat/lng/alt |
हर तीन से पांच सेकंड में |
हर 1 सेकंड में |
|
HeartRate |
बीपीएम |
एक मिनट में चार बार |
हर 1 सेकंड में |
23:14-23:15 - 150 बीपीएम |
तीसरी टेबल में, नींद के सेशन के दौरान या बाद में डेटा लिखने का तरीका बताया गया है:
डेटा टाइप |
यूनिट |
अनुमानित सैंपल |
उदाहरण |
नींद के चरण का पता लगाना |
स्टेज |
नींद के हर चरण के हिसाब से समय की विस्तृत जानकारी |
23:46 से 23:50 - नींद खुली 23:50 - 23:56 - हल्की नींद 23:56 - 00:16 - गहरी नींद |
RestingHeartRate |
बीपीएम |
रोज़ की एक वैल्यू (सुबह सबसे पहले अपडेट होने की उम्मीद है) |
सुबह 6:11 बजे - 60 बीपीएम |
OxygenSaturation |
% |
रोज़ की एक वैल्यू (सुबह सबसे पहले अपडेट होने की उम्मीद है) |
6:11 - 95.208% |
मल्टी-स्पोर्ट इवेंट
इस तरीके में, मौजूदा डेटा टाइप और स्ट्रक्चर का इस्तेमाल किया जाता है. साथ ही, यह पुष्टि की जाती है कि यह Health Connect के मौजूदा वर्शन और डेटा रीडर के साथ काम करता है. फ़िटनेस प्लैटफ़ॉर्म, आम तौर पर इसी तरीके का इस्तेमाल करते हैं.
इसके अलावा, तैराकी, साइकल चलाना, और दौड़ने जैसे अलग-अलग सेशन, Health Connect में अपने-आप लिंक नहीं होते. डेटा रीडर को इन सेशन के बीच के संबंध का पता, उनके समय के हिसाब से लगाना होता है. सेगमेंट के बीच ट्रांज़िशन, जैसे कि तैरने से साइकल चलाने पर स्विच करने के बारे में साफ़ तौर पर नहीं बताया गया है.
यहां दिए गए उदाहरण में, ट्रायथलॉन के लिए डेटा लिखने का तरीका बताया गया है:
val swimStartTime = Instant.parse("2024-08-22T08:00:00Z") val swimEndTime = Instant.parse("2024-08-22T08:30:00Z") val bikeStartTime = Instant.parse("2024-08-22T08:40:00Z") val bikeEndTime = Instant.parse("2024-08-22T09:40:00Z") val runStartTime = Instant.parse("2024-08-22T09:50:00Z") val runEndTime = Instant.parse("2024-08-22T10:20:00Z") val swimSession = ExerciseSessionRecord( startTime = swimStartTime, endTime = swimEndTime, exerciseType = ExerciseSessionRecord.EXERCISE_TYPE_SWIMMING_OPEN_WATER, metadata = Metadata.activelyRecorded( device = Device(type = Device.TYPE_WATCH) ), startZoneOffset = null, endZoneOffset = null, ) val bikeSession = ExerciseSessionRecord( startTime = bikeStartTime, endTime = bikeEndTime, exerciseType = ExerciseSessionRecord.EXERCISE_TYPE_BIKING, metadata = Metadata.activelyRecorded( device = Device(type = Device.TYPE_WATCH) ), startZoneOffset = null, endZoneOffset = null, ) val runSession = ExerciseSessionRecord( startTime = runStartTime, endTime = runEndTime, exerciseType = ExerciseSessionRecord.EXERCISE_TYPE_RUNNING, metadata = Metadata.activelyRecorded( device = Device(type = Device.TYPE_WATCH) ), startZoneOffset = null, endZoneOffset = null, ) healthConnectClient.insertRecords(listOf(swimSession, bikeSession, runSession))
गड़बड़ियों को ठीक करना
अगर कोई समस्या आती है, तो Health Connect, CRUD ऑपरेशनों के लिए स्टैंडर्ड अपवाद दिखाता है. आपका ऐप्लिकेशन, इन सभी अपवादों को सही तरीके से पकड़कर हैंडल करे.
HealthConnectClient पर मौजूद हर तरीके में, थ्रो किए जा सकने वाले अपवादों की सूची होती है.
आम तौर पर, आपके ऐप्लिकेशन को इन अपवादों को हैंडल करना चाहिए:
| अपवाद | ब्यौरा | सुझाया गया सबसे सही तरीका |
|---|---|---|
IllegalStateException
| इनमें से कोई एक स्थिति हुई है:
| अनुरोध करने से पहले, इनपुट से जुड़ी संभावित समस्याओं को ठीक करें. हमारा सुझाव है कि आप वैरिएबल को वैल्यू असाइन करें या उन्हें कस्टम फ़ंक्शन में पैरामीटर के तौर पर इस्तेमाल करें. ऐसा इसलिए, ताकि आप सीधे तौर पर अपने अनुरोधों में उनका इस्तेमाल न करें और गड़बड़ी ठीक करने की रणनीतियां लागू कर सकें. |
IOException
| डिस्क से डेटा पढ़ने और लिखने के दौरान समस्याएं आती हैं. | इस समस्या से बचने के लिए, यहां कुछ सुझाव दिए गए हैं:
|
RemoteException
| SDK जिस सेवा से कनेक्ट होता है उसमें या उससे कम्यूनिकेट करने में गड़बड़ियां हुई हैं. उदाहरण के लिए, आपका ऐप्लिकेशन दिए गए uid के साथ किसी रिकॉर्ड को मिटाने की कोशिश कर रहा है. हालांकि, ऐप्लिकेशन को यह अपवाद तब मिलता है, जब वह यह पता लगा लेता है कि रिकॉर्ड मौजूद नहीं है. इसके लिए, वह बुनियादी सेवा में जांच करता है.
| इस समस्या से बचने के लिए, यहां कुछ सुझाव दिए गए हैं:
|
SecurityException
| अनुरोधों के लिए ऐसी अनुमतियों की ज़रूरत होती है जो नहीं दी गई हैं. | इससे बचने के लिए, पक्का करें कि आपने पब्लिश किए गए ऐप्लिकेशन के लिए, Health Connect के डेटा टाइप के इस्तेमाल के बारे में एलान किया हो. साथ ही, आपको Health Connect की अनुमतियों के बारे में मेनिफ़ेस्ट फ़ाइल में और अपनी गतिविधि में एलान करना होगा. |