Tweak async for updater

This commit is contained in:
Max Goedjen 2025-01-05 00:37:03 -08:00
parent 8e707545d1
commit 304741e019
No known key found for this signature in database
3 changed files with 23 additions and 19 deletions

View File

@ -28,29 +28,31 @@ import Synchronization
testBuild = currentVersion == SemVer("0.0.0") testBuild = currentVersion == SemVer("0.0.0")
if checkOnLaunch { if checkOnLaunch {
// Don't do a launch check if the user hasn't seen the setup prompt explaining updater yet. // Don't do a launch check if the user hasn't seen the setup prompt explaining updater yet.
checkForUpdates() Task {
await checkForUpdates()
}
} }
let timer = Timer.scheduledTimer(withTimeInterval: checkFrequency, repeats: true) { _ in Task {
self.checkForUpdates() while !Task.isCancelled {
try? await Task.sleep(for: .seconds(Int(checkFrequency)))
await checkForUpdates()
}
} }
timer.tolerance = 60*60
} }
/// Manually trigger an update check. /// Manually trigger an update check.
public func checkForUpdates() { public func checkForUpdates() async {
URLSession.shared.dataTask(with: Constants.updateURL) { data, _, _ in guard let (data, _) = try? await URLSession.shared.data(from: Constants.updateURL) else { return }
guard let data = data else { return } guard let releases = try? JSONDecoder().decode([Release].self, from: data) else { return }
guard let releases = try? JSONDecoder().decode([Release].self, from: data) else { return } await evaluate(releases: releases)
self.evaluate(releases: releases)
}.resume()
} }
/// Ignores a specified release. `update` will be nil if the user has ignored the latest available release. /// Ignores a specified release. `update` will be nil if the user has ignored the latest available release.
/// - Parameter release: The release to ignore. /// - Parameter release: The release to ignore.
public func ignore(release: Release) { public func ignore(release: Release) async {
guard !release.critical else { return } guard !release.critical else { return }
defaults.set(true, forKey: release.name) defaults.set(true, forKey: release.name)
Task { @MainActor in await MainActor.run {
_update.withLock { value in _update.withLock { value in
value = nil value = nil
} }
@ -63,7 +65,7 @@ extension Updater {
/// Evaluates the available downloadable releases, and selects the newest non-prerelease release that the user is able to run. /// Evaluates the available downloadable releases, and selects the newest non-prerelease release that the user is able to run.
/// - Parameter releases: An array of ``Release`` objects. /// - Parameter releases: An array of ``Release`` objects.
func evaluate(releases: [Release]) { func evaluate(releases: [Release]) async {
guard let release = releases guard let release = releases
.sorted() .sorted()
.reversed() .reversed()
@ -73,7 +75,7 @@ extension Updater {
guard !release.prerelease else { return } guard !release.prerelease else { return }
let latestVersion = SemVer(release.name) let latestVersion = SemVer(release.name)
if latestVersion > currentVersion { if latestVersion > currentVersion {
Task { @MainActor in await MainActor.run {
_update.withLock { value in _update.withLock { value in
value = release value = release
} }

View File

@ -72,8 +72,8 @@ import Foundation
Release(name: "1.0.2", prerelease: false, html_url: URL(string: "https://example.com")!, body: "Emergency patch! Minimum macOS Version: 1.2.3"), Release(name: "1.0.2", prerelease: false, html_url: URL(string: "https://example.com")!, body: "Emergency patch! Minimum macOS Version: 1.2.3"),
] ]
updater.evaluate(releases: releases) await updater.evaluate(releases: releases)
try await Task.sleep(nanoseconds: 500) try await Task.sleep(nanoseconds: 1)
#expect(updater.update == two) #expect(updater.update == two)
} }
@ -89,8 +89,8 @@ import Foundation
Release(name: "2.0.0", prerelease: false, html_url: URL(string: "https://example.com")!, body: "2.0 available! Minimum macOS Version: 2.2.3"), Release(name: "2.0.0", prerelease: false, html_url: URL(string: "https://example.com")!, body: "2.0 available! Minimum macOS Version: 2.2.3"),
Release(name: "1.0.2", prerelease: false, html_url: URL(string: "https://example.com")!, body: "Emergency patch! Minimum macOS Version: 1.2.3"), Release(name: "1.0.2", prerelease: false, html_url: URL(string: "https://example.com")!, body: "Emergency patch! Minimum macOS Version: 1.2.3"),
] ]
updater.evaluate(releases: releases) await updater.evaluate(releases: releases)
try await Task.sleep(nanoseconds: 500) try await Task.sleep(nanoseconds: 1)
#expect(updater.update == oneOhTwo) #expect(updater.update == oneOhTwo)
} }

View File

@ -18,7 +18,9 @@ struct UpdateDetailView<UpdaterType: Updater>: View {
HStack { HStack {
if !update.critical { if !update.critical {
Button("update_ignore_button") { Button("update_ignore_button") {
updater.ignore(release: update) Task {
await updater.ignore(release: update)
}
} }
Spacer() Spacer()
} }