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

新建SwiftUI项目集成FirebaseAuth后实时预览报错但模拟器运行正常

问题原因与解决步骤
  • 根本原因:Xcode SwiftUI预览环境是独立沙箱,不会走App完整启动流程,你的代码存在两个导致预览崩溃的问题:

    1. ContentView依赖的AppViewModel没有注入到预览环境中
    2. AppViewModel初始化时直接调用Auth.auth(),但预览环境没有提前初始化Firebase,调用Firebase相关接口会直接触发崩溃,报Message send failure错误
  • 解决步骤:

    1. 修复预览的EnvironmentObject注入
      修改你的ContentView_Previews代码,手动注入AppViewModel实例:
    struct ContentView_Previews: PreviewProvider {
        static var previews: some View {
            ContentView()
                .environmentObject(AppViewModel())
        }
    }
    
    1. 兼容预览环境的Firebase调用
      给AppViewModel添加预览环境判断,预览时跳过真实Firebase初始化,使用模拟数据:
    class AppViewModel: ObservableObject {
        let auth: Auth?
        @Published var LoggedIn = false
        
        init(previewIsLoggedIn: Bool? = nil) {
            // 判断当前是否运行在预览环境
            #if DEBUG
            if ProcessInfo.processInfo.environment["XCODE_RUNNING_FOR_PREVIEWS"] == "1" {
                self.auth = nil
                self.LoggedIn = previewIsLoggedIn ?? false
                return
            }
            #endif
            // 非预览环境走正常Firebase初始化逻辑
            self.auth = Auth.auth()
        }
        
        var isLoggedIn: Bool{
            // 预览环境直接返回模拟的登录状态
            guard let auth = auth else { return LoggedIn }
            return auth.currentUser != nil
        }
        
        // 原有登录、注册方法保持不变即可,运行时不会触发预览分支逻辑
        func LogIn(email: String, password: String) {
            guard let auth = auth else {
                // 预览环境点击登录直接修改模拟状态
                DispatchQueue.main.async {
                    self.LoggedIn = true
                }
                return
            }
            auth.signIn(withEmail: email, password: password) { [weak self] result, error in
                guard result != nil, error == nil else{
                    return
                }
                DispatchQueue.main.async {
                    self?.LoggedIn = true
                }
            }
        }
        
        func SignUp(email: String, password: String) {
            guard let auth = auth else {
                // 预览环境点击注册直接修改模拟状态
                DispatchQueue.main.async {
                    self.LoggedIn = true
                }
                return
            }
            auth.createUser(withEmail: email, password: password) { [weak self] result, error in
                guard result != nil, error == nil else{
                    return
                }
                DispatchQueue.main.async {
                    self?.LoggedIn = true
                }
            }
        }
    }
    
    1. 如果仅需要预览界面布局,可以直接指定预览具体子视图,跳过复杂逻辑:
    struct ContentView_Previews: PreviewProvider {
        static var previews: some View {
            LogInView()
                .environmentObject(AppViewModel(previewIsLoggedIn: false))
        }
    }
    
  • 验证方法:修改完成后点击Xcode预览窗口的刷新按钮,正常情况下即可加载成功。如果依然报错,可以先清理Xcode缓存(快捷键Command+Shift+K),再重启Xcode重试。

内容的提问来源于stack exchange,提问作者sultan.h

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.27 05:06:04