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

使用JSQMessagesViewController执行Segue触发SIGABRT错误求助

SIGABRT Crash When Seguing From JSQMessagesViewController

我之前在使用JSQMessagesViewController结合Firebase做聊天功能时,也碰到过一模一样的Segue崩溃问题。结合你提供的代码来看,最可能的原因是Firebase的观察者没有被正确移除,导致内存引用异常,最终触发SIGABRT错误。下面是具体的排查和解决步骤:

1. 移除Firebase实时数据库的观察者

你在viewDidLoad里调用了query.observe(.childAdded),这个方法会返回一个DatabaseHandle,用来标记当前的监听任务。如果不手动移除这个监听,当你离开聊天VC时,Firebase仍然会持有VC的引用(哪怕你用了[weak self]),引发循环引用或者野指针问题。

解决方法:

  • 首先在VC类里添加一个属性保存观察者句柄:
private var messageObserverHandle: DatabaseHandle?
  • 然后在viewDidLoad中把observe的返回值赋值给这个属性:
messageObserverHandle = query.observe(.childAdded, with: { [weak self] snapshot in
    if let data = snapshot.value as? [String: String], let id = data["sender_id"], let name = data["name"], let text = data["text"], !text.isEmpty {
        if let message = JSQMessage(senderId: id, displayName: name, text: text) {
            self?.messages.append(message)
            self?.finishReceivingMessage()
        }
    }
})
  • 最后在VC的deinit方法里移除观察者:
deinit {
    if let handle = messageObserverHandle {
        Constants.refs.databaseChats.removeObserver(withHandle: handle)
    }
}

2. 停止JSQMessagesViewController的异步UI操作

JSQMessagesViewController有自己的消息处理生命周期,比如finishReceivingMessage会触发collectionView的刷新。如果VC已经出栈,再调用这个方法会导致UIKit操作异常。

你可以在viewWillDisappear里停止相关操作:

override func viewWillDisappear(_ animated: Bool) {
    super.viewWillDisappear(animated)
    self.stopReceivingMessage()
}

3. 排查Segue和目标VC的配置问题

如果上面两步还没解决,检查一下:

  • Storyboard里的Segue标识符是否和代码里的performSegue(withIdentifier:sender:)完全匹配
  • 目标视图控制器有没有未连接的IBOutlet,或者在viewDidLoad里有没有未初始化就使用的属性
  • 导航栏返回按钮的Segue是否正确关联了目标VC

调试小技巧

打开Xcode的断点导航栏(Command+8),添加一个All Exceptions断点。这样崩溃时Xcode会停在具体触发错误的代码行,能帮你快速定位问题(比如是Firebase回调里的UI操作,还是Segue时的VC初始化问题)。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.29 07:12:08