From 2a58323706839f2f43fd0a46c7f67ff655587326 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Thu, 29 Feb 2024 19:54:33 +0100 Subject: [PATCH 1/9] Add SettingsStore --- .../Secretive/Helpers/SettingsHelper.swift | 60 +++++++++++++++++++ 1 file changed, 60 insertions(+) create mode 100644 Sources/Secretive/Helpers/SettingsHelper.swift diff --git a/Sources/Secretive/Helpers/SettingsHelper.swift b/Sources/Secretive/Helpers/SettingsHelper.swift new file mode 100644 index 00000000..8b6ce645 --- /dev/null +++ b/Sources/Secretive/Helpers/SettingsHelper.swift @@ -0,0 +1,60 @@ +// +// SettingsHelper.swift +// Secretive +// +// Created by Paul Heidekrüger on 27.02.24. +// Copyright © 2024 Max Goedjen. All rights reserved. +// + +import Foundation + +class SettingsStore { + static let service = "com.maxgoedjen.Secretive" +} + +extension SettingsStore { + static func set(key: String, value: String) -> Bool { + let valueData = value.data(using: String.Encoding.utf8)! + + if let keyVal = get(key: key) { + if keyVal == value { + return true + } + + let updateQuery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, + kSecAttrServer as String: service] + let attributes: [String: Any] = [kSecAttrAccount as String: key, + kSecValueData as String: valueData] + // FIXME: Make this non-blocking as described here: https://developer.apple.com/documentation/security/1393617-secitemupdate + let status = SecItemUpdate(updateQuery as CFDictionary, attributes as CFDictionary) + guard status == errSecSuccess else { + print("Couldn't update item in keychain. " + status.description) + return false + } + } else { + let addquery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, + kSecAttrAccount as String: key, + kSecAttrServer as String: service, + kSecValueData as String: valueData] + // FIXME: Make this non-blocking as described here: https://developer.apple.com/documentation/security/1401659-secitemadd + let status = SecItemAdd(addquery as CFDictionary, nil) + guard status == errSecSuccess else { + print("Couldn't add item to keychain. " + status.description) + return false + } + } + return true + } + + static func get(key: String) -> String? { + let getquery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, + kSecAttrAccount as String: key, + kSecAttrServer as String: service, + kSecMatchLimit as String: kSecMatchLimitOne, + kSecReturnData as String: true] + var item: CFTypeRef? + let status = SecItemCopyMatching(getquery as CFDictionary, &item) + + return status == errSecSuccess ? String(decoding: item as! Data, as: UTF8.self) : nil + } +} From 70cfdf83270c36dd3d304b20545aba92949019af Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Thu, 29 Feb 2024 19:55:20 +0100 Subject: [PATCH 2/9] Use keychain instead of UserDefaults in JustUpdatedChecker.swift --- Sources/Secretive/Controllers/JustUpdatedChecker.swift | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/Sources/Secretive/Controllers/JustUpdatedChecker.swift b/Sources/Secretive/Controllers/JustUpdatedChecker.swift index 4c86f68a..ee0dceb6 100644 --- a/Sources/Secretive/Controllers/JustUpdatedChecker.swift +++ b/Sources/Secretive/Controllers/JustUpdatedChecker.swift @@ -15,14 +15,11 @@ class JustUpdatedChecker: ObservableObject, JustUpdatedCheckerProtocol { } func check() { - let lastBuild = UserDefaults.standard.object(forKey: Constants.previousVersionUserDefaultsKey) as? String ?? "None" + let lastBuild = SettingsStore.get(key: Constants.previousVersionUserDefaultsKey) ?? "None" let currentBuild = Bundle.main.infoDictionary!["CFBundleShortVersionString"] as! String - UserDefaults.standard.set(currentBuild, forKey: Constants.previousVersionUserDefaultsKey) + SettingsStore.set(key: Constants.previousVersionUserDefaultsKey, value: currentBuild) justUpdated = lastBuild != currentBuild } - - - } extension JustUpdatedChecker { From 46022962b8d0f55c305ddab9e53b3df51e606291 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Thu, 29 Feb 2024 19:56:23 +0100 Subject: [PATCH 3/9] Add ability disable the SSH comment via settings --- Sources/Secretive.xcodeproj/project.pbxproj | 9 +++ Sources/Secretive/App.swift | 3 + Sources/Secretive/Localizable.xcstrings | 15 +++++ .../Secretive/Views/SecretDetailView.swift | 9 ++- Sources/Secretive/Views/SettingsView.swift | 57 +++++++++++++++++++ 5 files changed, 91 insertions(+), 2 deletions(-) create mode 100644 Sources/Secretive/Views/SettingsView.swift diff --git a/Sources/Secretive.xcodeproj/project.pbxproj b/Sources/Secretive.xcodeproj/project.pbxproj index 1edd651f..cf5bdcad 100644 --- a/Sources/Secretive.xcodeproj/project.pbxproj +++ b/Sources/Secretive.xcodeproj/project.pbxproj @@ -53,6 +53,8 @@ 50BB046B2418AAAE00D6E079 /* EmptyStoreView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 50BB046A2418AAAE00D6E079 /* EmptyStoreView.swift */; }; 50C385A52407A76D00AF2719 /* SecretDetailView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 50C385A42407A76D00AF2719 /* SecretDetailView.swift */; }; 50E9CF422B51D596004AB36D /* Localizable.xcstrings in Resources */ = {isa = PBXBuildFile; fileRef = 500B93C22B478D8400E157DE /* Localizable.xcstrings */; }; + DA140C502B8DF70500948F81 /* SettingsHelper.swift in Sources */ = {isa = PBXBuildFile; fileRef = DA140C4F2B8DF70500948F81 /* SettingsHelper.swift */; }; + DA22A3402B712A57004D45DD /* SettingsView.swift in Sources */ = {isa = PBXBuildFile; fileRef = DA22A33F2B712A57004D45DD /* SettingsView.swift */; }; /* End PBXBuildFile section */ /* Begin PBXContainerItemProxy section */ @@ -152,6 +154,9 @@ 50B8550C24138C4F009958AC /* DeleteSecretView.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DeleteSecretView.swift; sourceTree = ""; }; 50BB046A2418AAAE00D6E079 /* EmptyStoreView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = EmptyStoreView.swift; sourceTree = ""; }; 50C385A42407A76D00AF2719 /* SecretDetailView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SecretDetailView.swift; sourceTree = ""; }; + DA140C4F2B8DF70500948F81 /* SettingsHelper.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SettingsHelper.swift; sourceTree = ""; }; + DA22A33C2B6EB835004D45DD /* SecretiveRelease.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = SecretiveRelease.entitlements; sourceTree = ""; }; + DA22A33F2B712A57004D45DD /* SettingsView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SettingsView.swift; sourceTree = ""; }; /* End PBXFileReference section */ /* Begin PBXFrameworksBuildPhase section */ @@ -192,6 +197,7 @@ isa = PBXGroup; children = ( 50033AC227813F1700253856 /* BundleIDs.swift */, + DA140C4F2B8DF70500948F81 /* SettingsHelper.swift */, ); path = Helpers; sourceTree = ""; @@ -282,6 +288,7 @@ 50153E1F250AFCB200525160 /* UpdateView.swift */, 5066A6C12516F303004B5A36 /* SetupView.swift */, 5066A6C72516FE6E004B5A36 /* CopyableView.swift */, + DA22A33F2B712A57004D45DD /* SettingsView.swift */, ); path = Views; sourceTree = ""; @@ -497,6 +504,7 @@ 5079BA0F250F29BF00EA86F4 /* StoreListView.swift in Sources */, 50617DD223FCEFA90099B055 /* PreviewStore.swift in Sources */, 5066A6F7251829B1004B5A36 /* ShellConfigurationController.swift in Sources */, + DA22A3402B712A57004D45DD /* SettingsView.swift in Sources */, 50033AC327813F1700253856 /* BundleIDs.swift in Sources */, 508A58B3241ED2180069DC07 /* AgentStatusChecker.swift in Sources */, 50C385A52407A76D00AF2719 /* SecretDetailView.swift in Sources */, @@ -508,6 +516,7 @@ 50BB046B2418AAAE00D6E079 /* EmptyStoreView.swift in Sources */, 50617D8323FCE48E0099B055 /* App.swift in Sources */, 506772C92425BB8500034DED /* NoStoresView.swift in Sources */, + DA140C502B8DF70500948F81 /* SettingsHelper.swift in Sources */, 50153E22250DECA300525160 /* SecretListItemView.swift in Sources */, 508A58B5241ED48F0069DC07 /* PreviewAgentStatusChecker.swift in Sources */, 508A58AA241E06B40069DC07 /* PreviewUpdater.swift in Sources */, diff --git a/Sources/Secretive/App.swift b/Sources/Secretive/App.swift index 81555ab9..d40521e6 100644 --- a/Sources/Secretive/App.swift +++ b/Sources/Secretive/App.swift @@ -62,6 +62,9 @@ struct Secretive: App { } SidebarCommands() } + Settings { + SettingsView() + } } } diff --git a/Sources/Secretive/Localizable.xcstrings b/Sources/Secretive/Localizable.xcstrings index f00568b7..8edc7ae4 100644 --- a/Sources/Secretive/Localizable.xcstrings +++ b/Sources/Secretive/Localizable.xcstrings @@ -2510,6 +2510,9 @@ } } } + }, + "General" : { + }, "no_secure_storage_description" : { "localizations" : { @@ -2702,6 +2705,9 @@ } } } + }, + "None" : { + }, "persist_authentication_accept_button" : { "comment" : "When the user authorizes an action using a secret that requires unlock, they're shown a notification offering to leave the secret unlocked for a set period of time. This is the title for the notification.", @@ -3415,6 +3421,9 @@ } } } + }, + "Settings" : { + }, "setup_agent_activity_monitor_description" : { "localizations" : { @@ -4464,6 +4473,12 @@ } } } + }, + "SSH Public Key Comment" : { + + }, + "SSH public keys can be extended with an arbitrary comment string without changing the meaning of the key." : { + }, "unnamed_secret" : { "extractionState" : "manual", diff --git a/Sources/Secretive/Views/SecretDetailView.swift b/Sources/Secretive/Views/SecretDetailView.swift index aefe49d7..319d668a 100644 --- a/Sources/Secretive/Views/SecretDetailView.swift +++ b/Sources/Secretive/Views/SecretDetailView.swift @@ -4,6 +4,7 @@ import SecretKit struct SecretDetailView: View { @State var secret: SecretType + @AppStorage("com.maxgoedjen.Secretive.commentStyle") var style: CommentStyle = .keyAndHost private let keyWriter = OpenSSHKeyWriter() private let publicKeyFileStoreController = PublicKeyFileStoreController(homeDirectory: NSHomeDirectory().replacingOccurrences(of: Bundle.main.hostBundleID, with: Bundle.main.agentBundleID)) @@ -42,9 +43,13 @@ struct SecretDetailView: View { } var keyString: String { - keyWriter.openSSHString(secret: secret, comment: "\(dashedKeyName)@\(dashedHostName)") + switch style { + case CommentStyle.none: + keyWriter.openSSHString(secret: secret, comment: "") + default: + keyWriter.openSSHString(secret: secret, comment: "\(dashedKeyName)@\(dashedHostName)") + } } - } #if DEBUG diff --git a/Sources/Secretive/Views/SettingsView.swift b/Sources/Secretive/Views/SettingsView.swift new file mode 100644 index 00000000..b0bc0657 --- /dev/null +++ b/Sources/Secretive/Views/SettingsView.swift @@ -0,0 +1,57 @@ +// +// SettingsView.swift +// Secretive +// +// Created by Paul Heidekrüger on 05.02.24. +// Copyright © 2024 Max Goedjen. All rights reserved. +// + +import SwiftUI + +enum CommentStyle: String, CaseIterable, Identifiable { + case keyAndHost, none + var id: Self { self } +} + +struct GeneralSettingsView: View { + @AppStorage("com.maxgoedjen.Secretive.commentStyle") var selectedCommentStyle: CommentStyle = .keyAndHost + + var body: some View { + VStack(alignment: .leading) { + Section(footer: Text("SSH public keys can be extended with an arbitrary comment string without changing the meaning of the key.") + .font(.caption) + .fontWeight(.light)) { + Picker("SSH Public Key Comment", selection: $selectedCommentStyle) { + Text("Default").tag(CommentStyle.keyAndHost) + Text("None").tag(CommentStyle.none) + } + .pickerStyle(DefaultPickerStyle()) + } + } + .padding(20) + .frame(width: 350, height: 100) + .navigationTitle("Settings") + } +} + + +struct SettingsView: View { + private enum Tabs: Hashable { + case general + } + var body: some View { + TabView { + GeneralSettingsView() + .tabItem { + Label("General", systemImage: "gear") + } + .tag(Tabs.general) + } + .padding(20) + .frame(width: 500, height: 200) + } +} + +#Preview { + SettingsView() +} From a5a3f1cec9867bc4e3fb1c81de982647176373d3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Fri, 5 Apr 2024 09:24:35 +0200 Subject: [PATCH 4/9] Make SettingsStore functions non-static, re-implement them as subscripts and make settingsStore an environmentObject Fixes: https://github.com/maxgoedjen/secretive/pull/536#discussion_r1508446459 --- Sources/Secretive/App.swift | 2 + .../Secretive/Helpers/SettingsHelper.swift | 81 ++++++++++--------- 2 files changed, 44 insertions(+), 39 deletions(-) diff --git a/Sources/Secretive/App.swift b/Sources/Secretive/App.swift index d40521e6..6df7033c 100644 --- a/Sources/Secretive/App.swift +++ b/Sources/Secretive/App.swift @@ -16,6 +16,7 @@ struct Secretive: App { }() private let agentStatusChecker = AgentStatusChecker() private let justUpdatedChecker = JustUpdatedChecker() + private let settingsStore = SettingsStore() @AppStorage("defaultsHasRunSetup") var hasRunSetup = false @State private var showingSetup = false @@ -27,6 +28,7 @@ struct Secretive: App { .environmentObject(storeList) .environmentObject(Updater(checkOnLaunch: hasRunSetup)) .environmentObject(agentStatusChecker) + .environmentObject(settingsStore) .onAppear { if !hasRunSetup { showingSetup = true diff --git a/Sources/Secretive/Helpers/SettingsHelper.swift b/Sources/Secretive/Helpers/SettingsHelper.swift index 8b6ce645..7c3d0daa 100644 --- a/Sources/Secretive/Helpers/SettingsHelper.swift +++ b/Sources/Secretive/Helpers/SettingsHelper.swift @@ -8,53 +8,56 @@ import Foundation -class SettingsStore { - static let service = "com.maxgoedjen.Secretive" +class SettingsStore: ObservableObject { + let service = "com.maxgoedjen.Secretive" } extension SettingsStore { - static func set(key: String, value: String) -> Bool { - let valueData = value.data(using: String.Encoding.utf8)! - - if let keyVal = get(key: key) { - if keyVal == value { - return true + subscript(key: String) -> String? { + set(value) { + guard let valueData = value?.data(using: String.Encoding.utf8)! else { + return } - let updateQuery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, - kSecAttrServer as String: service] - let attributes: [String: Any] = [kSecAttrAccount as String: key, - kSecValueData as String: valueData] - // FIXME: Make this non-blocking as described here: https://developer.apple.com/documentation/security/1393617-secitemupdate - let status = SecItemUpdate(updateQuery as CFDictionary, attributes as CFDictionary) - guard status == errSecSuccess else { - print("Couldn't update item in keychain. " + status.description) - return false + if let keyVal = self[key] { + if keyVal == value { + return + } + + let updateQuery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, + kSecAttrServer as String: service] + let attributes: [String: Any] = [kSecAttrAccount as String: key, + kSecValueData as String: valueData] + // FIXME: Make this non-blocking as described here: https://developer.apple.com/documentation/security/1393617-secitemupdate + let status = SecItemUpdate(updateQuery as CFDictionary, attributes as CFDictionary) + guard status == errSecSuccess else { + print("Couldn't update item in keychain. " + status.description) + return + } + } else { + let addquery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, + kSecAttrAccount as String: key, + kSecAttrServer as String: service, + kSecValueData as String: valueData] + // FIXME: Make this non-blocking as described here: https://developer.apple.com/documentation/security/1401659-secitemadd + let status = SecItemAdd(addquery as CFDictionary, nil) + guard status == errSecSuccess else { + print("Couldn't add item to keychain. " + status.description) + return + } } - } else { - let addquery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, + } + + get { + let getquery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, kSecAttrAccount as String: key, kSecAttrServer as String: service, - kSecValueData as String: valueData] - // FIXME: Make this non-blocking as described here: https://developer.apple.com/documentation/security/1401659-secitemadd - let status = SecItemAdd(addquery as CFDictionary, nil) - guard status == errSecSuccess else { - print("Couldn't add item to keychain. " + status.description) - return false - } + kSecMatchLimit as String: kSecMatchLimitOne, + kSecReturnData as String: true] + var item: CFTypeRef? + let status = SecItemCopyMatching(getquery as CFDictionary, &item) + + return status == errSecSuccess ? String(decoding: item as! Data, as: UTF8.self) : nil } - return true - } - - static func get(key: String) -> String? { - let getquery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, - kSecAttrAccount as String: key, - kSecAttrServer as String: service, - kSecMatchLimit as String: kSecMatchLimitOne, - kSecReturnData as String: true] - var item: CFTypeRef? - let status = SecItemCopyMatching(getquery as CFDictionary, &item) - - return status == errSecSuccess ? String(decoding: item as! Data, as: UTF8.self) : nil } } From 5cbc4e5f88f0ec50538610660dce8c67e8242922 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Fri, 5 Apr 2024 10:29:47 +0200 Subject: [PATCH 5/9] Add rawValues for CommentStyle enum --- Sources/Secretive/Views/SettingsView.swift | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/Sources/Secretive/Views/SettingsView.swift b/Sources/Secretive/Views/SettingsView.swift index b0bc0657..5f6f9f73 100644 --- a/Sources/Secretive/Views/SettingsView.swift +++ b/Sources/Secretive/Views/SettingsView.swift @@ -9,7 +9,9 @@ import SwiftUI enum CommentStyle: String, CaseIterable, Identifiable { - case keyAndHost, none + case keyAndHost = "keyAndHost" + case none = "none" + var id: Self { self } } From e29dd20722ce6762258064538351be32c4b2436f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Fri, 5 Apr 2024 10:30:48 +0200 Subject: [PATCH 6/9] Use SettingsStore for querying the comment style in SecretDetailView Fixes: https://github.com/maxgoedjen/secretive/pull/536#discussion_r1509655340 --- Sources/Secretive/Views/SecretDetailView.swift | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/Sources/Secretive/Views/SecretDetailView.swift b/Sources/Secretive/Views/SecretDetailView.swift index 319d668a..a0f8ebb5 100644 --- a/Sources/Secretive/Views/SecretDetailView.swift +++ b/Sources/Secretive/Views/SecretDetailView.swift @@ -4,7 +4,7 @@ import SecretKit struct SecretDetailView: View { @State var secret: SecretType - @AppStorage("com.maxgoedjen.Secretive.commentStyle") var style: CommentStyle = .keyAndHost + @EnvironmentObject private var settingsStore: SettingsStore private let keyWriter = OpenSSHKeyWriter() private let publicKeyFileStoreController = PublicKeyFileStoreController(homeDirectory: NSHomeDirectory().replacingOccurrences(of: Bundle.main.hostBundleID, with: Bundle.main.agentBundleID)) @@ -43,11 +43,12 @@ struct SecretDetailView: View { } var keyString: String { + var style: CommentStyle = CommentStyle(rawValue: settingsStore["com.maxgoedjen.Secretive.commentStyle"] ?? CommentStyle.keyAndHost.rawValue)! switch style { - case CommentStyle.none: - keyWriter.openSSHString(secret: secret, comment: "") - default: - keyWriter.openSSHString(secret: secret, comment: "\(dashedKeyName)@\(dashedHostName)") + case .none: + return keyWriter.openSSHString(secret: secret, comment: "") + case .keyAndHost: + return keyWriter.openSSHString(secret: secret, comment: "\(dashedKeyName)@\(dashedHostName)") } } } From 52f3fea9a8e84656180cf9a90ee57922170ad6f6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Fri, 5 Apr 2024 10:31:33 +0200 Subject: [PATCH 7/9] Revert "Use keychain instead of UserDefaults in JustUpdatedChecker.swift" This reverts commit ae8a21a1bf7f9e2d04fcb83c4543995db0111325. --- Sources/Secretive/Controllers/JustUpdatedChecker.swift | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/Sources/Secretive/Controllers/JustUpdatedChecker.swift b/Sources/Secretive/Controllers/JustUpdatedChecker.swift index ee0dceb6..4c86f68a 100644 --- a/Sources/Secretive/Controllers/JustUpdatedChecker.swift +++ b/Sources/Secretive/Controllers/JustUpdatedChecker.swift @@ -15,11 +15,14 @@ class JustUpdatedChecker: ObservableObject, JustUpdatedCheckerProtocol { } func check() { - let lastBuild = SettingsStore.get(key: Constants.previousVersionUserDefaultsKey) ?? "None" + let lastBuild = UserDefaults.standard.object(forKey: Constants.previousVersionUserDefaultsKey) as? String ?? "None" let currentBuild = Bundle.main.infoDictionary!["CFBundleShortVersionString"] as! String - SettingsStore.set(key: Constants.previousVersionUserDefaultsKey, value: currentBuild) + UserDefaults.standard.set(currentBuild, forKey: Constants.previousVersionUserDefaultsKey) justUpdated = lastBuild != currentBuild } + + + } extension JustUpdatedChecker { From 748fc4ef58f55a7a7155997d7d4e16a7e46d7f2c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Mon, 8 Apr 2024 10:23:59 +0200 Subject: [PATCH 8/9] Remove copyright info --- Sources/Secretive/Helpers/SettingsHelper.swift | 7 ------- Sources/Secretive/Views/SettingsView.swift | 7 ------- 2 files changed, 14 deletions(-) diff --git a/Sources/Secretive/Helpers/SettingsHelper.swift b/Sources/Secretive/Helpers/SettingsHelper.swift index 7c3d0daa..8bc5142b 100644 --- a/Sources/Secretive/Helpers/SettingsHelper.swift +++ b/Sources/Secretive/Helpers/SettingsHelper.swift @@ -1,10 +1,3 @@ -// -// SettingsHelper.swift -// Secretive -// -// Created by Paul Heidekrüger on 27.02.24. -// Copyright © 2024 Max Goedjen. All rights reserved. -// import Foundation diff --git a/Sources/Secretive/Views/SettingsView.swift b/Sources/Secretive/Views/SettingsView.swift index 5f6f9f73..accef15f 100644 --- a/Sources/Secretive/Views/SettingsView.swift +++ b/Sources/Secretive/Views/SettingsView.swift @@ -1,10 +1,3 @@ -// -// SettingsView.swift -// Secretive -// -// Created by Paul Heidekrüger on 05.02.24. -// Copyright © 2024 Max Goedjen. All rights reserved. -// import SwiftUI From 77bf72e21793fcaa6cb85ae0014379134d72572e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20Heidekr=C3=BCger?= Date: Mon, 8 Apr 2024 10:33:57 +0200 Subject: [PATCH 9/9] Use "enum Constants" in SettingsStore --- Sources/Secretive/Helpers/SettingsHelper.swift | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/Sources/Secretive/Helpers/SettingsHelper.swift b/Sources/Secretive/Helpers/SettingsHelper.swift index 8bc5142b..0f4a73ac 100644 --- a/Sources/Secretive/Helpers/SettingsHelper.swift +++ b/Sources/Secretive/Helpers/SettingsHelper.swift @@ -2,7 +2,9 @@ import Foundation class SettingsStore: ObservableObject { - let service = "com.maxgoedjen.Secretive" + enum Constants { + static let service = "com.maxgoedjen.Secretive" + } } extension SettingsStore { @@ -18,7 +20,7 @@ extension SettingsStore { } let updateQuery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, - kSecAttrServer as String: service] + kSecAttrServer as String: Constants.service] let attributes: [String: Any] = [kSecAttrAccount as String: key, kSecValueData as String: valueData] // FIXME: Make this non-blocking as described here: https://developer.apple.com/documentation/security/1393617-secitemupdate @@ -30,7 +32,7 @@ extension SettingsStore { } else { let addquery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, kSecAttrAccount as String: key, - kSecAttrServer as String: service, + kSecAttrServer as String: Constants.service, kSecValueData as String: valueData] // FIXME: Make this non-blocking as described here: https://developer.apple.com/documentation/security/1401659-secitemadd let status = SecItemAdd(addquery as CFDictionary, nil) @@ -44,7 +46,7 @@ extension SettingsStore { get { let getquery: [String: Any] = [kSecClass as String: kSecClassGenericPassword, kSecAttrAccount as String: key, - kSecAttrServer as String: service, + kSecAttrServer as String: Constants.service, kSecMatchLimit as String: kSecMatchLimitOne, kSecReturnData as String: true] var item: CFTypeRef?