HKObserverQuery only runs when the application is reopened

658 Views Asked by At

So I've been following the instructions in this answer... Healthkit background delivery when app is not running

The code runs fine and works whilst the application is open and says that background delivery is successful, however when I test the application by walking around and changing the clock on the device to an hour forward I do not receive any logs to let me know it has run. However, if I open the application again the observer query runs.

private func checkAuthorization(){
    let healthDataToRead = Set(arrayLiteral: self.distanceQuantityType!)


    healthKitStore.requestAuthorization(toShare: nil, read: healthDataToRead) { (success, error) in
        if error != nil {
            print(error?.localizedDescription)
            print("There was an error requesting Authorization to use Health App")
        }
        if success {
            print("success")

        }
    }

}
public func enableBackgroundDelivery() {

    self.checkAuthorization()
    self.healthKitStore.enableBackgroundDelivery(for: self.distanceQuantityType!, frequency: .hourly) { (success, error) in
        if success{
            print("Background delivery of steps. Success = \(success)")

        }

        if let error = error {
            print("Background delivery of steps failed = \(error.localizedDescription)")
        }
    }



}

func observeDistance(_ handler:@escaping (_ distance: Double) -> Void) {

    let updateHandler: (HKObserverQuery?, HKObserverQueryCompletionHandler?, Error?) -> Void = { query, completion, error in
        if !(error != nil) {
            print("got an update")
            completion!()
        } else {
            print("observer query returned error: \(error)")
        }
    }

    let query = HKObserverQuery(sampleType: self.distanceQuantityType!, predicate: nil, updateHandler: updateHandler)
    self.healthKitStore.execute(query)
}

The query is initialised in the appDelegate method didFinishLaunching

1

There are 1 best solutions below

1
On

This particular HealthKitQuery is asynchronous. You should wait until it finishes processing.

However, this case is not possible in didFinishLaunching. The application just ended execution and there is not enough time to process the query.

I would seriously suggest to rethink the logic behind the operation of your code. A good way to solve this would be to put the request elsewhere, preferrably after the needed operations were completed.