Call
Backend Basics

What Is Node.js? V8, libuv, Event-Driven I/O, Modules, npm, and Modern Node 26 Explained

Learn what Node.js actually is: a JavaScript runtime built on V8 with libuv event-driven I/O, standard networking/filesystem APIs, ES Modules and CommonJS, npm packages, streams, worker threads, built-in fetch and modern TypeScript support.

Published: September 21, 2024
Updated: September 12, 2026
7 min read
What Is Node.js? V8, libuv, Event-Driven I/O, Modules, npm, and Modern Node 26 Explained

What Is Node.js? V8, libuv, Event-Driven I/O, Modules, npm, and Modern Node 26 Explained

Node.js is a JavaScript runtime built on the V8 JavaScript engine. It lets JavaScript run outside the browser and adds server/runtime APIs for networking, files, processes, streams, cryptography, workers, testing, and more.

Node is commonly used for APIs, realtime servers, CLI tools, background workers, build tooling, and integration services.

As of September 2026, Node.js 26.8.2 is the Current release and Node.js 24 is the active LTS line.

Node.js is a runtime, not a framework

Node itself provides the runtime and standard APIs.

Frameworks such as Express, Fastify, NestJS, or full-stack web frameworks run on top of Node.

You can build an HTTP server with only Node's standard library:

import http from 'node:http';

const server = http.createServer((req, res) => {
  res.writeHead(200, { 'content-type': 'text/plain' });
  res.end('Hello from Node');
});

server.listen(3000);

A framework mainly adds higher-level routing, validation, middleware, dependency patterns, or application conventions.

V8 executes JavaScript

V8 is the JavaScript engine used by Node.

It parses and executes JavaScript, manages JavaScript objects/heap, and includes JIT optimization and garbage collection.

Node combines V8 with native runtime components that add capabilities a browser page normally does not have, such as direct filesystem and server socket APIs.

libuv provides much of the asynchronous runtime machinery

Node uses libuv, a native C library, for its event loop and many cross-platform asynchronous behaviors.

libuv helps coordinate:

  • network I/O
  • timers
  • selected filesystem/DNS work
  • an internal worker pool for certain operations

This is a key reason Node can keep one JavaScript thread productive while many I/O operations are waiting elsewhere.

Event-driven does not mean everything runs in parallel

Ordinary JavaScript callbacks in a Node process execute on a main event-loop thread.

If one callback performs a long CPU-heavy loop, other callbacks wait.

Node's scalability comes mainly from not blocking the JavaScript thread while asynchronous I/O waits.

For CPU-heavy JavaScript, use worker threads, processes, or another worker/service rather than monopolizing the main event loop.

async and await make I/O code readable

A typical asynchronous function can look synchronous:

async function loadOrder(id) {
  const order = await repository.find(id);
  return order;
}

While repository.find() is waiting asynchronously, Node can process other callbacks.

When the Promise resolves, continuation of the function runs later through Promise/microtask scheduling.

async does not make a synchronous CPU function non-blocking.

Node includes a large standard API surface

Modern Node includes modules/APIs for areas such as:

  • HTTP/HTTPS/HTTP2
  • TCP/UDP
  • filesystem/path
  • crypto/Web Crypto
  • streams
  • compression
  • child processes
  • worker threads
  • performance/diagnostics
  • testing
  • SQLite
  • Web Streams

The runtime has become substantially more capable without third-party packages than older Node tutorials suggest.

Node supports ES Modules and CommonJS

Node has two module systems.

ES Modules

import { readFile } from 'node:fs/promises';
export function load() {}

ES Modules are the JavaScript standard module format.

CommonJS

const fs = require('node:fs');
module.exports = something;

CommonJS is Node's older module system and remains widely used.

Modern projects should choose their module model deliberately and avoid mixing conventions accidentally.

package.json describes a Node package/application

A typical package.json can define:

  • package name/version
  • scripts
  • dependencies
  • module type
  • engines
  • exports

For ES Module .js files, projects often use:

{
  "type": "module"
}

Node uses package/module resolution rules to determine how files and dependencies are loaded.

npm manages packages

npm is the default package manager distributed with standard Node installations.

Install a dependency with:

npm install fastify

The package is recorded in the project manifest/lockfile depending on your workflow.

Commit your lockfile for normal applications so CI and developers resolve consistent dependency versions.

Dependencies run with your application's trust

A package can execute application-side code and, depending on install configuration, installation scripts.

Treat dependencies as supply-chain code:

  • minimize unnecessary packages
  • review important dependencies
  • scan vulnerabilities
  • keep versions supported
  • inspect suspicious lifecycle scripts

