Digital PCT265 story ONEAPP-7249 - Polling behavior fixes and logging for clarity.
This commit is contained in:
parent
0ab05f4206
commit
3f77a261bc
@ -0,0 +1,9 @@
|
|||||||
|
//
|
||||||
|
// MoleculeComparisonProtocol.swift
|
||||||
|
// MVMCoreUI
|
||||||
|
//
|
||||||
|
// Created by Kyle Hedden on 4/29/24.
|
||||||
|
// Copyright © 2024 Verizon Wireless. All rights reserved.
|
||||||
|
//
|
||||||
|
|
||||||
|
import Foundation
|
||||||
@ -8,6 +8,7 @@
|
|||||||
|
|
||||||
import Foundation
|
import Foundation
|
||||||
import MVMCore
|
import MVMCore
|
||||||
|
import Combine
|
||||||
|
|
||||||
public class PollingBehaviorModel: PageBehaviorModelProtocol {
|
public class PollingBehaviorModel: PageBehaviorModelProtocol {
|
||||||
public class var identifier: String { "pollingBehavior" }
|
public class var identifier: String { "pollingBehavior" }
|
||||||
@ -47,15 +48,24 @@ public class PollingBehaviorModel: PageBehaviorModelProtocol {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public class PollingBehavior: NSObject, PageVisibilityBehavior {
|
extension PollingBehaviorModel: CustomDebugStringConvertible {
|
||||||
|
public var debugDescription: String {
|
||||||
|
return "\(Self.self) @ \(refreshInterval) firing \(self.refreshAction)"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class PollingBehavior: NSObject, PageVisibilityBehavior, PageMoleculeTransformationBehavior, CoreLogging {
|
||||||
|
|
||||||
|
public static var loggingCategory: String? { return String(describing: Self.self) }
|
||||||
|
|
||||||
var model: PollingBehaviorModel
|
var model: PollingBehaviorModel
|
||||||
var delegateObject: MVMCoreUIDelegateObject?
|
var delegateObject: MVMCoreUIDelegateObject?
|
||||||
var lastRefresh = Date.distantPast
|
var lastRefresh = Date() // Treat the last refresh as now on init. refreshOnShown will bypass otherwise.
|
||||||
var pollTimer: DispatchSourceTimer?
|
var pollTimer: DispatchSourceTimer?
|
||||||
|
var backgroundEventSubscripiton: AnyCancellable?
|
||||||
|
|
||||||
var remainingTimeToRefresh: TimeInterval {
|
var remainingTimeToRefresh: TimeInterval {
|
||||||
lastRefresh.timeIntervalSinceNow - model.refreshInterval
|
model.refreshInterval + lastRefresh.timeIntervalSinceNow // timeIntervalSinceNow in negative since earlier recording (--)
|
||||||
}
|
}
|
||||||
|
|
||||||
var firstTimeLoad = true
|
var firstTimeLoad = true
|
||||||
@ -71,6 +81,14 @@ public class PollingBehavior: NSObject, PageVisibilityBehavior {
|
|||||||
public required init(model: PageBehaviorModelProtocol, delegateObject: MVMCoreUIDelegateObject?) {
|
public required init(model: PageBehaviorModelProtocol, delegateObject: MVMCoreUIDelegateObject?) {
|
||||||
self.model = model as! PollingBehaviorModel
|
self.model = model as! PollingBehaviorModel
|
||||||
self.delegateObject = delegateObject
|
self.delegateObject = delegateObject
|
||||||
|
Self.debugLog("Initializing for \(model)")
|
||||||
|
}
|
||||||
|
|
||||||
|
public func onPageNew(rootMolecules: [any MoleculeModelProtocol], _ delegateObject: MVMCoreUIDelegateObject?) {
|
||||||
|
if let behaviorVC = delegateObject?.moleculeDelegate as? ViewController, MVMCoreUIUtility.getCurrentVisibleController() == behaviorVC {
|
||||||
|
// If behavior is initialized after the page is shown, we need to start the timer.
|
||||||
|
resumePollingTimer(withRemainingTime: refreshOnShown ? 0 : remainingTimeToRefresh, refreshAction: model.refreshAction, interval: model.refreshInterval)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public func onPageShown(_ delegateObject: MVMCoreUIDelegateObject?) {
|
public func onPageShown(_ delegateObject: MVMCoreUIDelegateObject?) {
|
||||||
@ -79,23 +97,43 @@ public class PollingBehavior: NSObject, PageVisibilityBehavior {
|
|||||||
|
|
||||||
public func onPageHidden(_ delegateObject: MVMCoreUIDelegateObject?) {
|
public func onPageHidden(_ delegateObject: MVMCoreUIDelegateObject?) {
|
||||||
pollTimer?.cancel()
|
pollTimer?.cancel()
|
||||||
|
backgroundEventSubscripiton = nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func resumePollingTimer(withRemainingTime timeRemaining: TimeInterval, refreshAction: ActionModelProtocol, interval: TimeInterval) {
|
func resumePollingTimer(withRemainingTime timeRemaining: TimeInterval, refreshAction: ActionModelProtocol, interval: TimeInterval) {
|
||||||
let delegateObject = delegateObject
|
let delegateObject = delegateObject
|
||||||
pollTimer?.cancel()
|
pollTimer?.cancel()
|
||||||
|
let pollingId = UUID().uuidString
|
||||||
|
debugLog("Scheduling timed event \(pollingId) in \(timeRemaining), interval: \(interval)")
|
||||||
pollTimer = DispatchSource.makeTimerSource()
|
pollTimer = DispatchSource.makeTimerSource()
|
||||||
pollTimer?.schedule(deadline: .now() + timeRemaining, repeating: interval)
|
pollTimer?.schedule(deadline: .now() + timeRemaining, repeating: interval)
|
||||||
pollTimer?.setEventHandler(qos:.utility) {
|
pollTimer?.setEventHandler(qos:.utility) { [weak self] in
|
||||||
Task {
|
guard let self = self else { return }
|
||||||
|
lastRefresh = Date()
|
||||||
|
Task { [weak self] in
|
||||||
|
self?.debugLog("Firing timed event \(pollingId), \(refreshAction)")
|
||||||
if let delegateActionHandler = delegateObject?.actionDelegate as? ActionDelegateProtocol {
|
if let delegateActionHandler = delegateObject?.actionDelegate as? ActionDelegateProtocol {
|
||||||
try? await delegateActionHandler.performAction(with: refreshAction, additionalData: nil, delegateObject: delegateObject)
|
try? await delegateActionHandler.performAction(with: refreshAction, additionalData: nil, delegateObject: delegateObject)
|
||||||
} else {
|
} else {
|
||||||
try? await MVMCoreActionHandler.shared()?.handleAction(with: refreshAction, additionalData: nil, delegateObject: delegateObject)
|
try? await MVMCoreActionHandler.shared()?.handleAction(with: refreshAction, additionalData: nil, delegateObject: delegateObject)
|
||||||
}
|
}
|
||||||
|
self?.debugLog("Finished timed event \(pollingId)")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
pollTimer?.resume()
|
pollTimer?.resume()
|
||||||
|
setupBackgroundingPause()
|
||||||
|
}
|
||||||
|
|
||||||
|
private func setupBackgroundingPause() {
|
||||||
|
backgroundEventSubscripiton = NotificationCenter.default.publisher(for: UIApplication.didEnterBackgroundNotification).sink { [weak self] _ in
|
||||||
|
guard let self = self else { return }
|
||||||
|
pollTimer?.cancel()
|
||||||
|
|
||||||
|
backgroundEventSubscripiton = NotificationCenter.default.publisher(for: UIApplication.didBecomeActiveNotification).sink { [weak self] _ in
|
||||||
|
guard let self = self else { return }
|
||||||
|
resumePollingTimer(withRemainingTime: remainingTimeToRefresh, refreshAction: model.refreshAction, interval: model.refreshInterval)
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
deinit {
|
deinit {
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user