Как проверить, установлен ли Firefox WebExtension на странице JavaScript или нет?
Я разработал WebExtension для Firefox, и мой веб-сайт работает с расширением в качестве предварительного условия. Мне нужно программно проверить, установлено ли расширение или нет, и если нет, попросить пользователя установить его.
Я не могу найти способ проверить, работает ли мое расширение в браузере пользователя.
Примечание редактора: методы, доступные в Firefox, отличаются от методов, доступных в Chrome, поэтому этот вопрос не является дубликатом.
1 ответ
Важное примечание для начала: страница не может запрашивать, если расширение установлено без явной помощи от расширения. Это делается для предотвращения дактилоскопии в браузере и / или предотвращения запрета содержимого сайтами, если установлены определенные расширения.
WebExtensions в основном построены на тех же принципах, что и расширения Chrome. Таким образом, этот вопрос актуален: проверьте, установлено ли у пользователя расширение Chrome.
Однако некоторые из лучших методов, доступных в Chrome, в настоящее время недоступны в Firefox:
Вы не можете использовать внешние сообщения с веб-страницы (через
externally_connectable
), поскольку это не доступно в FF.Вы не можете использовать доступные через Интернет ресурсы для проверки присутствия, поскольку Firefox намеренно защищает их от снятия отпечатков пальцев:
Затем файлы будут доступны по URL-адресу:
moz-extension://<random-UUID>/<path/to/resource>
Этот UUID генерируется случайным образом для каждого экземпляра браузера и не является идентификатором вашего добавочного номера. Это предотвращает дактилоскопирование веб-сайтов расширениями, которые установил пользователь.
Как таковой, каковы ваши варианты? Страница не может напрямую взаимодействовать с контекстом расширения (фоном), а фон не может напрямую влиять на страницу; вам нужен контент-скрипт для взаимодействия с контентом страницы.
Как может взаимодействовать код страницы и скрипт контента? Они изолированы друг от друга, если контентный скрипт ничего не делает с этим.
Прежде всего, общие приемы, которые работают как в FF, так и в Chrome:
Вы можете создать или изменить элемент DOM на странице из сценария содержимого и посмотреть эти изменения на странице.
// Content script let beacon = document.createElement("div"); beacon.classname = browser.runtime.id; document.body.appendChild(beacon); // Page script // Make sure this runs after the extension code if (document.getElementsByClassName("expected-extension-id").length) { // Installed } else { // Not installed }
Вы можете использовать
postMessage
чтобы общаться между контекстами, хотя это неуклюже использовать в качестве двунаправленного канала.Вот документация и пример WebExtension.
// Content script code window.postMessage({ direction: "from-content-script", message: "Message from extension" }, "*"); // Page code window.addEventListener("message", function(event) { if (event.source == window && event.data.direction && event.data.direction == "from-content-script") { // Assume extension is now installed } });
Вы можете использовать пользовательские события DOM аналогичным образом.
Также есть интересные подходы, специфичные для Firefox:
Вы можете поделиться кодом со страницей, используя
exportFunction
или жеcloneInto
:// Content script function usefulFunction() { /* ... */ } const extensionInterface = { usefulFunction } window.wrappedJSObject.extensionInterface = cloneInto(extensionInterface, window, {cloneFunctions: true}); // Page code if (typeof window.extensionInterface !== "undefined") { // Installed window.extensionInterface.usefulFunction(); } else { // Not installed }