I am trying to read the latest heart rate using HealthKit. My script is working fine, however when I try to return an integer value from my function it always returns 0 (the default value of latestHeartRateBPM), even though it is being mutated.
func getLatestHeartRate() -> Int {
var latestHeartRateBPM = 0
guard let sampleType = HKObjectType.quantityType(forIdentifier: .heartRate) else {
return 0
}
let startDate = Calendar.current.date(byAdding: .month, value: -1, to: Date())
let predicate = HKQuery.predicateForSamples(withStart: startDate, end: Date(), options: .strictEndDate)
let sortDescriptor = NSSortDescriptor(key: HKSampleSortIdentifierStartDate, ascending: false)
let query = HKSampleQuery(sampleType: sampleType, predicate: predicate, limit: Int(HKObjectQueryNoLimit), sortDescriptors: [sortDescriptor]) { (sample, result, error) in
guard error == nil else {
return
}
let data = result![0] as!HKQuantitySample
let unit = HKUnit(from: "count/s")
let latestHeartRateBPS = data.quantity.doubleValue(for: unit)
latestHeartRateBPM = Int(ceil(latestHeartRateBPS * 60))
}
healthStore?.execute(query)
return latestHeartRateBPM
}
As let query = HKSampleQuery(sampleType: sampleType, predicate: predicate, limit: Int(HKObjectQueryNoLimit), sortDescriptors: [sortDescriptor]) { (sample, result, error) in
is an asynchronous part , you need a completion
func getLatestHeartRate(completion:@escaping((Int?) -> ())) {
guard let sampleType = HKObjectType.quantityType(forIdentifier: .heartRate) else {
completion(nil)
}
let startDate = Calendar.current.date(byAdding: .month, value: -1, to: Date())
let predicate = HKQuery.predicateForSamples(withStart: startDate, end: Date(), options: .strictEndDate)
let sortDescriptor = NSSortDescriptor(key: HKSampleSortIdentifierStartDate, ascending: false)
let query = HKSampleQuery(sampleType: sampleType, predicate: predicate, limit: Int(HKObjectQueryNoLimit), sortDescriptors: [sortDescriptor]) { (sample, result, error) in
guard error == nil else {
completion(nil)
return
}
let data = result![0] as!HKQuantitySample
let unit = HKUnit(from: "count/s")
let latestHeartRateBPS = data.quantity.doubleValue(for: unit)
let latestHeartRateBPM = Int(ceil(latestHeartRateBPS * 60))
completion(latestHeartRateBPM)
}
healthStore?.execute(query)
}
Usage
getLatestHeartRate() { res in
print(res)
}