StatStateModel.swift 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990
  1. import CoreData
  2. import Foundation
  3. import SwiftUI
  4. import Swinject
  5. extension Stat {
  6. final class StateModel: BaseStateModel<Provider> {
  7. @Injected() var settings: SettingsManager!
  8. @Published var highLimit: Decimal = 10 / 0.0555
  9. @Published var lowLimit: Decimal = 4 / 0.0555
  10. @Published var overrideUnit: Bool = false
  11. @Published var layingChart: Bool = false
  12. @Published var units: GlucoseUnits = .mmolL
  13. @Published var glucoseFromPersistence: [GlucoseStored] = []
  14. @Published var selectedDuration: Duration = .Today
  15. private let context = CoreDataStack.shared.newTaskContext()
  16. private let viewContext = CoreDataStack.shared.persistentContainer.viewContext
  17. enum Duration: String, CaseIterable, Identifiable {
  18. case Today
  19. case Day
  20. case Week
  21. case Month
  22. case Total
  23. var id: Self { self }
  24. }
  25. override func subscribe() {
  26. /// Default is today
  27. setupGlucoseArray(for: .Today)
  28. highLimit = settingsManager.settings.high
  29. lowLimit = settingsManager.settings.low
  30. units = settingsManager.settings.units
  31. overrideUnit = settingsManager.settings.overrideHbA1cUnit
  32. layingChart = settingsManager.settings.oneDimensionalGraph
  33. }
  34. func setupGlucoseArray(for duration: Duration) {
  35. Task {
  36. let ids = await self.fetchGlucose(for: duration)
  37. await updateGlucoseArray(with: ids)
  38. }
  39. }
  40. private func fetchGlucose(for duration: Duration) async -> [NSManagedObjectID] {
  41. await context.perform {
  42. let predicate: NSPredicate
  43. switch duration {
  44. case .Day:
  45. predicate = NSPredicate.glucoseForStatsDay
  46. case .Week:
  47. predicate = NSPredicate.glucoseForStatsWeek
  48. case .Today:
  49. predicate = NSPredicate.glucoseForStatsToday
  50. case .Month:
  51. predicate = NSPredicate.glucoseForStatsMonth
  52. case .Total:
  53. predicate = NSPredicate.glucoseForStatsTotal
  54. }
  55. return CoreDataStack.shared.fetchEntities(
  56. ofType: GlucoseStored.self,
  57. onContext: self.context,
  58. predicate: predicate,
  59. key: "date",
  60. ascending: false,
  61. batchSize: 100,
  62. propertiesToFetch: ["glucose", "date"]
  63. ).map(\.objectID)
  64. }
  65. }
  66. @MainActor private func updateGlucoseArray(with IDs: [NSManagedObjectID]) {
  67. do {
  68. let glucoseObjects = try IDs.compactMap { id in
  69. try viewContext.existingObject(with: id) as? GlucoseStored
  70. }
  71. glucoseFromPersistence = glucoseObjects
  72. } catch {
  73. debugPrint(
  74. "Home State: \(#function) \(DebuggingIdentifiers.failed) error while updating the glucose array: \(error.localizedDescription)"
  75. )
  76. }
  77. }
  78. }
  79. }