@kingstinct/react-native-healthkit 13.0.0 → 13.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (133) hide show
  1. package/ReactNativeHealthkit.podspec +2 -0
  2. package/ios/CoreModule.swift +1 -1
  3. package/ios/CorrelationTypeModule.swift +5 -2
  4. package/ios/ExceptionCatcher.h +17 -0
  5. package/ios/Helpers.swift +55 -33
  6. package/ios/QuantityTypeModule.swift +12 -32
  7. package/ios/WorkoutsModule.swift +1 -1
  8. package/nitrogen/generated/ios/ReactNativeHealthkit-Swift-Cxx-Bridge.cpp +1 -0
  9. package/nitrogen/generated/ios/swift/AuthDataTypes.swift +1 -0
  10. package/nitrogen/generated/ios/swift/CategorySample.swift +1 -0
  11. package/nitrogen/generated/ios/swift/CategorySampleForSaving.swift +1 -0
  12. package/nitrogen/generated/ios/swift/CategorySamplesWithAnchorResponse.swift +1 -0
  13. package/nitrogen/generated/ios/swift/CorrelationSample.swift +1 -0
  14. package/nitrogen/generated/ios/swift/DateFilter.swift +1 -0
  15. package/nitrogen/generated/ios/swift/DeletedSample.swift +1 -0
  16. package/nitrogen/generated/ios/swift/Device.swift +1 -0
  17. package/nitrogen/generated/ios/swift/ECGQueryOptionsWithAnchor.swift +1 -0
  18. package/nitrogen/generated/ios/swift/ECGQueryOptionsWithSortOrder.swift +1 -0
  19. package/nitrogen/generated/ios/swift/ElectrocardiogramSample.swift +1 -0
  20. package/nitrogen/generated/ios/swift/ElectrocardiogramSamplesWithAnchorResponse.swift +1 -0
  21. package/nitrogen/generated/ios/swift/ElectrocardiogramVoltage.swift +1 -0
  22. package/nitrogen/generated/ios/swift/FilterForSamples.swift +1 -0
  23. package/nitrogen/generated/ios/swift/FilterForSamplesBase.swift +1 -0
  24. package/nitrogen/generated/ios/swift/FilterForWorkouts.swift +1 -0
  25. package/nitrogen/generated/ios/swift/FilterForWorkoutsBase.swift +1 -0
  26. package/nitrogen/generated/ios/swift/Func_void_AuthorizationRequestStatus.swift +1 -1
  27. package/nitrogen/generated/ios/swift/Func_void_BiologicalSex.swift +1 -1
  28. package/nitrogen/generated/ios/swift/Func_void_BloodType.swift +1 -1
  29. package/nitrogen/generated/ios/swift/Func_void_CategorySamplesWithAnchorResponse.swift +1 -1
  30. package/nitrogen/generated/ios/swift/Func_void_ElectrocardiogramSamplesWithAnchorResponse.swift +1 -1
  31. package/nitrogen/generated/ios/swift/Func_void_FitzpatrickSkinType.swift +1 -1
  32. package/nitrogen/generated/ios/swift/Func_void_HeartbeatSeriesSamplesWithAnchorResponse.swift +1 -1
  33. package/nitrogen/generated/ios/swift/Func_void_MedicationDoseEventsWithAnchorResponse.swift +1 -1
  34. package/nitrogen/generated/ios/swift/Func_void_OnChangeCallbackArgs.swift +1 -1
  35. package/nitrogen/generated/ios/swift/Func_void_QuantitySamplesWithAnchorResponse.swift +1 -1
  36. package/nitrogen/generated/ios/swift/Func_void_QueryCorrelationSamplesWithAnchorResponse.swift +1 -1
  37. package/nitrogen/generated/ios/swift/Func_void_QueryStatisticsResponse.swift +1 -1
  38. package/nitrogen/generated/ios/swift/Func_void_QueryWorkoutSamplesWithAnchorResponse.swift +1 -1
  39. package/nitrogen/generated/ios/swift/Func_void_StateOfMindSamplesWithAnchorResponse.swift +1 -1
  40. package/nitrogen/generated/ios/swift/Func_void_WheelchairUse.swift +1 -1
  41. package/nitrogen/generated/ios/swift/Func_void_bool.swift +1 -1
  42. package/nitrogen/generated/ios/swift/Func_void_double.swift +1 -1
  43. package/nitrogen/generated/ios/swift/Func_void_std__exception_ptr.swift +1 -1
  44. package/nitrogen/generated/ios/swift/Func_void_std__optional_CategorySample_.swift +1 -1
  45. package/nitrogen/generated/ios/swift/Func_void_std__optional_CorrelationSample_.swift +1 -1
  46. package/nitrogen/generated/ios/swift/Func_void_std__optional_QuantitySample_.swift +1 -1
  47. package/nitrogen/generated/ios/swift/Func_void_std__optional_QueryStatisticsResponse_.swift +1 -1
  48. package/nitrogen/generated/ios/swift/Func_void_std__optional_StateOfMindSample_.swift +1 -1
  49. package/nitrogen/generated/ios/swift/Func_void_std__optional_WorkoutPlan_.swift +1 -1
  50. package/nitrogen/generated/ios/swift/Func_void_std__optional_std__chrono__system_clock__time_point_.swift +1 -1
  51. package/nitrogen/generated/ios/swift/Func_void_std__shared_ptr_HybridWorkoutProxySpec_.swift +1 -1
  52. package/nitrogen/generated/ios/swift/Func_void_std__unordered_map_std__string__QueryStatisticsResponse_.swift +1 -1
  53. package/nitrogen/generated/ios/swift/Func_void_std__unordered_map_std__string__bool_.swift +1 -1
  54. package/nitrogen/generated/ios/swift/Func_void_std__vector_CategorySample_.swift +1 -1
  55. package/nitrogen/generated/ios/swift/Func_void_std__vector_CorrelationSample_.swift +1 -1
  56. package/nitrogen/generated/ios/swift/Func_void_std__vector_ElectrocardiogramSample_.swift +1 -1
  57. package/nitrogen/generated/ios/swift/Func_void_std__vector_HeartbeatSeriesSample_.swift +1 -1
  58. package/nitrogen/generated/ios/swift/Func_void_std__vector_IdentifierWithUnit_.swift +1 -1
  59. package/nitrogen/generated/ios/swift/Func_void_std__vector_MedicationDoseEvent_.swift +1 -1
  60. package/nitrogen/generated/ios/swift/Func_void_std__vector_QuantitySample_.swift +1 -1
  61. package/nitrogen/generated/ios/swift/Func_void_std__vector_QueryStatisticsResponseFromSingleSource_.swift +1 -1
  62. package/nitrogen/generated/ios/swift/Func_void_std__vector_QueryStatisticsResponse_.swift +1 -1
  63. package/nitrogen/generated/ios/swift/Func_void_std__vector_StateOfMindSample_.swift +1 -1
  64. package/nitrogen/generated/ios/swift/Func_void_std__vector_UserAnnotatedMedication_.swift +1 -1
  65. package/nitrogen/generated/ios/swift/Func_void_std__vector_WorkoutRoute_.swift +1 -1
  66. package/nitrogen/generated/ios/swift/Func_void_std__vector_std__shared_ptr_HybridSourceProxySpec__.swift +1 -1
  67. package/nitrogen/generated/ios/swift/Func_void_std__vector_std__shared_ptr_HybridWorkoutProxySpec__.swift +1 -1
  68. package/nitrogen/generated/ios/swift/Heartbeat.swift +1 -0
  69. package/nitrogen/generated/ios/swift/HeartbeatSeriesSample.swift +1 -0
  70. package/nitrogen/generated/ios/swift/HeartbeatSeriesSamplesWithAnchorResponse.swift +1 -0
  71. package/nitrogen/generated/ios/swift/HybridCategoryTypeModuleSpec.swift +0 -1
  72. package/nitrogen/generated/ios/swift/HybridCategoryTypeModuleSpec_cxx.swift +0 -1
  73. package/nitrogen/generated/ios/swift/HybridCharacteristicTypeModuleSpec.swift +0 -1
  74. package/nitrogen/generated/ios/swift/HybridCharacteristicTypeModuleSpec_cxx.swift +0 -1
  75. package/nitrogen/generated/ios/swift/HybridCoreModuleSpec.swift +0 -1
  76. package/nitrogen/generated/ios/swift/HybridCoreModuleSpec_cxx.swift +0 -1
  77. package/nitrogen/generated/ios/swift/HybridCorrelationTypeModuleSpec.swift +0 -1
  78. package/nitrogen/generated/ios/swift/HybridCorrelationTypeModuleSpec_cxx.swift +0 -1
  79. package/nitrogen/generated/ios/swift/HybridElectrocardiogramModuleSpec.swift +0 -1
  80. package/nitrogen/generated/ios/swift/HybridElectrocardiogramModuleSpec_cxx.swift +0 -1
  81. package/nitrogen/generated/ios/swift/HybridHeartbeatSeriesModuleSpec.swift +0 -1
  82. package/nitrogen/generated/ios/swift/HybridHeartbeatSeriesModuleSpec_cxx.swift +0 -1
  83. package/nitrogen/generated/ios/swift/HybridMedicationModuleSpec.swift +0 -1
  84. package/nitrogen/generated/ios/swift/HybridMedicationModuleSpec_cxx.swift +0 -1
  85. package/nitrogen/generated/ios/swift/HybridQuantityTypeModuleSpec.swift +0 -1
  86. package/nitrogen/generated/ios/swift/HybridQuantityTypeModuleSpec_cxx.swift +0 -1
  87. package/nitrogen/generated/ios/swift/HybridStateOfMindModuleSpec.swift +0 -1
  88. package/nitrogen/generated/ios/swift/HybridStateOfMindModuleSpec_cxx.swift +0 -1
  89. package/nitrogen/generated/ios/swift/HybridWorkoutProxySpec.swift +0 -1
  90. package/nitrogen/generated/ios/swift/HybridWorkoutProxySpec_cxx.swift +0 -1
  91. package/nitrogen/generated/ios/swift/HybridWorkoutsModuleSpec.swift +0 -1
  92. package/nitrogen/generated/ios/swift/HybridWorkoutsModuleSpec_cxx.swift +0 -1
  93. package/nitrogen/generated/ios/swift/IdentifierWithUnit.swift +1 -0
  94. package/nitrogen/generated/ios/swift/IntervalComponents.swift +1 -0
  95. package/nitrogen/generated/ios/swift/LocationForSaving.swift +1 -0
  96. package/nitrogen/generated/ios/swift/MedicationConcept.swift +1 -0
  97. package/nitrogen/generated/ios/swift/MedicationDoseEvent.swift +1 -0
  98. package/nitrogen/generated/ios/swift/MedicationDoseEventsWithAnchorResponse.swift +1 -0
  99. package/nitrogen/generated/ios/swift/OnChangeCallbackArgs.swift +1 -0
  100. package/nitrogen/generated/ios/swift/PredicateWithMetadataKey.swift +1 -0
  101. package/nitrogen/generated/ios/swift/Quantity.swift +1 -0
  102. package/nitrogen/generated/ios/swift/QuantityDateInterval.swift +1 -0
  103. package/nitrogen/generated/ios/swift/QuantitySample.swift +1 -0
  104. package/nitrogen/generated/ios/swift/QuantitySampleForSaving.swift +1 -0
  105. package/nitrogen/generated/ios/swift/QuantitySamplesWithAnchorResponse.swift +1 -0
  106. package/nitrogen/generated/ios/swift/QueryCorrelationSamplesWithAnchorResponse.swift +1 -0
  107. package/nitrogen/generated/ios/swift/QueryOptionsWithAnchor.swift +1 -0
  108. package/nitrogen/generated/ios/swift/QueryOptionsWithAnchorAndUnit.swift +1 -0
  109. package/nitrogen/generated/ios/swift/QueryOptionsWithSortOrder.swift +1 -0
  110. package/nitrogen/generated/ios/swift/QueryOptionsWithSortOrderAndUnit.swift +1 -0
  111. package/nitrogen/generated/ios/swift/QueryStatisticsResponse.swift +1 -0
  112. package/nitrogen/generated/ios/swift/QueryStatisticsResponseFromSingleSource.swift +1 -0
  113. package/nitrogen/generated/ios/swift/QueryWorkoutSamplesWithAnchorResponse.swift +1 -0
  114. package/nitrogen/generated/ios/swift/RelatedCoding.swift +1 -0
  115. package/nitrogen/generated/ios/swift/SampleType.swift +1 -0
  116. package/nitrogen/generated/ios/swift/Source.swift +1 -0
  117. package/nitrogen/generated/ios/swift/SourceRevision.swift +1 -0
  118. package/nitrogen/generated/ios/swift/StateOfMindSample.swift +1 -0
  119. package/nitrogen/generated/ios/swift/StateOfMindSamplesWithAnchorResponse.swift +1 -0
  120. package/nitrogen/generated/ios/swift/StatisticsQueryOptions.swift +1 -0
  121. package/nitrogen/generated/ios/swift/UserAnnotatedMedication.swift +1 -0
  122. package/nitrogen/generated/ios/swift/WorkoutActivity.swift +1 -0
  123. package/nitrogen/generated/ios/swift/WorkoutConfiguration.swift +1 -0
  124. package/nitrogen/generated/ios/swift/WorkoutDurationPredicate.swift +1 -0
  125. package/nitrogen/generated/ios/swift/WorkoutEvent.swift +1 -0
  126. package/nitrogen/generated/ios/swift/WorkoutPlan.swift +1 -0
  127. package/nitrogen/generated/ios/swift/WorkoutQueryOptions.swift +1 -0
  128. package/nitrogen/generated/ios/swift/WorkoutQueryOptionsWithAnchor.swift +1 -0
  129. package/nitrogen/generated/ios/swift/WorkoutRoute.swift +1 -0
  130. package/nitrogen/generated/ios/swift/WorkoutRouteLocation.swift +1 -0
  131. package/nitrogen/generated/ios/swift/WorkoutSample.swift +1 -0
  132. package/nitrogen/generated/ios/swift/WorkoutTotals.swift +1 -0
  133. package/package.json +4 -4
