Javascript: Interpreted or Compiled
JavaScript: Interpreted or Compiled? (Spoiler: It’s Both)

JavaScript has long carried the reputation of being an interpreted language — one that is read and executed line by line by a browser. For many years, that perception wasn’t far from the truth. But as the web evolved and demanded faster, more efficient code execution, so did JavaScript. The modern reality is this:
JavaScript is both interpreted and compiled — thanks to something called Just-In-Time (JIT) compilation.
In this blog, we’ll explore what that really means, and break down how modern JavaScript engines like Google’s V8 compile and run your code.
Interpreter vs. Compiler
Before diving into JavaScript, let’s clear up what “interpreted” and “compiled” mean in general:
- Interpreted Languages: Code is read and executed line-by-line at runtime. Examples: Python (typically), early JavaScript.
- Compiled Languages: Code is translated into machine code by a compiler before it runs. Examples: C, Rust.
Traditionally, JavaScript was considered an interpreted language because browsers used an interpreter to execute scripts directly. But performance became a concern as web applications grew in complexity.
Enter: Just-In-Time Compilation
To make JavaScript faster, modern engines (like V8 in Chrome and Node.js, SpiderMonkey in Firefox, and JavaScriptCore in Safari) use a technique called Just-In-Time (JIT) Compilation.
Here’s how it works in general terms:
- Parsing: The JavaScript engine reads your code and turns it into an Abstract Syntax Tree (AST).
- Interpretation: The engine begins interpreting the AST and executing the code immediately. This allows for fast startup times.
- Profiling: While interpreting, the engine keeps track of which functions are run frequently.
- Compilation: The most-used (or “hot”) parts of the code are compiled into optimized machine code — while the program is still running. This compiled code replaces the interpreted code for those hot paths, making execution much faster.
This hybrid approach combines the flexibility of interpretation with the performance of compilation.
Real-World Example: Google’s V8 Engine
Let’s briefly look at how V8, the JavaScript engine behind Chrome and Node.js, handles compilation:
- Ignition is V8’s interpreter. It quickly parses and begins executing JavaScript as bytecode.
- TurboFan is V8’s optimizing compiler. It watches how the bytecode runs and recompiles “hot” code paths into highly optimized machine code.
- V8 can even deoptimize code — reverting to slower bytecode if assumptions used during optimization turn out to be false.
This process happens seamlessly and constantly behind the scenes while your JavaScript runs.
So… Is JavaScript Interpreted or Compiled?
The best answer today is:
JavaScript is a JIT-compiled language.
It starts out being interpreted for speed and flexibility, then compiles hot code on the fly to maximize performance.
This is why calling JavaScript simply “interpreted” is outdated and technically incorrect in the context of modern engines.
Why Does This Matter?
Understanding the compilation model behind JavaScript helps explain:
- Why some code is faster than others
- Why performance can improve over time in a long-running script
- Why writing “predictable” code (with consistent types and structures) often results in faster execution
Knowing how the engine works gives you insight into writing more performant code — and avoiding patterns that make JIT optimization harder.
Conclusion
JavaScript has come a long way from its interpreted-only roots. Today’s engines employ sophisticated techniques like JIT compilation to strike a balance between speed and flexibility. The next time someone calls JavaScript an interpreted language, you’ll know the full story.