【问题标题】:What is the correct way to self-terminate a MacOS XPC service?自行终止 MacOS XPC 服务的正确方法是什么?
【发布时间】:2014-06-05 20:29:47
【问题描述】:

我已成功遵循Daemons and Service Guide - Creating XPC Services 教程以及SandboxedFetch 示例代码,并拥有使用新NSXPCConnection 类的有效客户端/服务设置。

我仍然不完全清楚的是,一旦服务应用程序完成其工作,如何正确地自行终止它。我认识到,在许多情况下,该服务有望保持活动状态,但在我想到的用例中,该服务将用于仅执行一些我不会在主应用程序中执行的处理。一旦该处理完成,服务应用程序就没有理由保留。如果客户以后需要另一项服务,它可以重新创建一个新服务。

由于该服务是一个轻量级、非 nibbed 的NSApplication,我试图通过从applicationWillTerminate 内部调用invalidate 来自行终止它,但这几乎每次都会触发 EXC_BAD_ACCESS 异常。在服务的[NSXPCListener serviceListener] 上调用invalidate 会产生稍微不太可靠的崩溃,但它仍然会崩溃。

从客户端应用程序内部的NSXPCConnection 调用invalidate 几乎每次都会生成一个EXC_BAD_ACCESS 异常。

所以我很好奇正确的步骤顺序是干净地关闭 XPC 服务然后退出服务应用程序。理想情况下,服务会在对客户端进行最后一次 XPC 调用后自行终止。

附件是一个异常堆栈跟踪的小屏幕截图。 (是的,这是在服务中加载的 webview。一旦 webview 完成加载,我希望服务自行终止)

【问题讨论】:

  • 您是否将您的 XPC 服务建模为启动代理或类似服务?常规 XPC 服务应在需要时自动使用 launchd 启动和停止。
  • 我使用的 XPC 服务是使用 NSXPCConnection 启动的应用内 XPC 服务。我最终意识到,即使是这些服务也不意味着要明确终止。如果它们空闲,系统将根据需要终止它们。
  • 既然您不再担心它的生命周期管理,它确实有效?

标签: cocoa appkit foundation xpc nsxpcconnection


【解决方案1】:

我的第一反应是你不应该打扰终止。当发生内存压力并且您的服务处于空闲状态时,launchd 将终止您的服务。退出可能不符合任何人的最佳利益,因为您的服务需要时间才能再次启动。不要终止,您就不必弄清楚尝试崩溃的原因。

但是,如果出于某种原因您决定终止,请不要那么努力。只需做你需要做的任何事情来清理(刷新缓冲区,优雅地关闭网络连接,这样服务器就不会受到影响,无论如何)并调用 exit。尽管您似乎在使用 NSApplication,但您的服务在任何意义上都不是用户关心的应用程序,并且在这方面没有令人信服的理由表现得像一个应用程序。宿主应用程序需要能够应对您的服务崩溃,因此您故意毫不客气地退出就可以了。

顺便说一句,在 XPC 服务中使用 NSApplication 可能不是最好的主意,因为没有支持的方式来声明您想要这样。这可能有助于解释为什么它不能像您希望的那样工作,尽管本段不应被解释为对崩溃的正确分析。 :-)

【讨论】:

    猜你喜欢
    • 2019-02-25
    • 1970-01-01
    • 2014-01-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多