Lesson guide

Learning objectives

  • Explain the main purpose of Eval: run a code string in JavaScript.
  • Identify the syntax, APIs, or concepts introduced in this lesson.
  • Use the examples to predict how JavaScript will behave before you run similar code.
  • Connect this topic to nearby lessons in Miscellaneous.

Real-world context

This lesson matters when you need to recognize where Eval: run a code string fits into real JavaScript programs. The built-in function allows to execute a string of code.

Key ideas

  • Eval: run a code string is part of the Miscellaneous chapter, so it builds on the surrounding concepts rather than standing alone.
  • Read each code example in two passes: first for the result, then for the rule that explains the result.
  • When a section compares similar features, focus on the condition that makes you choose one feature over another.

Key terms

  • Eval: run a code string
  • Eval
  • run
  • code
  • string

The built-in eval function allows to execute a string of code.

The syntax is:

javascript
let result = eval(code);

For example:

javascript
let code = 'alert("Hello")';
eval(code); // Hello

A string of code may be long, contain line breaks, function declarations, variables and so on.

The result of eval is the result of the last statement.

For example:

javascript
let value = eval('1+1');
alert(value); // 2
javascript
let value = eval('let i = 0; ++i');
alert(value); // 1

The eval’ed code is executed in the current lexical environment, so it can see outer variables:

javascript
let a = 1;

function f() {
  let a = 2;

  eval('alert(a)'); // 2
}

f();

It can change outer variables as well:

javascript
let x = 5;
eval("x = 10");
alert(x); // 10, value modified

In strict mode, eval has its own lexical environment. So functions and variables, declared inside eval, are not visible outside:

javascript
// reminder: 'use strict' is enabled in runnable examples by default

eval("let x = 5; function f() {}");

alert(typeof x); // undefined (no such variable)
// function f is also not visible

Without use strict, eval doesn’t have its own lexical environment, so we would see x and f outside.

Using “eval”

In modern programming eval is used very sparingly. It’s often said that “eval is evil”.

The reason is simple: long, long time ago JavaScript was a much weaker language, many things could only be done with eval. But that time passed a decade ago.

Right now, there’s almost no reason to use eval. If someone is using it, there’s a good chance they can replace it with a modern language construct or a JavaScript Module.

Please note that its ability to access outer variables has side-effects.

Code minifiers (tools used before JS gets to production, to compress it) rename local variables into shorter ones (like a, b etc) to make the code smaller. That’s usually safe, but not if eval is used, as local variables may be accessed from eval’ed code string. So minifiers don’t do that renaming for all variables potentially visible from eval. That negatively affects code compression ratio.

Using outer local variables inside eval is also considered a bad programming practice, as it makes maintaining the code more difficult.

There are two ways how to be totally safe from such problems.

If eval’ed code doesn’t use outer variables, please call eval as window.eval(...):

This way the code is executed in the global scope:

javascript
let x = 1;
{
  let x = 5;
  window.eval('alert(x)'); // 1 (global variable)
}

If eval’ed code needs local variables, change eval to new Function and pass them as arguments:

javascript
let f = new Function('a', 'alert(a)');

f(5); // 5

The new Function construct is explained in the chapter The "new Function" syntax. It creates a function from a string, also in the global scope. So it can’t see local variables. But it’s so much clearer to pass them explicitly as arguments, like in the example above.

Common mistakes

  • Skipping the small examples and then missing the exact rule that Eval: run a code string depends on.
  • Copying code without changing one value at a time to see which part controls the result.
  • Treating similar-looking syntax or APIs as interchangeable before checking their edge cases.

Summary

A call to eval(code) runs the string of code and returns the result of the last statement.

  • Rarely used in modern JavaScript, as there’s usually no need.
  • Can access outer local variables. That’s considered bad practice.
  • Instead, to eval the code in the global scope, use window.eval(code).
  • Or, if your code needs some data from the outer scope, use new Function and pass it as arguments.

Predict

Before running this eval check, predict the seven output lines. It shows that direct eval returns the last expression, can see and change local variables, strict-mode declarations stay inside eval, and new Function receives data explicitly.

javascript
Reveal explanation

The output is 3, 5, 20, undefined, 7, undefined, and 1. Direct eval runs in the current lexical environment, so inside demo it sees the local outer value 2 and can change it to 5. The value of eval(...) is the value of the last evaluated expression, so the hidden variable expression returns 20. Because demo is strict, hidden is not visible outside the eval code. new Function runs in the global scope, so it does not see the local outer; passing a and b explicitly is the safe pattern. The outer top-level outer remains 1.

Try it

Replace new Function("a", "b", "return a + b") with eval("(a, b) => a + b"), then predict which scope the created arrow function can see.

Practice

  • Rewrite one example from this lesson without looking at the original, then run it and compare the result.
  • Change one input, operator, method call, or option in a code sample and predict what will happen before running it.
  • Explain Eval: run a code string in your own words as if you were reviewing it with another learner.

Keep learning

Continue with Currying when you are ready for the next lesson.