You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

M1 Mac上SwiftUI SignInWithAppleButton的onCompletion回调无法触发

问题原因

这是SwiftUI在macOS 11.x版本的已知缺陷,根源就是你推测的缺少presentationAnchor配置:iOS/iPadOS系统会自动为苹果登录授权弹窗分配展示锚点,但macOS上需要显式指定弹窗绑定的窗口,原生SwiftUI的SignInWithAppleButton在macOS 11的SDK中没有暴露相关配置项,导致授权流程卡在弹窗步骤,无法触发完成回调。

解决方案

根据你的项目兼容要求可以选择以下两种方案:

方案1:兼容macOS 11.x版本

放弃使用原生SwiftUI的SignInWithAppleButton,手动实现授权流程,显式配置弹窗锚点:

  1. 先创建macOS专用的展示上下文提供类
import AuthenticationServices
#if os(macOS)
class AppleSignInPresentationProvider: NSObject, ASAuthorizationControllerPresentationContextProviding {
    func presentationAnchor(for controller: ASAuthorizationController) -> ASPresentationAnchor {
        // 返回当前活跃的主窗口作为弹窗锚点
        return NSApplication.shared.windows.first { $0.isKeyWindow } ?? ASPresentationAnchor()
    }
}
#endif
  1. 自定义按钮触发授权流程,实现代理拿到回调
// 所在视图或者ViewModel需要遵守ASAuthorizationControllerDelegate协议
struct LoginView: View, ASAuthorizationControllerDelegate {
    var body: some View {
        Button {
            let appleIDProvider = ASAuthorizationAppleIDProvider()
            let request = appleIDProvider.createRequest()
            request.requestedScopes = [.email]
            
            let authController = ASAuthorizationController(authorizationRequests: [request])
            authController.delegate = self
            #if os(macOS)
            authController.presentationContextProvider = AppleSignInPresentationProvider()
            #endif
            authController.performRequests()
        } label: {
            // 按系统样式自定义按钮UI即可
            Text("Continue with Apple")
                .frame(maxWidth: .infinity)
                .padding()
                .background(.black)
                .foregroundColor(.white)
                .cornerRadius(8)
        }
    }
    
    // 实现授权成功回调
    func authorizationController(controller: ASAuthorizationController, didCompleteWithAuthorization authorization: ASAuthorization) {
        print(">>> auth completed")
        switch authorization.credential {
        case let credential as ASAuthorizationAppleIDCredential:
            guard let idToken = credential.identityToken else { return }
            Dummy.signUpOrLogInWithApple(idToken: idToken)
        default:
            print(">>> default case")
        }
    }
    
    // 实现授权失败回调
    func authorizationController(controller: ASAuthorizationController, didCompleteWithError error: Error) {
        print(">>> Sign in with Apple failed", error.localizedDescription)
    }
}

方案2:最低支持版本升级到macOS 12+

直接将Xcode升级到13及以上版本,使用macOS 12+的SDK编译项目,苹果已经在新版SDK中修复了这个缺陷,你原来的SignInWithAppleButton代码不需要做任何修改即可正常触发onCompletion回调。

内容的提问来源于stack exchange,提问作者XYZ

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.06 19:06:02