JavaScript eval () "синтаксическая ошибка" при разборе строки функции

у меня есть немного кода JavaScript, который указан в файле конфигурации на стороне сервера. Поскольку я не могу указать функцию JavaScript на языке конфигурации (Lua), я имею ее как строку. Сервер возвращает строку в некотором JSON, и у меня есть клиент, интерпретирующий ее с помощью функции очистки:

parse_fields = function(fields) {
    for (var i = 0; i < fields.length; ++i) {
        if (fields[i].sortType) {
            sort_string = fields[i].sortType;
            fields[i].sortType = eval(sort_string);
        }
        return fields;
    }
}; 

так что в основном он просто оценивает sortType если он существует. Проблема в том, что Firebug сообщает о "синтаксической ошибке" на eval() линии. Когда я запускаю же действия на консоли Firebug, он работает без проблем и я могу выполнить функцию, как я ожидаю. Я пробовал несколько разных вариантов:window.eval вместо простого eval хранение sortType как я сделал выше, и пробую небольшие вариации на строку.

пробы стоимостью fields[i].sortType и "function(value) { return Math.abs(value); }". Вот тестирование, которое я сделал в консоли Firebug:

>>> sort_string
"function(value) { return Math.abs(value); }"
>>> eval(sort_string)
function()
>>> eval(sort_string)(-1)
1

и сама ошибка в Firebug:

syntax error
[Break on this error] function(value) { return Math.abs(value); }

последний бит, который может иметь отношение что все это завернуто в Ext JS , с Ext.ns изменение пространства имен вверху. Но я предположил window.eval вызовет глобальный eval, независимо от любых возможных eval в более конкретных пространствах имен.

любые идеи.

2 ответов


чтобы сделать то, что вы хотите, оберните строку в скобки:

a = "function(value) { return Math.abs(value);}";
b = eval("("+a+")");
b(-1);

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

без скобок, это может быть функция декларация, и кажется, что иногда он анализируется таким образом - это может быть источником странного/непоследовательного поведения, которое вы описываете.

сравните это объявление функции:

function foo(arg) {}

С этим функция-выражение:

var funcExpr = function foo(arg) {};

Он также должен быть выражением функции, если у него нет имени. Объявления функций требуют имен.

таким образом, это недействительное объявление, потому что в нем отсутствует его имя:

function (arg) {}

но это действительная, анонимная функция-выражение:

var funcExpr = function(arg) {};