Dynamic Evaluation Risks (eval, new Function)
eval and new Function execute a string as code with full access to their reachable scope — neither provides a meaningful sandbox boundary.
eval(code) / new Function(...params, body)
Purpose
eval() and new Function() both execute a string as JavaScript at runtime. Both are commonly, and
incorrectly, believed to offer some degree of isolation for running untrusted code — neither does.
Syntax
eval('console.log("hi")'); // direct eval — runs in the calling scope
const fn = new Function('a', 'b', 'return a + b'); // runs in the global scope only
Behavior notes
- Direct eval (called literally as
eval(...), not through an alias) runs in the calling function’s own scope — full read/write access to its local variables. new Functionalways runs in the global scope, regardless of where it’s constructed — it cannot see the enclosing function’s local variables at all, but still has full access to every global.- Neither restricts access to global objects, built-in constructors, or anything reachable via the prototype chain from any accessible value — there is no partial-trust execution mode inside a single JavaScript realm.
- Both block a wide range of engine optimizations for the surrounding code, since the engine can no longer statically determine what variables might be read or modified.
Common mistakes
- Believing a
try/catcharound anevalcall, or a limited-looking local scope, provides any real containment — it doesn’t; the evaluated code can still reach the global object and every built-in. - Building a dynamic
import()specifier from untrusted input — carries a comparable risk, since the imported module’s code runs with full privileges in its own scope. - Reaching for
eval/new Functionfor convenience (dynamic property access, for instance) where bracket notation or another non-evaluating technique already solves the problem.
Runtime notes
Behavior is core ECMAScript, identical everywhere; genuine sandboxing (a separate process, a properly isolated realm with no shared references) is an application-architecture concern, not something these APIs provide on their own.