|
@@ -391,9 +391,10 @@ void main() { |
|
@@ -391,9 +391,10 @@ void main() { |
|
391
|
expect(daily.single.uploaded, isTrue);
|
391
|
expect(daily.single.uploaded, isTrue);
|
|
392
|
});
|
392
|
});
|
|
393
|
|
393
|
|
|
394
|
- test('startCoreCaculate skips raw reads when health auth is missing',
|
394
|
+ test(
|
|
|
|
395
|
+ 'startCoreCaculate skips raw reads when health auth and local data are missing',
|
|
395
|
() async {
|
396
|
() async {
|
|
396
|
- final api = _FakeHealthKitRawDataHostApi();
|
397
|
+ final api = _FakeHealthKitRawDataHostApi()..hasData = false;
|
|
397
|
final service = AppleHealthRawDataCoreService(
|
398
|
final service = AppleHealthRawDataCoreService(
|
|
398
|
healthApi: _FakeHealthKitHostApi(status: 2),
|
399
|
healthApi: _FakeHealthKitHostApi(status: 2),
|
|
399
|
rawDataApi: api,
|
400
|
rawDataApi: api,
|
|
@@ -411,6 +412,79 @@ void main() { |
|
@@ -411,6 +412,79 @@ void main() { |
|
411
|
expect(api.workoutCallCount, 0);
|
412
|
expect(api.workoutCallCount, 0);
|
|
412
|
});
|
413
|
});
|
|
413
|
|
414
|
|
|
|
|
415
|
+ test(
|
|
|
|
416
|
+ 'startCoreCaculate reads raw data when health auth is missing but data exists',
|
|
|
|
417
|
+ () async {
|
|
|
|
418
|
+ final now = DateTime.now().millisecondsSinceEpoch ~/ 1000;
|
|
|
|
419
|
+ final api = _FakeHealthKitRawDataHostApi()..hasData = true;
|
|
|
|
420
|
+ api.setPoints(HealthDataUploadType.hrv.type, [
|
|
|
|
421
|
+ _point(now - 120, 35),
|
|
|
|
422
|
+ ]);
|
|
|
|
423
|
+ final service = AppleHealthRawDataCoreService(
|
|
|
|
424
|
+ healthApi: _FakeHealthKitHostApi(status: 2),
|
|
|
|
425
|
+ rawDataApi: api,
|
|
|
|
426
|
+ localStore: _MemoryHealthRawStressLocalStore(),
|
|
|
|
427
|
+ userIdProvider: () => 42,
|
|
|
|
428
|
+ uploadResultsAfterCalculation: false,
|
|
|
|
429
|
+ );
|
|
|
|
430
|
+
|
|
|
|
431
|
+ final result = await service.startCoreCaculate(
|
|
|
|
432
|
+ endTime: now,
|
|
|
|
433
|
+ readChunkDays: 1,
|
|
|
|
434
|
+ );
|
|
|
|
435
|
+
|
|
|
|
436
|
+ expect(result.hrvStressPoints.map((e) => e.rawEndTime), [now - 120]);
|
|
|
|
437
|
+ expect(api.calls, isNotEmpty);
|
|
|
|
438
|
+ expect(api.hasHealthDataCallCount, 1);
|
|
|
|
439
|
+ });
|
|
|
|
440
|
+
|
|
|
|
441
|
+ test('startCoreCaculate skips raw reads when local data check fails',
|
|
|
|
442
|
+ () async {
|
|
|
|
443
|
+ final api = _FakeHealthKitRawDataHostApi()
|
|
|
|
444
|
+ ..hasDataError = StateError('health data unavailable');
|
|
|
|
445
|
+ final service = AppleHealthRawDataCoreService(
|
|
|
|
446
|
+ healthApi: _FakeHealthKitHostApi(status: 2),
|
|
|
|
447
|
+ rawDataApi: api,
|
|
|
|
448
|
+ localStore: _MemoryHealthRawStressLocalStore(),
|
|
|
|
449
|
+ userIdProvider: () => 42,
|
|
|
|
450
|
+ uploadResultsAfterCalculation: false,
|
|
|
|
451
|
+ );
|
|
|
|
452
|
+
|
|
|
|
453
|
+ final result = await service.startCoreCaculate(readChunkDays: 1);
|
|
|
|
454
|
+
|
|
|
|
455
|
+ expect(result.hrvStressPoints, isEmpty);
|
|
|
|
456
|
+ expect(result.realtimeStressPoints, isEmpty);
|
|
|
|
457
|
+ expect(api.calls, isEmpty);
|
|
|
|
458
|
+ expect(api.hasHealthDataCallCount, 1);
|
|
|
|
459
|
+ });
|
|
|
|
460
|
+
|
|
|
|
461
|
+ test(
|
|
|
|
462
|
+ 'startCoreCaculate does not call local data fallback when auth is granted',
|
|
|
|
463
|
+ () async {
|
|
|
|
464
|
+ final now = DateTime.now().millisecondsSinceEpoch ~/ 1000;
|
|
|
|
465
|
+ final api = _FakeHealthKitRawDataHostApi()
|
|
|
|
466
|
+ ..hasData = false
|
|
|
|
467
|
+ ..hasDataError = StateError('should not call hasHealthData');
|
|
|
|
468
|
+ api.setPoints(HealthDataUploadType.hrv.type, [
|
|
|
|
469
|
+ _point(now - 120, 35),
|
|
|
|
470
|
+ ]);
|
|
|
|
471
|
+ final service = AppleHealthRawDataCoreService(
|
|
|
|
472
|
+ healthApi: _FakeHealthKitHostApi(status: 1),
|
|
|
|
473
|
+ rawDataApi: api,
|
|
|
|
474
|
+ localStore: _MemoryHealthRawStressLocalStore(),
|
|
|
|
475
|
+ userIdProvider: () => 42,
|
|
|
|
476
|
+ uploadResultsAfterCalculation: false,
|
|
|
|
477
|
+ );
|
|
|
|
478
|
+
|
|
|
|
479
|
+ final result = await service.startCoreCaculate(
|
|
|
|
480
|
+ endTime: now,
|
|
|
|
481
|
+ readChunkDays: 1,
|
|
|
|
482
|
+ );
|
|
|
|
483
|
+
|
|
|
|
484
|
+ expect(result.hrvStressPoints.map((e) => e.rawEndTime), [now - 120]);
|
|
|
|
485
|
+ expect(api.hasHealthDataCallCount, 0);
|
|
|
|
486
|
+ });
|
|
|
|
487
|
+
|
|
414
|
test('onHealthDataUpdated emits event with data types after calculation',
|
488
|
test('onHealthDataUpdated emits event with data types after calculation',
|
|
415
|
() async {
|
489
|
() async {
|
|
416
|
final now = DateTime.now().millisecondsSinceEpoch ~/ 1000;
|
490
|
final now = DateTime.now().millisecondsSinceEpoch ~/ 1000;
|
|
@@ -943,6 +1017,8 @@ class _FakeHealthKitRawDataHostApi extends HealthKitRawDataHostApi { |
|
@@ -943,6 +1017,8 @@ class _FakeHealthKitRawDataHostApi extends HealthKitRawDataHostApi { |
|
943
|
Completer<int>? hrUploadCompleter;
|
1017
|
Completer<int>? hrUploadCompleter;
|
|
944
|
Completer<int>? hrvUploadCompleter;
|
1018
|
Completer<int>? hrvUploadCompleter;
|
|
945
|
var hasData = true;
|
1019
|
var hasData = true;
|
|
|
|
1020
|
+ Object? hasDataError;
|
|
|
|
1021
|
+ var hasHealthDataCallCount = 0;
|
|
946
|
|
1022
|
|
|
947
|
void setPoints(int dataType, List<HealthKitRawDataPoint> points) {
|
1023
|
void setPoints(int dataType, List<HealthKitRawDataPoint> points) {
|
|
948
|
_pointsByType[dataType] = points;
|
1024
|
_pointsByType[dataType] = points;
|
|
@@ -965,7 +1041,14 @@ class _FakeHealthKitRawDataHostApi extends HealthKitRawDataHostApi { |
|
@@ -965,7 +1041,14 @@ class _FakeHealthKitRawDataHostApi extends HealthKitRawDataHostApi { |
|
965
|
}
|
1041
|
}
|
|
966
|
|
1042
|
|
|
967
|
@override
|
1043
|
@override
|
|
968
|
- Future<bool> hasHealthData() async => hasData;
|
1044
|
+ Future<bool> hasHealthData() async {
|
|
|
|
1045
|
+ hasHealthDataCallCount += 1;
|
|
|
|
1046
|
+ final error = hasDataError;
|
|
|
|
1047
|
+ if (error != null) {
|
|
|
|
1048
|
+ throw error;
|
|
|
|
1049
|
+ }
|
|
|
|
1050
|
+ return hasData;
|
|
|
|
1051
|
+ }
|
|
969
|
|
1052
|
|
|
970
|
@override
|
1053
|
@override
|
|
971
|
Future<List<HealthKitRawDataPoint>> getHealthKitRawData(
|
1054
|
Future<List<HealthKitRawDataPoint>> getHealthKitRawData(
|