Используйте сценарий содержимого для определения глобальных переменных

Я создаю расширение Firefox, и одна из его функций, которую я хотел бы, — это возможность для пользователя вводить скрипт или таблицу стилей на определенный веб-сайт, как Greasemonkey (за исключением того, что это будет только для одного сайта). Я добавляю некоторые функции для сценариев, которые я намеревался добавить из сценария содержимого в главное (небезопасное) окно. В блоге MDN, в нем говорится, что они внесли изменения в то, как это должно быть реализовано, поэтому я основывал свой код на новой реализации, как указано в посте, и вот что у меня есть:

var $jq = jQuery.noConflict();//Yes, I am also injecting jQuery at the same time
console.log("created jquery object"); //This works
exportFunction($jq, unsafeWindow, {defineAs: "$jq"});
console.log("This will never be called");

Но выполнение скрипта просто останавливается, а в консоли выводится Message: TypeError: window is null. Я тестирую преимущественно в Firefox 28 (похоже, я не могу заставить Firefox для Ubuntu обновляться сверх этого прямо сейчас, и целый ряд проблем вынуждает меня использовать для этого Ubuntu на виртуальной машине), но в Nightly 31a1 (Win7 ) ничего никогда не вводится, включая жестко закодированный стиль (который работает на FF28), так что в какой-то момент мне придется это выяснить. (Код PageMod здесь:

var lttWorker = sdk.pageMod.PageMod({
    include:["*"],
    /*contentScriptFile: [sdk.data.url("jquery.large.js"), sdk.data.url("scripts/bootstrapper.js")],
    contentScriptWhen: "ready",*/ //This is commented to test whether it was an issue with the script. It's not.
    contentStyle: "#header_bar{background-color:green;}", //This is injected in FF28 but not 31
    attachTo: ["existing", "top"],
    onAttach: function(){desktopNotifications({title:"attached content worker", text:"The content worker has been successfully attached"})} //This is called in FF28 but not 31
});
lttWorker.on("error", function(){callError("pageWorker failed");}); //This never gets called. Ever.

если кому интересно)

РЕДАКТИРОВАТЬ: я попробовал это на Firefox 30b, и все еще есть множество проблем, хотя они, похоже, немного отличаются как от FF28, так и от 31...


person JackW    schedule 04.06.2014    source источник
comment
Пожалуйста, используйте Firefox Beta 30 при игре с этими API. Они очень новые и не были полностью установлены до 30: mozilla.org/ en-US/firefox/channel/#beta   -  person therealjeffg    schedule 04.06.2014


Ответы (1)


Прежде всего: эти новые функции поддерживаются в Firefox 30 и более поздних версиях. См. ответ @canuckistani.

exportFunction API слишком ограничен, чтобы на самом деле внедрить что-то вроде jQuery со всеми сложными объектами, являющимися или содержащими узлы DOM. Это просто не работает с алгоритмом структурированного клонирования, который применяется к аргументам. API предназначен для двунаправленного взаимодействия надстроек со страницами, а не для внедрения сложных библиотек.

Лучше всего на самом деле создать тег сценария с использованием API DOM и поместить туда jQuery.

person nmaier    schedule 05.06.2014
comment
Я пробовал, и почему-то не получилось. Вот что у меня есть: $jq("body").append($jq("<script>", { src: "https://code.jquery.com/jquery-2.1.1.min.js" })).append($jq("<script>").html("var $jq = jQuery.noConflict();$jq('body').hide()"));, но хотя тело скрыто (поэтому должно быть определено $jq), оно не определено глобально в соответствии с firebug. Мне нужно использовать noConflict(). - person JackW; 05.06.2014
comment
Выглядит достаточно разумно, за исключением удаленной инъекции кода (вы должны ввести локально отправленную копию, если jquery)... Я мог бы изучить это позже... - person nmaier; 05.06.2014
comment
Я использую только удаленную копию jQuery, чтобы упростить тестирование, иначе мне придется возиться с отправкой URL-адресов ресурсов в скрипт. Я бы сделал это в производственном коде. Кроме того, если я помещу тот же код, что и в теге script, в консоль FB, он будет работать нормально. - person JackW; 05.06.2014