【问题标题】:Force restart on install and upgrade of Firefox Add-on-SDK based extension安装和升级基于 Firefox Add-on-SDK 的扩展时强制重启
【发布时间】:2016-06-03 02:30:15
【问题描述】:

我有基于 Firefox Jetpack Add-on-SDK 的扩展,它不是以最佳方式构建的 - 重新安装后,一些旧的 XPCOM 组件挂在内存中,无法注册新组件。所以,我需要在扩展更新/安装时强制重启浏览器。我知道旧版本默认会这样做,但这个是无需重启的。

所以我的问题是:如何强制浏览器在扩展升级时重启? 我查看了 package.json 并一无所获。

【问题讨论】:

  • 您是否正在寻找一种方法来将您的扩展程序标记为不可重新启动,或者以编程方式从您的代码中导致重新启动?如果您打算以编程方式执行此操作,而没有将您的扩展程序标记为不可重启,那么您应该警告用户并要求确认用户此时可以接受重启。
  • 如果您想将您的代码标记为不可重启,您可能是 SOL。如果在 install.rdf 中标记为 <em:bootstrap>false</em:bootstrap>,我希望任何无需重新启动的附加组件都将失效。无需重新启动的附加组件使用明显不同的启动顺序,如果标记为非引导,我希望不会遵循该顺序。换句话说,我希望 bootstrap.js 不会被加载,并且不会调用其中的任何内容。因此,我希望您需要自己强制重启。
  • 您是否考虑过进行适当的清理?以我的经验,寻找所有悬空的位可能有点乏味,但通常是可能的

标签: javascript firefox firefox-addon firefox-addon-sdk


【解决方案1】:

如果您希望尝试将您的附加 SDK 扩展标记为不可重启,我的期望是您基本上是 SOL。 Add-on SDK 产生一个restartless 扩展,它使用标准的无重启启动方法。因此,无论何时您创建一个 Add-on SDK 插件,您实际上已经创建了一个由 Add-on SDK 包装的无需重启的插件。

您可以在jpm xpi 时创建的install.rdf 文件中更改以下行:
<em:bootstrap>true</em:bootstrap>

<em:bootstrap>false</em:bootstrap>
这将导致您的扩展被视为不可重启的附加组件。 Firefox 和 Mozilla 附加组件会将其视为需要重新启动才能启用/禁用的扩展。

但是,这样做会导致您的插件无法运行。永远不会调用您的插件的入口点。

因此,您必须自行强制重启。

您将需要存储一个首选项,表明您是否已重新启动(即,这样您最终不会连续重新启动)。见:

您应该向用户打开一个dialog/panel (MDN add-on SDK panel API),通知他们需要重新启动才能使您的附加组件正常运行,并为他们提供当时重新启动的选项,或等待。见:Addon SDK way to make a dialog

在我的一个附加组件Change Profile's Window Icons 中,需要重新启动才能使更改完全生效(不重新启动只会导致部分效果)。我会通知用户该需求,并从选项对话框中为他们提供执行此操作的选项。对话框如下所示:

在此对话框中,按钮 Accept changes and Restart Firefox 将执行它所说的操作,并重新启动 Firefox。我用来重启 Firefox 的代码是:

window.opener.content.document.getElementById('cmd_restartApp').doCommand();

这使用 Firefox 内置的重启功能来执行重启。因此,如果必须执行重启的确切方法或与此相关的任何内务管理发生变化,则无需更新该代码。

确切地说,您将如何调用该函数取决于您想要这样做时所处的上下文。在某种程度上,这将取决于您如何实现通知用户需要重新启动并为他们提供现在或以后执行此操作的选项。鉴于您没有在问题中指定这一点,因此无法准确告诉您需要使用哪些代码才能导致重新启动。但是,一般来说,您将需要对基本 Firefox 窗口之一的引用。您可以通过多种方法中的任何一种来获取该引用,具体取决于您如何实现与用户的交互。

一种方法是:

if (window === null || typeof window !== "object") {
    //If you do not already have a window reference, you need to obtain one:
    //  Add/remove a "/" to comment/un-comment the code appropriate for your add-on type.
    //* Add-on SDK:
    var window = require('sdk/window/utils').getMostRecentBrowserWindow();
    //*/
    /* Overlay and bootstrap (from almost any context/scope):
    var window=Components.classes["@mozilla.org/appshell/window-mediator;1"]
                         .getService(Components.interfaces.nsIWindowMediator)
                         .getMostRecentWindow("navigator:browser");        
    //*/
}
if (typeof document === "undefined") {
    //If there is no document defined, get it
    var document = window.content.document;
}

//Then restart:
document.getElementById('cmd_restartApp').doCommand();

上述代码的部分内容是从我的其他答案中复制的,包括this one,或者来自我写的extension

【讨论】:

  • 谢谢。您准确地指出了我在这里的情况。您能否提供一个指向您的扩展程序的链接,以便我查看它是如何工作的?
  • @msangel,插件是Change Profile's Window Icons。它是一个基于 XUL 的插件,可以更改该配置文件的窗口图标。它是不可重启的,因为 Firefox 不允许从无需重启的附加组件中更改窗口图标。如果在选项对话框中更改了所选图标,则任何已存在窗口的图标都不会更改。要进行这些更改,必须重新启动 Firefox。该按钮存在,因此用户有一个简单的方法来做到这一点。请参阅 chrome/content/options.jschrome/content/options.xul
  • @msangel,我使用附加 SDK 添加了指向其他问题、搜索和 MDN 重新面板/对话框的链接。此外,还链接了一个关于使用首选项仅在安装时执行一次操作的问题以及基于 XUL 的信息,该信息基于使用首选项来确定是否已执行安装时执行操作的概念。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-06-10
相关资源
最近更新 更多