2010-12-05 9 views
2

Comment puis-je exécuter une chaîne en tant que code (en utilisant eval()) et lui donner quelques variables? Par exemple, j'ai un objet nommé vars et je souhaite que chacune de ses propriétés soit accessible pour le code sans spécifier le nom de l'objet. Quelque chose comme ceci:eval() avec des variables d'un objet dans la portée

function evalWithVariables(func, vars) { 
//some magic here 
return eval(func); 
} 

function test() { 
var retval = evalWithVariables("a>5", {"a":7}); 
console.log(retval); 
} 

Oh, et le code est digne de confiance, il vient du même serveur que le script, il est généré par l'utilisateur et je suis sûr que eval est l'outil ici (et Je sais que eval est souvent maléfique).

Edit: La chose la plus importante pour moi est que le code qui est passé à eval() semble bon, est court et ne pas contenir les noms de variables d'aide ou si.

Répondre

3

découvert qu'il est possible d'utiliser simplement with:

eval("with (vars) {var result = (" + func + ")}"); 
1

Vous pouvez reconstituer les valeurs en code JavaScript et ajouter le code à exécuter. Ensuite, affectez le résultat de l'expression réelle à une variable locale. Ainsi,

evalWithVariables("a>5", {"a":7}); 

en fait eval s:

var a=7; var result = (a>5); 

Puis, juste après la eval, vérifier la valeur de result:

function evalWithVariables(func, vars) { 
var varString = ""; 

for (var i in vars) 
    varString += "var " + i + " = " + vars[i] + ";"; 

eval(varString + "; var result = (" + func + ")"); 
return result; 
} 
+0

Hmm, oui, cela devrait fonctionner, mais il semble en quelque sorte malpropre. – thejh

+1

Le concept lui-même est sale :) –

0

Peut-être que vous utilisez une approche plus fonctionnelle:

function evalWithVariables(func, vars) { 
    return func(vars); 
} 
evalWithVariables(function(vars) { return vars.a > 5; }, {"a":7}) 

ou moins:

(function(vars) { return vars.a > 5; })({"a":7}) 
+0

Non, je charge vraiment le code JS à partir d'un attribut de nœud XML. – thejh

1

Une option de renoncer eval() est de générer une fonction, puis utiliser with(), comme vous l'avez fait, de changer la bloc portée:

function evalWithVariables(func, vars) { 
    return new Function("v", "with (v) { return (" + func +")}")(vars); 
} 
+0

N'est-ce pas simplement plus compliqué et plus lent que ma solution? – thejh

+0

Oui, et probablement ainsi. – salathe

Questions connexes