|
| 1 | +import AppKit |
| 2 | +import CodexBarCore |
| 3 | +import CodexBarMacroSupport |
| 4 | +import Foundation |
| 5 | +import SwiftUI |
| 6 | + |
| 7 | +@ProviderImplementationRegistration |
| 8 | +struct MiMoProviderImplementation: ProviderImplementation { |
| 9 | + let id: UsageProvider = .mimo |
| 10 | + let supportsLoginFlow: Bool = true |
| 11 | + |
| 12 | + @MainActor |
| 13 | + func presentation(context _: ProviderPresentationContext) -> ProviderPresentation { |
| 14 | + ProviderPresentation { _ in "web" } |
| 15 | + } |
| 16 | + |
| 17 | + @MainActor |
| 18 | + func observeSettings(_ settings: SettingsStore) { |
| 19 | + _ = settings.miMoCookieSource |
| 20 | + _ = settings.miMoCookieHeader |
| 21 | + } |
| 22 | + |
| 23 | + @MainActor |
| 24 | + func settingsSnapshot(context: ProviderSettingsSnapshotContext) -> ProviderSettingsSnapshotContribution? { |
| 25 | + .mimo(context.settings.miMoSettingsSnapshot(tokenOverride: context.tokenOverride)) |
| 26 | + } |
| 27 | + |
| 28 | + @MainActor |
| 29 | + func settingsPickers(context: ProviderSettingsContext) -> [ProviderSettingsPickerDescriptor] { |
| 30 | + let cookieBinding = Binding( |
| 31 | + get: { context.settings.miMoCookieSource.rawValue }, |
| 32 | + set: { raw in |
| 33 | + context.settings.miMoCookieSource = ProviderCookieSource(rawValue: raw) ?? .auto |
| 34 | + }) |
| 35 | + let cookieOptions = ProviderCookieSourceUI.options( |
| 36 | + allowsOff: false, |
| 37 | + keychainDisabled: context.settings.debugDisableKeychainAccess) |
| 38 | + let cookieSubtitle: () -> String? = { |
| 39 | + ProviderCookieSourceUI.subtitle( |
| 40 | + source: context.settings.miMoCookieSource, |
| 41 | + keychainDisabled: context.settings.debugDisableKeychainAccess, |
| 42 | + auto: "Automatic imports Chrome browser cookies from Xiaomi MiMo.", |
| 43 | + manual: "Paste a Cookie header from platform.xiaomimimo.com.", |
| 44 | + off: "Xiaomi MiMo cookies are disabled.") |
| 45 | + } |
| 46 | + |
| 47 | + return [ |
| 48 | + ProviderSettingsPickerDescriptor( |
| 49 | + id: "mimo-cookie-source", |
| 50 | + title: "Cookie source", |
| 51 | + subtitle: "Automatic imports Chrome browser cookies from Xiaomi MiMo.", |
| 52 | + dynamicSubtitle: cookieSubtitle, |
| 53 | + binding: cookieBinding, |
| 54 | + options: cookieOptions, |
| 55 | + isVisible: nil, |
| 56 | + onChange: nil, |
| 57 | + trailingText: { |
| 58 | + guard let entry = CookieHeaderCache.load(provider: .mimo) else { return nil } |
| 59 | + let when = entry.storedAt.relativeDescription() |
| 60 | + return "Cached: \(entry.sourceLabel) • \(when)" |
| 61 | + }), |
| 62 | + ] |
| 63 | + } |
| 64 | + |
| 65 | + @MainActor |
| 66 | + func settingsFields(context: ProviderSettingsContext) -> [ProviderSettingsFieldDescriptor] { |
| 67 | + [ |
| 68 | + ProviderSettingsFieldDescriptor( |
| 69 | + id: "mimo-cookie", |
| 70 | + title: "", |
| 71 | + subtitle: "", |
| 72 | + kind: .secure, |
| 73 | + placeholder: "Cookie: ...", |
| 74 | + binding: context.stringBinding(\.miMoCookieHeader), |
| 75 | + actions: [ |
| 76 | + ProviderSettingsActionDescriptor( |
| 77 | + id: "mimo-open-balance", |
| 78 | + title: "Open MiMo Balance", |
| 79 | + style: .link, |
| 80 | + isVisible: nil, |
| 81 | + perform: { |
| 82 | + guard let url = URL(string: "https://platform.xiaomimimo.com/#/console/balance") else { |
| 83 | + return |
| 84 | + } |
| 85 | + NSWorkspace.shared.open(url) |
| 86 | + }), |
| 87 | + ], |
| 88 | + isVisible: { context.settings.miMoCookieSource == .manual }, |
| 89 | + onActivate: { context.settings.ensureMiMoCookieLoaded() }), |
| 90 | + ] |
| 91 | + } |
| 92 | + |
| 93 | + @MainActor |
| 94 | + func runLoginFlow(context _: ProviderLoginContext) async -> Bool { |
| 95 | + let loginURL = "https://platform.xiaomimimo.com/api/v1/genLoginUrl?currentPath=%2F%23%2Fconsole%2Fbalance" |
| 96 | + guard let url = URL(string: loginURL) else { |
| 97 | + return false |
| 98 | + } |
| 99 | + NSWorkspace.shared.open(url) |
| 100 | + return false |
| 101 | + } |
| 102 | +} |
0 commit comments