mirror of
https://github.com/home-assistant/iOS.git
synced 2026-02-23 10:33:13 -06:00
## Summary When the Local Push extension is running (when we're on Wi-Fi in an SSID marked as 'Internal' and location is set to Always), we're given a persistent opportunity to do work. When we're running, we now update sensors on a regular interval. ## Link to pull request in Documentation repository Documentation: home-assistant/companion.home-assistant#753 ## Any other notes Updating the metadata/sensors every 5 minutes (by default) should have minimal, if any, battery implications. This follows the same setting as the "Periodic" timer which we use for foreground updates.
67 lines
2.3 KiB
Swift
67 lines
2.3 KiB
Swift
#if os(iOS)
|
|
import Foundation
|
|
import PromiseKit
|
|
import UIKit
|
|
|
|
public class PeriodicUpdateManager {
|
|
public let applicationStateGetter: () -> UIApplication.State
|
|
public init(applicationStateGetter: @escaping () -> UIApplication.State) {
|
|
self.applicationStateGetter = applicationStateGetter
|
|
}
|
|
|
|
private var periodicUpdateTimer: Timer? {
|
|
willSet {
|
|
if periodicUpdateTimer != newValue {
|
|
periodicUpdateTimer?.invalidate()
|
|
}
|
|
}
|
|
}
|
|
|
|
public static var supportsBackgroundPeriodicUpdates: Bool {
|
|
Current.isCatalyst || Current.isAppExtension
|
|
}
|
|
|
|
public func invalidatePeriodicUpdateTimer(forBackground: Bool = false) {
|
|
if !Self.supportsBackgroundPeriodicUpdates || !forBackground {
|
|
periodicUpdateTimer = nil
|
|
}
|
|
}
|
|
|
|
private func schedulePeriodicUpdateTimer() {
|
|
guard periodicUpdateTimer == nil || periodicUpdateTimer?.isValid == false else {
|
|
return
|
|
}
|
|
|
|
guard Self.supportsBackgroundPeriodicUpdates || applicationStateGetter() != .background else {
|
|
// it's fine to schedule, but we don't wanna fire two when we come back to foreground later
|
|
Current.Log.info("not scheduling periodic update; backgrounded")
|
|
return
|
|
}
|
|
|
|
guard let interval = Current.settingsStore.periodicUpdateInterval else {
|
|
Current.Log.info("not scheduling periodic update; disabled")
|
|
return
|
|
}
|
|
|
|
periodicUpdateTimer = Timer.scheduledTimer(withTimeInterval: interval, repeats: false) { [weak self] _ in
|
|
self?.connectAPI(reason: .periodic)
|
|
}
|
|
}
|
|
|
|
public func connectAPI(reason: HomeAssistantAPI.ConnectReason) {
|
|
Current.backgroundTask(withName: "connect-api") { _ in
|
|
when(resolved: Current.apis.map { api in
|
|
api.Connect(reason: reason)
|
|
}).asVoid()
|
|
}.done {
|
|
Current.Log.info("Connect finished for reason \(reason)")
|
|
}.catch { error in
|
|
// if the error is e.g. token is invalid, we'll force onboarding through status-code-watching mechanisms
|
|
Current.Log.error("Couldn't connect for reason \(reason): \(error)")
|
|
}.finally {
|
|
self.schedulePeriodicUpdateTimer()
|
|
}
|
|
}
|
|
}
|
|
#endif
|