From f50353c643b5d23fad5064e353356abb94e382c8 Mon Sep 17 00:00:00 2001 From: CelloSerenity <195480169+CelloSerenity@users.noreply.github.com> Date: Sun, 27 Sep 2026 13:26:07 -0600 Subject: [PATCH] perf: reduce redundant device queries --- .../InstalledAppsViewModel.swift | 31 ++++++++++++++----- StikDebug/Views/HomeView.swift | 15 --------- 2 files changed, 24 insertions(+), 22 deletions(-) diff --git a/StikDebug/Features/InstalledApps/InstalledAppsViewModel.swift b/StikDebug/Features/InstalledApps/InstalledAppsViewModel.swift index 5b36ebb..7a1ecb1 100644 --- a/StikDebug/Features/InstalledApps/InstalledAppsViewModel.swift +++ b/StikDebug/Features/InstalledApps/InstalledAppsViewModel.swift @@ -21,6 +21,8 @@ final class InstalledAppsViewModel: ObservableObject { private let cacheKeyNonDebuggable = "cachedNonDebuggableApps" private let cacheKeySystem = "cachedSystemApps" private var cancellables: Set = [] + private var refreshInProgress = false + private var refreshPending = false init() { loadCachedApps() @@ -32,6 +34,12 @@ final class InstalledAppsViewModel: ObservableObject { } func refreshAppLists() { + guard !refreshInProgress else { + refreshPending = true + return + } + + refreshInProgress = true isLoading = true lastError = nil @@ -47,6 +55,11 @@ final class InstalledAppsViewModel: ObservableObject { debuggable: debuggable, hiddenSystem: hiddenSystem ) + self.cacheApps( + debuggable: debuggable, + nonDebuggable: classifiedApps.nonDebuggable, + system: classifiedApps.system + ) DispatchQueue.main.async { self.apply( @@ -54,22 +67,26 @@ final class InstalledAppsViewModel: ObservableObject { nonDebuggable: classifiedApps.nonDebuggable, system: classifiedApps.system ) - self.isLoading = false - self.cacheApps( - debuggable: debuggable, - nonDebuggable: classifiedApps.nonDebuggable, - system: classifiedApps.system - ) + self.finishRefresh() } } catch { DispatchQueue.main.async { - self.isLoading = false self.lastError = error.localizedDescription + self.finishRefresh() } } } } + private func finishRefresh() { + refreshInProgress = false + isLoading = false + + guard refreshPending else { return } + refreshPending = false + refreshAppLists() + } + func displayName(for bundleID: String) -> String? { debuggableApps[bundleID] ?? systemApps[bundleID] ?? nonDebuggableApps[bundleID] } diff --git a/StikDebug/Views/HomeView.swift b/StikDebug/Views/HomeView.swift index ab605c3..48ec835 100644 --- a/StikDebug/Views/HomeView.swift +++ b/StikDebug/Views/HomeView.swift @@ -12,8 +12,6 @@ struct HomeView: View { @AppStorage("bundleID") private var bundleID: String = "" @AppStorage(UserDefaults.Keys.confirmExternalJITRequests) private var confirmExternalJITRequests = true - @ObservedObject private var mounting = MountingProgress.shared - @State private var hasAppeared = false @State private var pendingJITEnableConfiguration: JITEnableConfiguration? @State private var isShowingPairingFilePicker = false @@ -22,8 +20,6 @@ struct HomeView: View { @State private var pendingLiveContainerApp: LiveContainerApp? @State private var scriptRunModel: RunJSViewModel? - private let timer = Timer.publish(every: 1, on: .main, in: .common).autoconnect() - private struct DebugFeedback: Identifiable { let id = UUID() let message: String @@ -53,9 +49,6 @@ struct HomeView: View { } .onAppear(perform: handleAppear) .onReceive(NotificationCenter.default.publisher(for: .intentJSScriptReady), perform: handleScriptReadyNotification) - .onReceive(timer) { _ in - refreshMountStatusIfNeeded() - } .onOpenURL { url in handleExternalURL(url) } @@ -130,7 +123,6 @@ struct HomeView: View { private func handleAppear() { startTunnelInBackground() - MountingProgress.shared.checkforMounted() hasAppeared = true if let config = pendingJITEnableConfiguration { @@ -153,13 +145,6 @@ struct HomeView: View { scriptRunModel = model } - private func refreshMountStatusIfNeeded() { - guard mounting.mountingThread == nil, !mounting.coolisMounted else { - return - } - MountingProgress.shared.checkforMounted() - } - private func importPairingFile(_ result: Result) { switch result { case .success(let url):