diff --git a/ios/Runner/AppDelegate.swift b/ios/Runner/AppDelegate.swift index 95291688..6e8498fc 100644 --- a/ios/Runner/AppDelegate.swift +++ b/ios/Runner/AppDelegate.swift @@ -70,21 +70,22 @@ import Gobackend // Import Go framework GeneratedPluginRegistrant.register(with: self) if let url = launchOptions?[.url] as? URL { - handleExtensionOAuthRedirect(url: url) + _ = handleExtensionOAuthRedirect(url: url) } return super.application(application, didFinishLaunchingWithOptions: launchOptions) } /// PKCE OAuth return URL: spotiflac://callback?code=...&state= - private func handleExtensionOAuthRedirect(url: URL) { - guard let scheme = url.scheme?.lowercased(), scheme == "spotiflac" else { return } + @discardableResult + private func handleExtensionOAuthRedirect(url: URL) -> Bool { + guard let scheme = url.scheme?.lowercased(), scheme == "spotiflac" else { return false } let host = (url.host ?? "").lowercased() let path = url.path.lowercased() let ok = host == "callback" || host == "spotify-callback" || path.contains("callback") - guard ok else { return } + guard ok else { return false } guard let components = URLComponents(url: url, resolvingAgainstBaseURL: false) else { - return + return false } let q = components.queryItems ?? [] let code = @@ -93,10 +94,10 @@ import Gobackend // Import Go framework let state = q.first { $0.name == "state" }?.value?.trimmingCharacters( in: .whitespacesAndNewlines) ?? "" - if code.isEmpty { return } + if code.isEmpty { return false } if state.isEmpty { NSLog("SpotiFLAC: Extension OAuth redirect missing state (extension id)") - return + return false } streamQueue.async { var err: NSError? @@ -107,6 +108,7 @@ import Gobackend // Import Go framework "SpotiFLAC: Extension OAuth complete failed: \(err.localizedDescription)") } } + return true } override func application( @@ -114,7 +116,9 @@ import Gobackend // Import Go framework open url: URL, options: [UIApplication.OpenURLOptionsKey: Any] = [:] ) -> Bool { - handleExtensionOAuthRedirect(url: url) + if handleExtensionOAuthRedirect(url: url) { + return true + } return super.application(app, open: url, options: options) } diff --git a/lib/screens/settings/extension_detail_page.dart b/lib/screens/settings/extension_detail_page.dart index 25b36ba4..09a3570e 100644 --- a/lib/screens/settings/extension_detail_page.dart +++ b/lib/screens/settings/extension_detail_page.dart @@ -443,7 +443,9 @@ class _ExtensionDetailPageState extends ConsumerState { } /// Extensions may return `setting_updates` from button actions (e.g. OAuth URL field). - Future _handleExtensionActionPayload(Map payload) async { + Future _handleExtensionActionPayload( + Map payload, + ) async { final raw = payload['setting_updates']; if (raw is! Map) return; final partial = {}; @@ -511,19 +513,19 @@ class _OauthLoginLinkPreview extends StatelessWidget { return Text( 'Tap Connect to Spotify to fill this field.', style: Theme.of(context).textTheme.bodySmall?.copyWith( - color: colorScheme.onSurfaceVariant, - fontStyle: FontStyle.italic, - ), + color: colorScheme.onSurfaceVariant, + fontStyle: FontStyle.italic, + ), ); } return SelectionArea( child: Text( text, style: Theme.of(context).textTheme.bodySmall?.copyWith( - color: colorScheme.primary, - fontFamily: 'monospace', - fontSize: 11, - ), + color: colorScheme.primary, + fontFamily: 'monospace', + fontSize: 11, + ), ), ); } @@ -878,7 +880,7 @@ class _SettingItemState extends State<_SettingItem> { Map payload = result; final nested = result['result']; if (nested is Map) { - payload = Map.from(nested as Map); + payload = Map.from(nested); } final success = payload['success'] as bool? ?? false;