Como executo algum JavaScript que é uma string?
function ExecuteJavascriptString()
{
var s = "alert('hello')";
// how do I get a browser to alert('hello')?
}
fonte
Como executo algum JavaScript que é uma string?
function ExecuteJavascriptString()
{
var s = "alert('hello')";
// how do I get a browser to alert('hello')?
}
Com eval("my script here")
função.
Você pode executá-lo usando uma função. Exemplo:
var theInstructions = "alert('Hello World'); var x = 100";
var F=new Function (theInstructions);
return(F());
var F=function(){eval(theInstructions);};
?
new Function("alert('Hello World');")()
A eval
função avaliará uma string que é passada para ela.
Mas o uso de eval
pode ser perigoso , portanto, use com cuidado.
Edit: annakata tem um bom argumento - não é apenas eval
perigoso , é lento . Isso ocorre porque o código a ser avaliado deve ser analisado no local, de modo que serão necessários alguns recursos de computação.
eval()
é perigoso. Existe alguma alternativa?
Use eval ().
W3 Visita às escolas de avaliação . O site tem alguns exemplos úteis de avaliação. A documentação do Mozilla cobre isso em detalhes.
Você provavelmente receberá muitos avisos sobre como usá-lo com segurança. NÃO permita que os usuários injetem QUALQUER COISA no eval () , pois é um grande problema de segurança.
Você também vai querer saber que eval () tem um escopo diferente .
eval
melhor para mim do que o artigo do W3Schools. Algo legível com boas explicações e exemplos seria developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/… . E não, eu não sou bjorninge
Tente o seguinte:
var script = "<script type='text/javascript'> content </script>";
//using jquery next
$('body').append(script);//incorporates and executes inmediatelly
Pessoalmente, não testei, mas parece funcionar.
Um pouco como o que Hossein Hajizadeh alerady disse, embora com mais detalhes:
Existe uma alternativa para eval()
.
A função setTimeout()
foi projetada para executar algo após um intervalo de milissegundos e o código a ser executado é formatado como uma sequência.
Funcionaria assim:
ExecuteJavascriptString(); //Just for running it
function ExecuteJavascriptString()
{
var s = "alert('hello')";
setTimeout(s, 1);
}
1
significa que ele aguardará 1 milissegundo antes de executar a sequência.
Pode não ser a maneira mais correta de fazê-lo, mas funciona.
setTimeout
? Observe que, em qualquer caso, isso tornará a execução assíncrona. Isso significa que todo o código que segue a setTimeout
chamada será invocado antes da passagem do código setTimeout
(mesmo se chamado com 0 (zero)).
new Function('alert("Hello")')();
Eu acho que esse é o melhor caminho.
Use eval como abaixo. Eval deve ser usado com cautela, uma simples pesquisa sobre " eval is evil " deve apontar algumas dicas.
function ExecuteJavascriptString()
{
var s = "alert('hello')";
eval(s);
}
Verifiquei isso em muitos scripts complexos e ofuscados:
var js = "alert('Hello, World!');" // put your JS code here
var oScript = document.createElement("script");
var oScriptText = document.createTextNode(js);
oScript.appendChild(oScriptText);
document.body.appendChild(oScript);
Se você deseja executar um comando específico (ou seja, string) após um tempo específico - cmd = seu código - InterVal = atraso na execução
function ExecStr(cmd, InterVal) {
try {
setTimeout(function () {
var F = new Function(cmd);
return (F());
}, InterVal);
} catch (e) { }
}
//sample
ExecStr("alert(20)",500);
Val
em InterVal
maiúscula?
Para usuários que estão usando o nó e que estão preocupados com as implicações de contexto das eval()
ofertas do nodejs vm
. Ele cria uma máquina virtual V8 que pode proteger a execução do seu código em um contexto separado.
Levar as coisas um passo adiante é o vm2
que fortalece, vm
permitindo que a VM execute código não confiável.
https://nodejs.org/api/vm.html - Nó oficialjs / vm
https://github.com/patriksimek/vm2 - vm2 estendido
const vm = require('vm');
const x = 1;
const sandbox = { x: 2 };
vm.createContext(sandbox); // Contextify the sandbox.
const code = 'x += 40; var y = 17;';
// `x` and `y` are global variables in the sandboxed environment.
// Initially, x has the value 2 because that is the value of sandbox.x.
vm.runInContext(code, sandbox);
console.log(sandbox.x); // 42
console.log(sandbox.y); // 17
console.log(x); // 1; y is not defined.
eval(s);
Mas isso pode ser perigoso se você estiver obtendo dados de usuários, embora eu suponha que se eles travarem o próprio navegador, isso é problema deles.
eval
é código de usuários, que poderia, por exemplo, permitir que os usuários roubassem contas de outros usuários sem que eles soubessem apenas carregando a página.
Não tenho certeza se isso é trapaça ou não:
window.say = function(a) { alert(a); };
var a = "say('hello')";
var p = /^([^(]*)\('([^']*)'\).*$/; // ["say('hello')","say","hello"]
var fn = window[p.exec(a)[1]]; // get function reference by name
if( typeof(fn) === "function")
fn.apply(null, [p.exec(a)[2]]); // call it with params
Eu estava respondendo a uma pergunta semelhante e tive outra ideia de como fazer isso sem usar eval()
:
const source = "alert('test')";
const el = document.createElement("script");
el.src = URL.createObjectURL(new Blob([source], { type: 'text/javascript' }));
document.head.appendChild(el);
No código acima, você basicamente cria o Blob, contendo seu script, para criar a URL do objeto (representação do objeto File ou Blob na memória do navegador). Como você possui src
propriedade na <script>
tag, o script será executado da mesma maneira como se tivesse sido carregado de qualquer outro URL.
function executeScript(source) {
var script = document.createElement("script");
script.onload = script.onerror = function(){ this.remove(); };
script.src = "data:text/plain;base64," + btoa(source);
document.body.appendChild(script);
}
executeScript("alert('Hello, World!');");
eval(s);
Lembre-se, porém, que a avaliação é muito poderosa e insegura. É melhor você ter certeza de que o script que você está executando é seguro e imutável pelos usuários.
Pode-se usar mathjs
Snippet do link acima:
// evaluate expressions
math.evaluate('sqrt(3^2 + 4^2)') // 5
math.evaluate('sqrt(-4)') // 2i
math.evaluate('2 inch to cm') // 5.08 cm
math.evaluate('cos(45 deg)') // 0.7071067811865476
// provide a scope
let scope = {
a: 3,
b: 4
}
math.evaluate('a * b', scope) // 12
math.evaluate('c = 2.3 + 4.5', scope) // 6.8
scope.c
scope
é qualquer objeto. Portanto, se você passar o escopo global para a função evalute, poderá executar alert () dinamicamente.
Além disso, mathjs é uma opção muito melhor que eval () porque é executado em uma sandbox.
Um usuário pode tentar injetar código JavaScript malicioso por meio do analisador de expressões. O analisador de expressões do mathjs oferece um ambiente em área restrita para executar expressões que devem tornar isso impossível. É possível, no entanto, que haja vulnerabilidades de segurança desconhecidas, por isso é importante ter cuidado, principalmente ao permitir a execução de expressões arbitrárias no servidor.
As versões mais recentes do mathjs não usam eval () ou Function ().
O analisador impede ativamente o acesso à avaliação interna do JavaScripts e à nova Function, que são a principal causa de ataques de segurança. As versões 4 e mais recentes do Mathjs não usam a avaliação do JavaScript por baixo. A versão 3 e anterior usava eval para a etapa de compilação. Isso não é diretamente um problema de segurança, mas resulta em uma maior superfície de ataque possível.
Usar o eval e criar uma nova função para executar o javascript traz muitos riscos à segurança.
const script = document.createElement("script");
const stringJquery = '$("#button").on("click", function() {console.log("hit")})';
script.text = stringJquery;
document.body.appendChild(script);
Eu prefiro esse método para executar o Javascript que recebo como uma string.