Расширение Mozilla (Firefox, Thunderbird): Как получить идентификатор расширения (из install.rdf)?
Если вы разрабатываете расширение для одного из приложений mozilla (например, Firefox, Thunderbird и т. Д.), Вы определяете идентификатор расширения в install.rdf.
Если по какой-либо причине вам необходимо знать идентификатор расширения, например, чтобы получить dir расширения в локальной файловой системе (1) или если вы хотите отправить его в веб-сервис (статистика использования) и т. Д., Было бы неплохо получить его из установки..rdf за то, чтобы это было жестко закодировано в вашем коде javascript.
Но как получить доступ к идентификатору расширения из моего расширения?
1) пример кода:
var extId = "myspecialthunderbirdextid@mydomain.com";
var filename = "install.rdf";
var file = extManager.getInstallLocation(extId).getItemFile(extId, filename);
var fullPathToFile = file.path;
5 ответов
Я вполне уверен, что "жестко идентифицированный идентификатор" никогда не должен изменяться в течение всего срока действия расширения. Вот и вся цель идентификатора: он уникален для этого расширения навсегда. Просто сохраните его как константу и используйте эту константу в своих библиотеках. В этом нет ничего плохого.
Плохая практика - это использование install.rdf, который существует с единственной целью... ну, установка. Как только расширение разработано, состояние файла install.rdf не имеет значения и вполне может быть несовместимым.
"Манифест установки - это файл, который приложение XUL с поддержкой диспетчера надстроек использует для определения информации о надстройке во время ее установки" [1]
По аналогии это похоже на доступ к памяти удаленного объекта из переполнения. Этот объект все еще существует в памяти, но он логически не актуален, и использование его данных - действительно очень плохая идея.
Как и lwburk, я не думаю, что он доступен через API Mozilla, но у меня есть идея, которая работает, но это похоже на сложный взлом. Основные шаги:
- Настройте пользовательский URL ресурса, чтобы он указывал на базовый каталог вашего расширения.
- Прочитайте файл и проанализируйте его в XML
- Вытащите идентификатор с помощью XPath
Добавьте следующую строку в ваш файл chrome.manifest
resource packagename-base-dir chrome/../
Затем мы можем получить и проанализировать файл с помощью следующего кода:
function myId(){
var req = new XMLHttpRequest();
// synchronous request
req.open('GET', "resource://packagename-base-dir/install.rdf", false);
req.send(null);
if( req.status !== 0){
throw("file not found");
}
var data = req.responseText;
// this is so that we can query xpath with namespaces
var nsResolver = function(prefix){
var ns = {
"rdf" : "http://www.w3.org/1999/02/22-rdf-syntax-ns#",
"em" : "http://www.mozilla.org/2004/em-rdf#"
};
return ns[prefix] || null;
};
var parser = CCIN("@mozilla.org/xmlextras/domparser;1", Ci.nsIDOMParser);
var doc = parser.parseFromString(data, "text/xml");
// you might have to change this xpath expression a bit to fit your setup
var myExtId = doc.evaluate("//em:targetApplication//em:id", doc, nsResolver,
Ci.nsIDOMXPathResult.FIRST_ORDERED_NODE_TYPE, null);
return myExtId.singleNodeValue.textContent;
}
Я решил использовать XMLHttpRequest(в отличие от простого чтения из файла) для извлечения содержимого, поскольку в Firefox 4 расширения не обязательно распаковываются. Тем не менее, XMLHttpRequest будет по-прежнему работать, если расширение остается упакованным (не проверял это, но читал об этом).
Обратите внимание, что URL ресурсов являются общими для всех установленных расширений, поэтому если packagename-base-dir
не уникален, вы столкнетесь с проблемами. Вы можете использовать программно добавление псевдонимов для решения этой проблемы.
Этот вопрос побудил меня присоединиться к Stackru сегодня вечером, и я с нетерпением жду возможности участвовать еще... Я буду видеть вас, ребята!
Поскольку Firefox сейчас использует только API Chrome WebExtension, вы можете использовать ответ @serg в разделе Как получить идентификатор моего расширения из JavaScript?:
Вы можете получить его так (без дополнительных разрешений) двумя различными способами:
Используя API времени выполнения:
var myid = chrome.runtime.id;
Использование i18n api:
var myid = chrome.i18n.getMessage("@@extension_id");
Я не могу доказать отрицание, но я провел некоторое исследование, и я не думаю, что это возможно. Доказательства:
- Этот вопрос, который показывает, что
nsIExtensionManager
интерфейс ожидает, что вы получите информацию о расширении по идентификатору - Полный
nsIExtensionManager
описание интерфейса, которое не показывает метод, который помогает
Интерфейс позволяет вам получить полный список установленных расширений, поэтому можно получить информацию о вашем расширении, используя что-то, кроме идентификатора. Посмотрите этот код, например:
var em = Cc['@mozilla.org/extensions/manager;1']
.getService(Ci.nsIExtensionManager);
const nsIUpdateItem = Ci.nsIUpdateItem;
var extension_type = nsIUpdateItem.TYPE_EXTENSION;
items = em.getItemList(extension_type, {});
items.forEach(function(item, index, array) {
alert(item.name + " / " + item.id + " version: " + item.version);
});
Но вы все равно будете полагаться на жестко закодированные свойства, из которых идентификатор является единственным, гарантированно уникальным.
Посмотрите на это дополнение, возможно, его автор мог бы помочь вам, или вы сами можете выяснить:
[Extension Manager] Extended очень прост в использовании. После установки просто откройте менеджер расширений, перейдя в Инструменты и нажав Расширения. Теперь вы увидите рядом с каждым расширением идентификатор этого расширения.
(Пока не совместим с Firefox 4.0)