mirror of
https://github.com/maxgoedjen/secretive.git
synced 2025-09-15 08:50:57 +00:00
.
This commit is contained in:
parent
2efba1bc21
commit
be28d59873
@ -46,22 +46,16 @@ import Observation
|
|||||||
|
|
||||||
/// Manually trigger an update check.
|
/// Manually trigger an update check.
|
||||||
public func checkForUpdates() async throws {
|
public func checkForUpdates() async throws {
|
||||||
let releaseData = try await withXPCCall(to: "com.maxgoedjen.Secretive.ReleasesDownloader", ReleasesDownloaderProtocol.self) {
|
let session: XPCSession
|
||||||
try await $0.downloadReleases()
|
if #available(macOS 26.0, *) {
|
||||||
|
session = try XPCSession(xpcService: "com.maxgoedjen.Secretive.ReleasesDownloader", requirement: .isFromSameTeam())
|
||||||
|
} else {
|
||||||
|
session = try XPCSession(xpcService: "com.maxgoedjen.Secretive.ReleasesDownloader")
|
||||||
}
|
}
|
||||||
let releases = try JSONDecoder().decode([Release].self, from: releaseData)
|
await evaluate(releases: try await session.send())
|
||||||
await evaluate(releases: releases)
|
session.cancel(reason: "Done")
|
||||||
}
|
}
|
||||||
|
|
||||||
func withXPCCall<ServiceProtocol, Result>(to service: String, _: ServiceProtocol.Type, closure: (ServiceProtocol) async throws -> Result) async rethrows -> Result {
|
|
||||||
let connectionToService = NSXPCConnection(serviceName: "com.maxgoedjen.Secretive.ReleasesDownloader")
|
|
||||||
connectionToService.remoteObjectInterface = NSXPCInterface(with: (any ReleasesDownloaderProtocol).self)// fixme
|
|
||||||
connectionToService.resume()
|
|
||||||
let service = connectionToService.remoteObjectProxy as! ServiceProtocol
|
|
||||||
let result = try await closure(service)
|
|
||||||
connectionToService.invalidate()
|
|
||||||
return result
|
|
||||||
}
|
|
||||||
|
|
||||||
/// 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.
|
||||||
@ -110,3 +104,32 @@ extension Updater {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private extension XPCSession {
|
||||||
|
|
||||||
|
func send<Response: Decodable & Sendable>(_ message: some Encodable = XPCSession.emptyMessage) async throws -> Response {
|
||||||
|
try await withCheckedThrowingContinuation { continuation in
|
||||||
|
do {
|
||||||
|
try send(message) { result in
|
||||||
|
switch result {
|
||||||
|
case .success(let message):
|
||||||
|
do {
|
||||||
|
let decoded = try message.decode(as: Response.self)
|
||||||
|
continuation.resume(returning: decoded)
|
||||||
|
} catch {
|
||||||
|
continuation.resume(throwing: error)
|
||||||
|
}
|
||||||
|
case .failure(let error):
|
||||||
|
continuation.resume(throwing: error)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch {
|
||||||
|
continuation.resume(throwing: error)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static var emptyMessage: some Encodable {
|
||||||
|
Data()
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
@ -1,27 +0,0 @@
|
|||||||
import Foundation
|
|
||||||
import Brief
|
|
||||||
|
|
||||||
final class ReleasesDownloader: NSObject, ReleasesDownloaderProtocol {
|
|
||||||
|
|
||||||
@objc func downloadReleases(with reply: @escaping (Data?, (any Error)?) -> Void) {
|
|
||||||
Task {
|
|
||||||
do {
|
|
||||||
let (data, _) = try await URLSession.shared.data(from: Constants.updateURL)
|
|
||||||
let releases = try JSONDecoder().decode([Release].self, from: data)
|
|
||||||
print(releases)
|
|
||||||
let jsonOut = try JSONEncoder().encode(releases)
|
|
||||||
reply(jsonOut, nil)
|
|
||||||
} catch {
|
|
||||||
reply(nil, error)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
extension ReleasesDownloader {
|
|
||||||
|
|
||||||
enum Constants {
|
|
||||||
static let updateURL = URL(string: "https://api.github.com/repos/maxgoedjen/secretive/releases")!
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,18 +1,44 @@
|
|||||||
import Foundation
|
import XPC
|
||||||
|
import OSLog
|
||||||
import Brief
|
import Brief
|
||||||
|
|
||||||
class ServiceDelegate: NSObject, NSXPCListenerDelegate {
|
private let logger = Logger(subsystem: "com.maxgoedjen.secretive.ReleasesDownloader", category: "ReleasesDownloader")
|
||||||
|
|
||||||
func listener(_ listener: NSXPCListener, shouldAcceptNewConnection newConnection: NSXPCConnection) -> Bool {
|
enum Constants {
|
||||||
newConnection.exportedInterface = NSXPCInterface(with: (any ReleasesDownloaderProtocol).self)
|
static let updateURL = URL(string: "https://api.github.com/repos/maxgoedjen/secretive/releases")!
|
||||||
let exportedObject = ReleasesDownloader()
|
}
|
||||||
newConnection.exportedObject = exportedObject
|
|
||||||
newConnection.resume()
|
func handleRequest(_ request: XPCListener.IncomingSessionRequest) -> XPCListener.IncomingSessionRequest.Decision {
|
||||||
return true
|
logger.log("ReleasesDownloader received inbound request")
|
||||||
|
return request.accept { xpcDictionary in
|
||||||
|
xpcDictionary.handoffReply(to: .global(qos: .userInteractive)) {
|
||||||
|
logger.log("ReleasesDownloader accepted inbound request")
|
||||||
|
Task {
|
||||||
|
do {
|
||||||
|
let (data, _) = try await URLSession.shared.data(from: Constants.updateURL)
|
||||||
|
let releases = try JSONDecoder().decode([Release].self, from: data)
|
||||||
|
xpcDictionary.reply(releases)
|
||||||
|
} catch {
|
||||||
|
logger.error("ReleasesDownloader failed with unknown error \(error)")
|
||||||
|
xpcDictionary.reply([] as [Release])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let delegate = ServiceDelegate()
|
do {
|
||||||
let listener = NSXPCListener.service()
|
if #available(macOS 26.0, *) {
|
||||||
listener.delegate = delegate
|
_ = try XPCListener(
|
||||||
listener.resume()
|
service: "com.maxgoedjen.Secretive.ReleasesDownloader",
|
||||||
|
requirement: .isFromSameTeam(),
|
||||||
|
incomingSessionHandler: handleRequest(_:)
|
||||||
|
)
|
||||||
|
} else {
|
||||||
|
_ = try XPCListener(service: "com.maxgoedjen.Secretive.ReleasesDownloader", incomingSessionHandler: handleRequest(_:))
|
||||||
|
}
|
||||||
|
logger.log("ReleasesDownloader initialized")
|
||||||
|
dispatchMain()
|
||||||
|
} catch {
|
||||||
|
logger.error("Failed to create ReleasesDownloader, error: \(error)")
|
||||||
|
}
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import Foundation
|
import Foundation
|
||||||
import SecretAgentKit
|
import SecretAgentKit
|
||||||
|
import Brief
|
||||||
|
|
||||||
/// Delegates all agent input parsing to an XPC service which wraps OpenSSH
|
/// Delegates all agent input parsing to an XPC service which wraps OpenSSH
|
||||||
public final class XPCAgentInputParser: SSHAgentInputParserProtocol {
|
public final class XPCAgentInputParser: SSHAgentInputParserProtocol {
|
||||||
@ -16,7 +17,6 @@ public final class XPCAgentInputParser: SSHAgentInputParserProtocol {
|
|||||||
Task {
|
Task {
|
||||||
// Warm up the XPC endpoint.
|
// Warm up the XPC endpoint.
|
||||||
_ = try? await parse(data: Data())
|
_ = try? await parse(data: Data())
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -31,7 +31,6 @@
|
|||||||
501577C82E6BC5B4004A37D0 /* ReleasesDownloader.xpc in Embed XPC Services */ = {isa = PBXBuildFile; fileRef = 501577BD2E6BC5B4004A37D0 /* ReleasesDownloader.xpc */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
501577C82E6BC5B4004A37D0 /* ReleasesDownloader.xpc in Embed XPC Services */ = {isa = PBXBuildFile; fileRef = 501577BD2E6BC5B4004A37D0 /* ReleasesDownloader.xpc */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
||||||
501577CF2E6BC5D4004A37D0 /* ReleasesDownloader.xpc in Embed XPC Services */ = {isa = PBXBuildFile; fileRef = 501577BD2E6BC5B4004A37D0 /* ReleasesDownloader.xpc */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
501577CF2E6BC5D4004A37D0 /* ReleasesDownloader.xpc in Embed XPC Services */ = {isa = PBXBuildFile; fileRef = 501577BD2E6BC5B4004A37D0 /* ReleasesDownloader.xpc */; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; };
|
||||||
501577DA2E6BC5F3004A37D0 /* main.swift in Sources */ = {isa = PBXBuildFile; fileRef = 501577D62E6BC5F3004A37D0 /* main.swift */; };
|
501577DA2E6BC5F3004A37D0 /* main.swift in Sources */ = {isa = PBXBuildFile; fileRef = 501577D62E6BC5F3004A37D0 /* main.swift */; };
|
||||||
501577DB2E6BC5F3004A37D0 /* ReleasesDownloader.swift in Sources */ = {isa = PBXBuildFile; fileRef = 501577D72E6BC5F3004A37D0 /* ReleasesDownloader.swift */; };
|
|
||||||
501577DF2E6BC647004A37D0 /* Brief in Frameworks */ = {isa = PBXBuildFile; productRef = 501577DE2E6BC647004A37D0 /* Brief */; };
|
501577DF2E6BC647004A37D0 /* Brief in Frameworks */ = {isa = PBXBuildFile; productRef = 501577DE2E6BC647004A37D0 /* Brief */; };
|
||||||
501578132E6C0479004A37D0 /* XPCInputParser.swift in Sources */ = {isa = PBXBuildFile; fileRef = 501578122E6C0479004A37D0 /* XPCInputParser.swift */; };
|
501578132E6C0479004A37D0 /* XPCInputParser.swift in Sources */ = {isa = PBXBuildFile; fileRef = 501578122E6C0479004A37D0 /* XPCInputParser.swift */; };
|
||||||
5018F54F24064786002EB505 /* Notifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5018F54E24064786002EB505 /* Notifier.swift */; };
|
5018F54F24064786002EB505 /* Notifier.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5018F54E24064786002EB505 /* Notifier.swift */; };
|
||||||
@ -180,7 +179,6 @@
|
|||||||
501577BD2E6BC5B4004A37D0 /* ReleasesDownloader.xpc */ = {isa = PBXFileReference; explicitFileType = "wrapper.xpc-service"; includeInIndex = 0; path = ReleasesDownloader.xpc; sourceTree = BUILT_PRODUCTS_DIR; };
|
501577BD2E6BC5B4004A37D0 /* ReleasesDownloader.xpc */ = {isa = PBXFileReference; explicitFileType = "wrapper.xpc-service"; includeInIndex = 0; path = ReleasesDownloader.xpc; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||||
501577D52E6BC5F3004A37D0 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
501577D52E6BC5F3004A37D0 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
||||||
501577D62E6BC5F3004A37D0 /* main.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = main.swift; sourceTree = "<group>"; };
|
501577D62E6BC5F3004A37D0 /* main.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = main.swift; sourceTree = "<group>"; };
|
||||||
501577D72E6BC5F3004A37D0 /* ReleasesDownloader.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ReleasesDownloader.swift; sourceTree = "<group>"; };
|
|
||||||
501578122E6C0479004A37D0 /* XPCInputParser.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = XPCInputParser.swift; sourceTree = "<group>"; };
|
501578122E6C0479004A37D0 /* XPCInputParser.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = XPCInputParser.swift; sourceTree = "<group>"; };
|
||||||
5018F54E24064786002EB505 /* Notifier.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Notifier.swift; sourceTree = "<group>"; };
|
5018F54E24064786002EB505 /* Notifier.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Notifier.swift; sourceTree = "<group>"; };
|
||||||
504788EB2E680DC400B4556F /* URLs.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = URLs.swift; sourceTree = "<group>"; };
|
504788EB2E680DC400B4556F /* URLs.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = URLs.swift; sourceTree = "<group>"; };
|
||||||
@ -293,7 +291,6 @@
|
|||||||
children = (
|
children = (
|
||||||
501577D52E6BC5F3004A37D0 /* Info.plist */,
|
501577D52E6BC5F3004A37D0 /* Info.plist */,
|
||||||
501577D62E6BC5F3004A37D0 /* main.swift */,
|
501577D62E6BC5F3004A37D0 /* main.swift */,
|
||||||
501577D72E6BC5F3004A37D0 /* ReleasesDownloader.swift */,
|
|
||||||
);
|
);
|
||||||
path = ReleasesDownloader;
|
path = ReleasesDownloader;
|
||||||
sourceTree = "<group>";
|
sourceTree = "<group>";
|
||||||
@ -674,7 +671,6 @@
|
|||||||
buildActionMask = 2147483647;
|
buildActionMask = 2147483647;
|
||||||
files = (
|
files = (
|
||||||
501577DA2E6BC5F3004A37D0 /* main.swift in Sources */,
|
501577DA2E6BC5F3004A37D0 /* main.swift in Sources */,
|
||||||
501577DB2E6BC5F3004A37D0 /* ReleasesDownloader.swift in Sources */,
|
|
||||||
);
|
);
|
||||||
runOnlyForDeploymentPostprocessing = 0;
|
runOnlyForDeploymentPostprocessing = 0;
|
||||||
};
|
};
|
||||||
|
Loading…
Reference in New Issue
Block a user