Определение строки источника и файла ссылки на функцию - Как это делает Firebug? - PullRequest
5 голосов
/ 30 июля 2011

Краткое введение:

Я пытаюсь получить номер строки определения функции для анализа комментариев документации только к общедоступным материалам. Я дошел до того, что смог найти имя функции и, если бы захотел, мог бы выполнить функцию, но, похоже, не могу придумать, как извлечь информацию о номере строки. Примечание: это только для целей документирования, поэтому кросс-браузер не нужен.

Я знаю, что firebug (но не firebug lite, так что я не знаю, насколько это возможно) показывает номер строки и расположение скрипта ссылочной функции при наведении курсора мыши. Я просмотрел источник firebug и дошел до того, что обнаружил, что они вызывают (domPanel.js:536), но не могу найти эту функцию "addMember" где-нибудь в их источнике:

this.addMember(object, "userFunction", userFuncs, name, val, level, 0, context);

Может быть, это просто невозможно определить. Мои запасные варианты используют [userfunction].name и [userfunction].toSource(), а затем пытаются сопоставить источник с источником. Но я бы хотел избежать этого, если это возможно, поскольку имя может быть неуникальным, а метод toSource () предоставляет постобработку источника. Может быть, есть способ привязать к API Firebug?

Минимальный код объяснения:

[Обратите внимание, цель будет получить эту информацию: window.MyWindowObject.PublicFunction: script.js line 3]

script.js

(function () {

    function referencedFunction() {
       ///<summary>Sample XML Doc Comment</summary>
       alert('well hello there!');
    }

    var publicObject = window.MyWindowObject || {};
    publicObject.PublicFunction = referencedFunction;

    window.MyWindowObject = publicObject;
}());

index.htm

<!DOCTYPE html>
<html>
  <script src="script.js"></script>
</html>

РЕДАКТИРОВАТЬ: для тех, кто находит это в поиске позже, есть другая полезная информация, которую я нашел:

Stacktrace.js: https://github.com/eriwen/javascript-stacktrace - Довольно близко, но не совсем то, что я хочу, так как кажется, что оно не определяет окончательную функцию. Пример на их сайте не верный (хотя демо-версия «выглядит» так, как я хотел)

В chrome (и IE9): [userfunction].toString() сохраняет комментарии (не в Firefox), что я, вероятно, в конечном итоге и буду использовать. Я собирался использовать Firefox [userfunction] .toSource (), но это похоже на манипулируемый браузером источник функции. * Firefox [userfunction] .toString (), кажется, сохраняет код, но удаляет комментарии

Ответы [ 2 ]

2 голосов
/ 31 июля 2011

Вот потенциальное решение, которое я не проверял.Пару лет назад был эксплойт безопасности , который позволял JavaScript переопределять конструкторы нативных объектов. Джон Уокер привел такой пример:

function Array() {
    this[1] = 50;
}
var a = [40];
alert(a[0] + a[1]); // Gives 90

В том же духе, возможно, можно повторно объявить объявление функции в браузерах, где существует эксплойт?

function Function() {
    // Should give the stack trace, complete with line number?
    alert(new Error().stack); 
}

window.x = function () {}

У меня нет необходимых браузеров (Джон Резиг цитирует Firefox 2, Opera 9 и Safari 3 в качестве браузеров, в которых работает эксплойт Array), поэтому я не могу его протестировать, но, возможно, это место для начала?

0 голосов
/ 01 августа 2011

Firebug имеет доступ к защищенным функциям Chrome, которых нет у обычного JS.

Но JS все еще может получить доступ к необработанному источнику <script> с нетронутыми комментариями, если политика того же происхождения не имеетблокировать доступ.

Например, этот код получит необработанный источник всех встроенных сценариев и всех сценариев, загруженных из одного домена.:

var scipts = document.querySelectorAll ('script');

for (var J = 0, L = scipts.length;  J < L;  ++J) {
    console.log ('Number: ', J);
    var node    = scipts[J];
    if (!node)  continue;

    if (node.src) {
        //$.get (node.src, function (data) {console.log ('Text: ', data); } );
        try {
            var req = new XMLHttpRequest();
            req.open ('GET', node.src, false);
            req.send (null);
            if (req.status == 200  ||  req.status == 304)
                console.log ('Text: ', req.responseText);
        }
        catch (err) {
            console.log (err);
        }
    }
    else if (node.innerHTML) {
        console.log ('Text: ', node.innerHTML);
    }
}

Затем необработанный скрипт может быть проанализирован для номеров строк и определений функций и т. Д.

...