From 44c1ed4d602102ba99784af087705bcb0afa8b45 Mon Sep 17 00:00:00 2001 From: jinyaqiu Date: Wed, 27 Aug 2025 15:41:33 +0800 Subject: [PATCH] feat: 1 2 --- wake/Utils/KeychainHelper.swift | 34 ++++++++++++++++++++- wake/Utils/Router.swift | 3 ++ wake/View/Owner/UserInfo/AvatarPicker.swift | 1 + 3 files changed, 37 insertions(+), 1 deletion(-) diff --git a/wake/Utils/KeychainHelper.swift b/wake/Utils/KeychainHelper.swift index b2c4127..a8e35ec 100644 --- a/wake/Utils/KeychainHelper.swift +++ b/wake/Utils/KeychainHelper.swift @@ -4,7 +4,7 @@ import Security /// 用于安全存储和检索敏感信息(如令牌)的 Keychain 帮助类 public class KeychainHelper { // Keychain 键名 - private enum KeychainKey: String { + private enum KeychainKey: String, CaseIterable { case accessToken = "com.memorywake.accessToken" case refreshToken = "com.memorywake.refreshToken" } @@ -35,6 +35,38 @@ public class KeychainHelper { delete(for: .refreshToken) } + /// 清除所有存储的 Keychain 数据 + public static func clearAll() { + // 清除所有已知的 keychain 项 + KeychainKey.allCases.forEach { key in + delete(for: key) + } + + // 额外清理:删除所有通用密码项(作为安全措施) + let query: [String: Any] = [ + kSecClass as String: kSecClassGenericPassword, + kSecReturnAttributes as String: true, + kSecMatchLimit as String: kSecMatchLimitAll + ] + + var result: AnyObject? + let status = SecItemCopyMatching(query as CFDictionary, &result) + + if status == errSecSuccess, let items = result as? [[String: Any]] { + for item in items { + if let account = item[kSecAttrAccount as String] as? String, + let service = item[kSecAttrService as String] as? String { + let deleteQuery: [String: Any] = [ + kSecClass as String: kSecClassGenericPassword, + kSecAttrAccount as String: account, + kSecAttrService as String: service + ] + SecItemDelete(deleteQuery as CFDictionary) + } + } + } + } + // MARK: - 私有方法 private static func save(_ string: String, for key: KeychainKey) -> Bool { diff --git a/wake/Utils/Router.swift b/wake/Utils/Router.swift index 09d5dad..5e4b673 100644 --- a/wake/Utils/Router.swift +++ b/wake/Utils/Router.swift @@ -2,6 +2,7 @@ import SwiftUI @MainActor enum AppRoute: Hashable { + case login case avatarBox case feedbackView case feedbackDetail(type: FeedbackView.FeedbackType) @@ -12,6 +13,8 @@ enum AppRoute: Hashable { @ViewBuilder var view: some View { switch self { + case .login: + LoginView() case .avatarBox: AvatarBoxView() case .feedbackView: diff --git a/wake/View/Owner/UserInfo/AvatarPicker.swift b/wake/View/Owner/UserInfo/AvatarPicker.swift index 49cd59a..98e3982 100644 --- a/wake/View/Owner/UserInfo/AvatarPicker.swift +++ b/wake/View/Owner/UserInfo/AvatarPicker.swift @@ -56,6 +56,7 @@ public struct AvatarPicker: View { SVGImage(svgName: "IP") .frame(width: avatarSize, height: avatarSize) .contentShape(Rectangle()) + .clipShape(RoundedRectangle(cornerRadius: 20)) .overlay( RoundedRectangle(cornerRadius: 20) .stroke(style: StrokeStyle(