0

When I'm launching Health application, I can see the whole distance I've walked or ran for a period of time and see details with separate events. But when I'm trying to get all walking workouts in my application using HealthKit, there are no samples at all.

Does it mean that I can't access workouts that were saved by Apple's Health application or they are not workouts?

Here is my code:

func fetchData() {

    guard HKHealthStore.isHealthDataAvailable() else {
        throwError(HealthTrackerError.notAvailableOnDevice)
        return
    }

    let type = HKWorkoutType.workoutType()

    let completion = { [weak self] (isAuthorized: Bool, error: Error?) in
        DispatchQueue.main.async { [weak self] in
            isAuthorized ? self?.fetchData(type) : self?.throwError(error)
        }
    }

    switch HKHealthStore().authorizationStatus(for: type) {
    case .notDetermined:
        HKHealthStore().requestAuthorization(toShare: [type],
                                             read: [type],
                                             completion: completion)
    case .sharingAuthorized:
        fetchData(type)
    case .sharingDenied:
        throwError(HealthTrackerError.accessDenied)
    }
}

private func fetchData(_ workout: HKWorkoutType) {

    let predicate = HKQuery.predicateForWorkouts(with: .walking)

    let query = HKSampleQuery(sampleType: workout, predicate: predicate, limit: 0, sortDescriptors: nil) { [weak self] (query, samples, error) in

        guard let workouts = samples as? [HKWorkout] else {
            self?.throwError(error)
            return
        }

        // No workouts were found

        self?.values = workouts
            .map { $0.totalEnergyBurned?.doubleValue(for: HKUnit.kilocalorie()) }
            .filter { $0 != nil }
            .map { $0! }
    }

    HKHealthStore().execute(query)
}

Thanks to MwcsMac for the link, here is updated code that works for me.

func fetchData() {

    guard HKHealthStore.isHealthDataAvailable() else {
        throwError(HealthTrackerError.notAvailableOnDevice)
        return
    }

    guard let type = HKQuantityType.quantityType(forIdentifier: .distanceWalkingRunning) else {
        throwError(HealthTrackerError.dataTypeNotAvailable)
        return
    }

    let completion = { [weak self] (isAuthorized: Bool, error: Error?) in
        DispatchQueue.main.async { [weak self] in
            isAuthorized ? self?.fetchData(type) : self?.throwError(error)
        }
    }

    switch HKHealthStore().authorizationStatus(for: type) {
    case .notDetermined:
        HKHealthStore().requestAuthorization(toShare: [type],
                                             read: [type],
                                             completion: completion)
    case .sharingAuthorized:
        fetchData(type)
    case .sharingDenied:
        throwError(HealthTrackerError.accessDenied)
    }
}

private func fetchData(_ quantityType: HKQuantityType) {

    let predicate = HKQuery.predicateForSamples(withStart: startDate,
                                                end: currentDate,
                                                options: [])


    let query = HKSampleQuery(sampleType: quantityType, predicate: predicate, limit: HKObjectQueryNoLimit, sortDescriptors: nil) { [weak self] (query, samples, error) in

        guard let samples = samples as? [HKQuantitySample] else {
            self?.throwError(error)
            return
        }

        self?.values = samples.map { $0.quantity.doubleValue(for: HKUnit.meter()) }
    }

    HKHealthStore().execute(query)
}
  • I use your code and it produces results. Are you running this on a device? Also have you confirmed that you have walking workouts logged on your device? – MwcsMac Feb 13 '19 at 19:24
  • Yes, I’m running it on my iPhone 6s+ and I have recorded data in Health app. I didn’t add workouts before. All data was written by my iPhone automatically. – Nikita Tepliakov Feb 13 '19 at 20:11
  • I mean Health application in my device has walking+running data. I didn’t add any workouts manually. – Nikita Tepliakov Feb 13 '19 at 20:19
  • 1
    If you are looking for the auto recored data which doesn't logged as a workout. Then you need to look at this [stackoverflow.com/a/52206863/4080925](https://stackoverflow.com/a/52206863/4080925) – MwcsMac Feb 13 '19 at 20:46
  • Thank you, that link solved my problem. Now, I can fetch separate walking and running samples. – Nikita Tepliakov Feb 14 '19 at 09:56

0 Answers0