@@ -22,6 +22,8 @@ Pod::Spec.new do |s|
22
22
  "cpp/**/*.{hpp,cpp}",
23
23
  ]
24
24
 
25
+ s.public_header_files = "ios/**/*.h"
26
+
25
27
  s.pod_target_xcconfig = {
26
28
  # C++ compiler flags, mainly for folly.
27
29
  "GCC_PREPROCESSOR_DEFINITIONS" => "$(inherited) FOLLY_NO_CONFIG FOLLY_CFG_NO_COROUTINES"
@@ -19,7 +19,7 @@ private var quantityTypeUnitCache = [HKQuantityType: HKUnit]()
19
19
 
20
20
  func getUnitToUse(unitOverride: String?, quantityType: HKQuantityType) async throws -> HKUnit {
21
21
  if let unitOverride = unitOverride {
22
- let unit = HKUnit(from: unitOverride)
22
+ let unit = try parseUnitStringSafe(unitOverride)
23
23
 
24
24
  if !quantityType.is(compatibleWith: unit) {
25
25
  throw runtimeErrorWithPrefix(
@@ -137,8 +137,11 @@ class CorrelationTypeModule: HybridCorrelationTypeModuleSpec {
137
137
  continue
138
138
  }
139
139
 
140
- let unit = HKUnit(from: quantitySample.unit)
141
- let quantity = HKQuantity(unit: unit, doubleValue: quantitySample.quantity)
140
+ let unit = try parseUnitStringSafe(quantitySample.unit)
141
+ let quantity = HKQuantity(
142
+ unit: unit,
143
+ doubleValue: quantitySample.quantity
144
+ )
142
145
  let hkQuantitySample = HKQuantitySample(
143
146
  type: quantityType,
144
147
  quantity: quantity,
@@ -0,0 +1,17 @@
1
+ #import <Foundation/Foundation.h>
2
+ #import <HealthKit/HealthKit.h>
3
+
4
+ NS_INLINE HKUnit * _Nullable HKUnitFromStringCatchingExceptions(NSString * _Nonnull unitString, NSError * _Nullable * _Nullable outError) {
5
+ if (outError) { *outError = nil; }
6
+ @try {
7
+ HKUnit *unit = [HKUnit unitFromString:unitString];
8
+ return unit;
9
+ }
10
+ @catch (NSException *exception) {
11
+ if (outError) {
12
+ NSDictionary *userInfo = exception.userInfo ?: @{};
13
+ *outError = [NSError errorWithDomain:exception.name code:0 userInfo:userInfo];
14
+ }
15
+ return nil;
16
+ }
17
+ }
package/ios/Helpers.swift CHANGED
@@ -9,6 +9,17 @@ import Foundation
9
9
  import HealthKit
10
10
  import NitroModules
11
11
 
12
+ func parseUnitStringSafe(_ unitString: String) throws -> HKUnit {
13
+ var err: NSError?
14
+ let unitOut = HKUnitFromStringCatchingExceptions(unitString, &err)
15
+
16
+ if let hkUnit = unitOut {
17
+ return hkUnit
18
+ }
19
+
20
+ throw runtimeErrorWithPrefix("Supplied invalid '\(unitString)' as HKUnit")
21
+ }
22
+
12
23
  func getQueryLimit(_ limit: Double) -> Int {
13
24
  if limit == .infinity || limit <= 0 || limit == .nan || limit == .signalingNaN {
14
25
  return HKObjectQueryNoLimit
@@ -355,39 +366,6 @@ func objectTypeFrom(objectTypeIdentifier: ObjectTypeIdentifier) throws -> HKObje
355
366
  "Failed initializing unrecognized objectType identifier " + typeIdentifier)
356
367
  }
357
368
 
358
- func hkStatisticsOptionsFromOptions(_ options: NSArray) -> HKStatisticsOptions {
359
- var opts = HKStatisticsOptions()
360
-
361
- for o in options {
362
- guard let str = o as? String else { continue }
363
-
364
- switch str {
365
- case "cumulativeSum":
366
- opts.insert(.cumulativeSum)
367
- case "discreteAverage":
368
- opts.insert(.discreteAverage)
369
- case "discreteMax":
370
- opts.insert(.discreteMax)
371
- case "discreteMin":
372
- opts.insert(.discreteMin)
373
- case "duration":
374
- if #available(iOS 13, *) {
375
- opts.insert(.duration)
376
- }
377
- case "mostRecent":
378
- if #available(iOS 13, *) {
379
- opts.insert(.mostRecent)
380
- }
381
- case "separateBySource":
382
- opts.insert(.separateBySource)
383
- default:
384
- continue
385
- }
386
- }
387
-
388
- return opts
389
- }
390
-
391
369
  func componentsFromInterval(_ interval: NSDictionary) -> DateComponents {
392
370
  let componentKeys: [String: WritableKeyPath<DateComponents, Int?>] = [
393
371
  "minute": \.minute,
@@ -443,3 +421,47 @@ func runtimeErrorWithPrefix(_ withMessage: String) -> Error {
443
421
  func warnWithPrefix(_ withMessage: String) {
444
422
  print("[react-native-healthkit] \(withMessage)")
445
423
  }
424
+
425
+ func buildStatisticsOptions(statistics: [StatisticsOptions], quantityType: HKQuantityType) -> HKStatisticsOptions {
426
+
427
+ // Build statistics options
428
+ var opts = HKStatisticsOptions()
429
+ opts.insert(.separateBySource)
430
+ for statistic in statistics {
431
+ if statistic == .cumulativesum {
432
+ if quantityType.aggregationStyle == .cumulative {
433
+ opts.insert(HKStatisticsOptions.cumulativeSum)
434
+ } else {
435
+ warnWithPrefix("buildStatisticsOptions: cumulativesum statistic requested for discrete quantity type \(quantityType.identifier)")
436
+ }
437
+
438
+ } else if statistic == .discreteaverage {
439
+ if quantityType.aggregationStyle != .cumulative {
440
+ opts.insert(HKStatisticsOptions.discreteAverage)
441
+ } else {
442
+ warnWithPrefix("buildStatisticsOptions: discreteaverage statistic requested for cumulative quantity type \(quantityType.identifier)")
443
+ }
444
+ } else if statistic == .discretemax {
445
+ if quantityType.aggregationStyle != .cumulative {
446
+ opts.insert(HKStatisticsOptions.discreteMax)
447
+ } else {
448
+ warnWithPrefix("buildStatisticsOptions: discretemax statistic requested for cumulative quantity type \(quantityType.identifier)")
449
+ }
450
+ } else if statistic == .discretemin {
451
+ if quantityType.aggregationStyle != .cumulative {
452
+ opts.insert(HKStatisticsOptions.discreteMin)
453
+ } else {
454
+ warnWithPrefix("buildStatisticsOptions: discretemin statistic requested for cumulative quantity type \(quantityType.identifier)")
455
+ }
456
+ }
457
+ if #available(iOS 13, *) {
458
+ if statistic == .duration {
459
+ opts.insert(HKStatisticsOptions.duration)
460
+ }
461
+ if statistic == .mostrecent {
462
+ opts.insert(HKStatisticsOptions.mostRecent)
463
+ }
464
+ }
465
+ }
466
+ return opts
467
+ }
@@ -21,7 +21,7 @@ func queryStatisticsForQuantityInternal(
21
21
  let query = HKStatisticsQuery.init(
22
22
  quantityType: quantityType,
23
23
  quantitySamplePredicate: predicate,
24
- options: buildStatisticsOptions(statistics: statistics)
24
+ options: buildStatisticsOptions(statistics: statistics, quantityType: quantityType)
25
25
  ) { (_, stats: HKStatistics?, error: Error?) in
26
26
  DispatchQueue.main.async {
27
27
  if let error = error {
@@ -49,6 +49,10 @@ func serializeStatistics(gottenStats: HKStatistics, unit: HKUnit) -> QueryStatis
49
49
  response.startDate = gottenStats.startDate
50
50
  response.endDate = gottenStats.endDate
51
51
 
52
+ response.sources = gottenStats.sources?.map { source in
53
+ return serializeSource(source)
54
+ } ?? []
55
+
52
56
  if let averageQuantity = gottenStats.averageQuantity() {
53
57
  response.averageQuantity = Quantity(
54
58
  unit: unit.unitString,
@@ -131,9 +135,7 @@ func queryStatisticsCollectionForQuantityInternal(
131
135
  }
132
136
 
133
137
  // Build statistics options
134
- let opts = buildStatisticsOptions(statistics: statistics)
135
-
136
- let unit = try await getUnitToUse(unitOverride: options?.unit, quantityType: quantityType)
138
+ let opts = buildStatisticsOptions(statistics: statistics, quantityType: quantityType)
137
139
 
138
140
  return try await withCheckedThrowingContinuation { continuation in
139
141
  let query = HKStatisticsCollectionQuery.init(
@@ -250,31 +252,6 @@ func getAnyMapValue(_ anyMap: AnyMap, key: String) -> Any? {
250
252
  return nil
251
253
  }
252
254
 
253
- func buildStatisticsOptions(statistics: [StatisticsOptions]) -> HKStatisticsOptions {
254
- // Build statistics options
255
- var opts = HKStatisticsOptions()
256
- for statistic in statistics {
257
- if statistic == .cumulativesum {
258
- opts.insert(HKStatisticsOptions.cumulativeSum)
259
- } else if statistic == .discreteaverage {
260
- opts.insert(HKStatisticsOptions.discreteAverage)
261
- } else if statistic == .discretemax {
262
- opts.insert(HKStatisticsOptions.discreteMax)
263
- } else if statistic == .discretemin {
264
- opts.insert(HKStatisticsOptions.discreteMin)
265
- }
266
- if #available(iOS 13, *) {
267
- if statistic == .duration {
268
- opts.insert(HKStatisticsOptions.duration)
269
- }
270
- if statistic == .mostrecent {
271
- opts.insert(HKStatisticsOptions.mostRecent)
272
- }
273
- }
274
- }
275
- return opts
276
- }
277
-
278
255
  /// Handles HealthKit's `errorNoData` by resuming the continuation with a fallback value if provided,
279
256
  /// otherwise resumes with `nil` for Optional result types. For other errors, resumes by throwing.
280
257
  /// - Parameters:
@@ -361,11 +338,14 @@ class QuantityTypeModule: HybridQuantityTypeModuleSpec {
361
338
  func isQuantityCompatibleWithUnit(identifier: QuantityTypeIdentifier, unit: String) throws -> Bool {
362
339
  let sampleType = try initializeQuantityType(identifier.stringValue)
363
340
 
364
- return sampleType.is(compatibleWith: HKUnit.init(from: unit))
341
+ let hkUnit = try parseUnitStringSafe(unit)
342
+
343
+ return sampleType.is(compatibleWith: hkUnit)
365
344
  }
366
345
 
367
346
  func queryStatisticsForQuantity(
368
- identifier: QuantityTypeIdentifier, statistics: [StatisticsOptions],
347
+ identifier: QuantityTypeIdentifier,
348
+ statistics: [StatisticsOptions],
369
349
  options: StatisticsQueryOptions?
370
350
  ) -> Promise<QueryStatisticsResponse> {
371
351
  return Promise.async {
@@ -464,7 +444,7 @@ class QuantityTypeModule: HybridQuantityTypeModuleSpec {
464
444
  metadata: AnyMap?
465
445
  ) -> Promise<QuantitySample?> {
466
446
  return Promise.async {
467
- let unit = HKUnit.init(from: unit)
447
+ let unit = try parseUnitStringSafe(unit)
468
448
  let quantity = HKQuantity.init(unit: unit, doubleValue: value)
469
449
  let typeIdentifier = HKQuantityType(
470
450
  HKQuantityTypeIdentifier(rawValue: identifier.stringValue)
@@ -104,7 +104,7 @@ class WorkoutsModule: HybridWorkoutsModuleSpec {
104
104
  let quantityVal = quantity.quantity
105
105
  let quantityStart = quantity.startDate
106
106
  let quantityEnd = quantity.endDate
107
- let unit = HKUnit.init(from: unitStr)
107
+ let unit = try parseUnitStringSafe(unitStr)
108
108
  let quantity = HKQuantity.init(unit: unit, doubleValue: quantityVal)
109
109
 
110
110
  if quantity.is(compatibleWith: HKUnit.kilocalorie()) {
@@ -21,6 +21,7 @@
21
21
  #include "HybridWorkoutProxySpecSwift.hpp"
22
22
  #include "HybridWorkoutsModuleSpecSwift.hpp"
23
23
  #include "ReactNativeHealthkit-Swift-Cxx-Umbrella.hpp"
24
+ #include <NitroModules/NitroDefines.hpp>
24
25
 
25
26
  namespace margelo::nitro::healthkit::bridge::swift {
26
27
 
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,6 +5,7 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
11
  /**
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: AuthorizationRequestStatus) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: BiologicalSex) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: BloodType) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: CategorySamplesWithAnchorResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: ElectrocardiogramSamplesWithAnchorResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: FitzpatrickSkinType) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: HeartbeatSeriesSamplesWithAnchorResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: MedicationDoseEventsWithAnchorResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ args: OnChangeCallbackArgs) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: QuantitySamplesWithAnchorResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: QueryCorrelationSamplesWithAnchorResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: QueryStatisticsResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: QueryWorkoutSamplesWithAnchorResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: StateOfMindSamplesWithAnchorResponse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: WheelchairUse) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: Bool) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: Double) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ error: Error) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: CategorySample?) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.
@@ -5,9 +5,9 @@
5
5
  /// Copyright © 2025 Marc Rousavy @ Margelo
6
6
  ///
7
7
 
8
+ import Foundation
8
9
  import NitroModules
9
10
 
10
-
11
11
  /**
12
12
  * Wraps a Swift `(_ value: CorrelationSample?) -> Void` as a class.
13
13
  * This class can be used from C++, e.g. to wrap the Swift closure as a `std::function`.