The convenience of npm should not turn dependency selection into a zero-review action.

Modern Node can run some TypeScript directly

Current Node includes stable built-in TypeScript type stripping for erasable TypeScript syntax.

That means selected .ts code can execute without a separate transpile step.

Important limitation: Node's built-in support does not perform TypeScript type checking and intentionally does not implement every tsconfig-dependent transform.

For full TypeScript compilation/type checking, use TypeScript/tooling as normal.

Node has built-in fetch

Modern Node provides a browser-compatible global fetch() implementation powered by Undici.

const response = await fetch('https://example.com/api');

For production calls, still design:

  • cancellation/timeouts
  • connection behavior
  • retries
  • idempotency

A built-in HTTP API does not make remote dependencies reliable automatically.

Streams process data incrementally

Node's HTTP requests/responses and many filesystem operations integrate with streams.

Instead of loading a huge file completely into memory:

read entire object -> transform -> send

you can process chunks:

read -> transform -> write

Streams are especially important for file transfer and high-throughput services because they support backpressure and lower peak memory.

Events are a core programming pattern

Node's EventEmitter lets objects publish named events:

emitter.on('ready', () => {
  console.log('ready');
});

Ordinary EventEmitter listeners are invoked synchronously when the event is emitted.

Do not assume “event” automatically means “runs later.”

Worker threads run JavaScript in parallel

node:worker_threads provides actual parallel JavaScript execution in separate threads.

Workers are most useful for CPU-intensive tasks.

Official docs explicitly note that they generally do not improve I/O-heavy work, because Node's asynchronous I/O already handles that efficiently.

Use worker pools for repeated tasks rather than spawning a new worker for every request.

Child processes provide stronger process isolation

Node can launch other processes with child_process.

Separate processes have separate V8 heaps and can isolate crashes/resources more strongly than worker threads.

Use them for:

  • external commands
  • independent process workloads
  • multi-process application patterns

Be careful with untrusted shell input; command construction can create injection vulnerabilities.

Node is garbage collected

Developers do not manually free normal JavaScript objects.

V8 reclaims objects that are no longer reachable.

You can still leak memory by keeping references alive through:

  • global caches
  • listeners
  • queues
  • closures

GC provides memory management, not automatic application lifecycle correctness.

Node and the browser share JavaScript, not all APIs

Both environments support JavaScript/ECMAScript features, but runtime APIs differ.

Browser code has things such as DOM APIs.

Node has things such as:

  • node:fs
  • process APIs
  • server sockets

Many web-standard APIs have become shared across both environments (fetch, Web Streams, Web Crypto), but do not assume every browser API exists in Node or vice versa.

What Node is good at

Node is a strong fit for:

  • JSON APIs
  • BFF services
  • realtime WebSocket servers
  • integration-heavy SaaS
  • streaming responses
  • CLI/build tooling
  • serverless functions

These workloads often spend much of their time waiting on network/storage rather than executing CPU-heavy JavaScript.

When Node may not be the best fit

Another runtime may be simpler for:

  • CPU-intensive algorithms that dominate request time
  • low-level systems software
  • highly constrained native resource environments
  • workloads whose key libraries live in another ecosystem

Node can still offload CPU work, but if nearly every request requires that workaround, reconsider the runtime boundary.

Current Node release model

Node publishes Current and LTS release lines.

Production teams generally prefer an active LTS line unless they specifically need Current features and accept the faster lifecycle.

Unsupported EOL releases stop receiving security fixes and gradually lose ecosystem support.

Keep runtime versions current and test major upgrades deliberately.

Beginner checklist

Remember:

  1. Node.js is a runtime, not a framework.
  2. V8 executes JavaScript.
  3. libuv provides the event loop and asynchronous runtime plumbing.
  4. I/O can wait without blocking JavaScript callbacks.
  5. CPU-heavy synchronous work blocks the main event loop.
  6. npm manages third-party packages.
  7. Node supports ES Modules and CommonJS.
  8. Modern Node includes built-in fetch, testing, TypeScript stripping, SQLite, streams, and more.
  9. Worker threads are for parallel CPU-heavy JavaScript.
  10. Garbage collection does not prevent logical memory leaks.

Node.js is best understood as JavaScript plus a server/runtime platform: V8 executes the language, libuv coordinates asynchronous work, and Node's standard library exposes operating-system and network capabilities needed to build production software.

Official references

Tags:Node.jsJavaScriptV8libuvnpmBackend Development
AI & AGENT ENGINEERING

BUILDING AN AI PRODUCT?

Talk to Lofingo about custom autonomous AI agents, enterprise workflow automation, and scalable software systems.

EXPLORE AI SERVICES →