Node.js Interview Prep: Questions + Answers (With Code Examples)

Adam Odziemkowski
Adam Odziemkowski
hero image

Are you ready to ace your first Node.js interview?

It’s an exciting milestone, but I get it—there’s a bit of anxiety mixed in too. What if they ask a question that catches you off guard? Don’t worry, you’re not alone.

Here’s the good news: this guide is designed to help you prepare step-by-step. You’ll find the answers to common interview questions, explained in plain language, so you can truly understand them—not just memorize them. Whether you’re nailing down the basics of Node.js, tackling tricky asynchronous tasks, or diving into advanced topics, this guide will give you the confidence to walk into your interview feeling prepared.

By the time you’re done here, you won’t just know what to say; you’ll know why it matters. So grab a coffee, settle in, and let’s get started on the path to your dream job!

Sidenote: If you find that you’re struggling with the questions in this guide, or perhaps feel that you could use some more training, or simply want to build some more impressive projects for your portfolio, then check out my complete Node.js Developer course:

Learn Node.js in 2025

This is the only Node.js course you need to learn Node, build advanced large-scale apps from scratch, and get hired as a Backend Developer or Node JS Developer in 2025!

With that out of the way, let’s get into the questions.

Beginner Node.js interview questions

#1. What is Node.js, and why is it used?

Node.js is a runtime environment that allows you to run JavaScript outside the browser.

Traditionally, JavaScript was limited to frontend tasks, but Node.js expanded its use to backend development,** enabling developers to build the entire stack of an application using one language**.

Another key feature of Node.js is its non-blocking, event-driven architecture. This design allows it to handle multiple tasks simultaneously, such as processing user requests or fetching data from a database, without waiting for one task to finish.

Because of this efficiency, Node.js is widely used for real-time applications like chat systems, RESTful APIs, and IoT solutions.

#2. What is the Node.js event loop?

The event loop is the core mechanism that enables Node.js to handle multiple tasks efficiently on a single thread.

When you perform an operation like reading a file, Node.js doesn’t wait for the task to complete. Instead, it delegates the task to the operating system and moves on to handle other tasks in the queue. Once the task finishes, the event loop picks up the result and executes the associated callback function.

This asynchronous, non-blocking approach is what makes Node.js highly scalable and efficient, especially for I/O-intensive tasks like serving multiple users or processing API requests.

#3. What are npm and package.json?

npm, short for Node Package Manager, is a tool for managing dependencies in your Node.js projects. It allows you to install, update, and remove libraries (called packages) with ease, saving you time and effort when adding functionality to your applications.

The package.json file serves as the blueprint for your project. It includes essential details like the project name, version, dependencies, and scripts for automating tasks like starting your app or running tests. For example, installing a library like Express using npm automatically updates your package.json file to track the dependency.

Together, npm and package.json streamline development and ensure consistency across environments.

#4. How do you create a basic HTTP server in Node.js?

Node.js makes it simple to create an HTTP server using the built-in http module.

For example

const http = require('http');

const server = http.createServer((req, res) => {
  res.writeHead(200, { 'Content-Type': 'text/plain' });
  res.end('Hello, World!');
});

server.listen(3000, () => {
  console.log('Server is running on http://localhost:3000');
});

Here’s what happens:

  • The http.createServer method creates the server
  • A callback function handles incoming requests and sends responses
  • The listen method specifies the port (3000) where the server will run

This example demonstrates the foundation of a Node.js web server, which you can expand with routing, middleware, or database integration.

#5. What are the differences between require() and import?

Both require() and import are used to include code from other files or libraries, but they belong to different module systems.

require()

  • Part of CommonJS, the default module system in Node.js
  • Synchronous and works in all Node.js versions without additional configuration

For example, using require():

const fs = require('fs');

import:

  • Part of ES6 modules, offering a modern and concise syntax
  • Asynchronous and requires enabling ES modules by adding "type": "module" to your package.json

For example

import fs from 'fs';

In modern projects, import is preferred for its cleaner syntax and consistency with the broader JavaScript ecosystem, while require() remains common in older codebases.

#6. What is the fs module, and how do synchronous and asynchronous file operations work in Node.js?

The fs module provides tools to interact with the file system, such as reading, writing, or deleting files and directories.

Here’s an example of reading a file asynchronously:

const fs = require('fs');

fs.readFile('example.txt', 'utf8', (err, data) => {
  if (err) {
	console.error(err);
	return;
  }
  console.log(data);
});

For synchronous operations:

const data = fs.readFileSync('example.txt', 'utf8'); // Blocks further execution
console.log(data);
  • Synchronous Methods: Block the rest of the application while completing the operation
  • Asynchronous Methods: Use callbacks or promises to keep the application responsive

Asynchronous methods are generally preferred for scalability, except during initialization tasks like loading configurations.

#7. What are modules in Node.js, and how do you use them?

Modules in Node.js are reusable blocks of code that help organize functionality into smaller, manageable pieces.

There are three types of modules:

  1. Core Modules: Built into Node.js (e.g., fs, http, path)
  2. Local Modules: Custom modules you create within your project
  3. Third-Party Modules: Installed via npm (e.g., Express)

Here’s an example of a local module.

math.js

 function add(a, b) {
  return a + b;
}

module.exports = add;

In app.js:

const add = require('./math');
console.log(add(2, 3)); // Output: 5

Modules promote reusability, maintainability, and separation of concerns in your code.

#8. What are streams in Node.js, and how do they work?

Streams in Node.js process data piece-by-piece, making them memory-efficient for handling large datasets. Instead of loading everything into memory at once, streams process data in chunks.

There are four types of streams:

  1. Readable: For reading data (e.g., file or API)
  2. Writable: For writing data (e.g., to a file or network)
  3. Duplex: For both reading and writing (e.g., network sockets)
  4. Transform: For modifying data as it flows (e.g., compression)

For example (Readable Stream):

const fs = require('fs');
const readableStream = fs.createReadStream('largeFile.txt', 'utf8');

readableStream.on('data', (chunk) => {
  console.log('Chunk received:', chunk);
});

readableStream.on('end', () => {
  console.log('File reading completed');
});

Streams are essential for tasks like processing large files, streaming video, or handling real-time data.

Intermediate Node.js interview questions

#9. What is middleware in Node.js, and how is it used in Express?

Middleware in Node.js is a function that has access to the request and response objects, as well as the next() function. It’s commonly used in Express to handle tasks like logging, authentication, error handling, and parsing incoming requests.

Here’s an example of a simple logging middleware:

const express = require('express');
const app = express();

app.use((req, res, next) => {
  console.log(`${req.method} request to ${req.url}`);
  next(); // Pass control to the next middleware
});

app.get('/', (req, res) => {
  res.send('Hello, World!');
});

app.listen(3000, () => console.log('Server running on http://localhost:3000'));

In this example:

  • Middleware logs the HTTP method and URL for every request
  • Middleware functions execute in the order they’re defined, making them flexible for building modular and reusable application features

#10. How do you handle errors in Node.js?

Error handling is essential in Node.js, especially since many operations are asynchronous. There are several common patterns:

Using Callbacks

Many asynchronous methods accept a callback with an err parameter.

fs.readFile('file.txt', 'utf8', (err, data) => {
  if (err) {
	console.error('Error reading file:', err.message);
	return;
  }
  console.log(data);
});

Using Promises

Promises handle errors with .catch().

fs.promises.readFile('file.txt', 'utf8')
  .then((data) => console.log(data))
  .catch((err) => console.error('Error:', err.message));

Using try...catch with Async/Await

Async/await provides a clean way to handle errors.

async function readFile() {
  try {
	const data = await fs.promises.readFile('file.txt', 'utf8');
	console.log(data);
  } catch (err) {
	console.error('Error:', err.message);
  }
}
readFile();

Each method is suited to different scenarios, but async/await is preferred in modern applications for its readability.

#11. How do you implement routing in a Node.js application?

Routing defines how an application responds to HTTP requests for specific endpoints (URLs) and HTTP methods (GET, POST, etc.).

In Node.js, you can handle routing with the built-in http module, but using a framework like Express significantly simplifies the process.

For example (Using Express):

const express = require('express');
const app = express();

// Define routes
app.get('/', (req, res) => {
  res.send('Welcome to the homepage!');
});

app.get('/about', (req, res) => {
  res.send('This is the about page.');
});

app.post('/submit', (req, res) => {
  res.send('Form submitted!');
});

// Start the server
app.listen(3000, () => {
  console.log('Server running on http://localhost:3000');
});

How it works:

  1. Routes are defined for specific HTTP methods and endpoints, such as GET / or POST /submit
  2. Each route includes a handler function that specifies how the server responds. For example, the GET /about route sends a message: "This is the about page"
  3. The listen method starts the server, making it accessible on the specified port

Why use Express for routing?

  • Simplified Syntax: Express reduces boilerplate code, making routes easy to define and manage
  • Middleware Integration: Middleware can be attached to routes for tasks like authentication, logging, or validation
  • Scalability: For larger applications, you can group related routes into separate modules, keeping your codebase organized and maintainable

#12. How do you manage environment variables in Node.js?

Environment variables store configuration details, such as database credentials or API keys, outside your codebase. This makes your application more secure and flexible across environments like development, testing, and production.

To manage environment variables:

Install the dotenv package:

npm install dotenv

Create a .env file:

DB_HOST=localhost
DB_USER=root
DB_PASS=securepassword

Load variables in your application:

require('dotenv').config();

const dbHost = process.env.DB_HOST;
console.log(`Connecting to database at ${dbHost}`);

Environment variables ensure sensitive information isn’t hardcoded and make deployment across environments seamless.

Advanced Node.js interview questions

This section covers more complex topics, focusing on optimization, scalability, and advanced concepts in Node.js.

#13. What is clustering in Node.js, and how does it improve performance?

Clustering in Node.js allows you to create multiple instances of your application to take advantage of multi-core processors. By default, Node.js runs on a single thread, but clustering enables the workload to be distributed across multiple CPU cores.

Here’s an example:

const cluster = require('cluster');
const http = require('http');
const os = require('os');

if (cluster.isMaster) {
  const numCPUs = os.cpus().length;
  for (let i = 0; i < numCPUs; i++) {
	cluster.fork(); // Create a worker process
  }
} else {
  http.createServer((req, res) => {
	res.writeHead(200);
	res.end('Hello, World!');
  }).listen(3000);
}

In this setup:

  • The master process forks a worker process for each CPU core
  • Each worker handles incoming requests, distributing the load and improving performance

Clustering is ideal for CPU-intensive tasks and high-traffic applications.

#14. What are child processes in Node.js, and how are they used?

Child processes allow you to run system commands or execute scripts in parallel with your main application. This is particularly useful for offloading heavy computations or running isolated tasks.

Node.js provides four methods to create child processes:

  1. exec: Executes a shell command and buffers the output
  2. spawn: Launches a new process with a command and streams the output
  3. fork: Spawns a new Node.js process to run a module
  4. execFile: Executes a file directly without spawning a shell

Example using spawn:

const { spawn } = require('child_process');

const ls = spawn('ls', ['-lh']);

ls.stdout.on('data', (data) => {
  console.log(`Output: ${data}`);
});

ls.stderr.on('data', (data) => {
  console.error(`Error: ${data}`);
});

ls.on('close', (code) => {
  console.log(`Process exited with code ${code}`);
});

Child processes are valuable for parallel execution, and avoiding blocking the main thread.

#15. What are worker threads in Node.js, and when should you use them?

Worker threads allow you to run JavaScript code in parallel threads, which is useful for CPU-intensive tasks. Unlike child processes, worker threads share memory with the main thread, making them more efficient for tasks requiring shared state.

Example using worker threads:

const { Worker } = require('worker_threads');

if (isMainThread) {
  const worker = new Worker('./worker.js');
  worker.on('message', (msg) => console.log(`Message from worker: ${msg}`));
} else {
  parentPort.postMessage('Hello from the worker thread!');
}

We use worker threads for computationally expensive tasks, like algorithms or data processing, where shared memory access is beneficial.

#16. What is event loop starvation, and how can it be prevented?

Event loop starvation occurs when long-running tasks block the event loop, preventing it from handling other tasks. This can make your application unresponsive.

Example of a blocking task:

while (true) {
  // This loop blocks the event loop
}

How to prevent event loop starvation:

  • Use worker threads: Offload CPU-intensive tasks to separate threads
  • Asynchronous operations: Avoid blocking the event loop with synchronous methods
  • Split tasks into smaller chunks: Process large tasks incrementally to allow the event loop to handle other operations in between

By designing your application with non-blocking principles, you can keep the event loop responsive and ensure scalability.

#17. What are the differences between process.nextTick() and setImmediate()?

Both process.nextTick() and setImmediate() schedule callbacks for asynchronous execution, but they differ in when they execute:

  • process.nextTick(): Executes callbacks at the end of the current operation, before any I/O events are processed
  • setImmediate(): Executes callbacks after I/O events, as part of the check phase in the event loop

For example:

process.nextTick(() => console.log('This runs first'));
setImmediate(() => console.log('This runs second'));
console.log('This runs before both');

Output:

This runs before both  
This runs first  
This runs second  

Use process.nextTick() for tasks that need to execute immediately after the current operation and setImmediate() for tasks that can wait until the I/O cycle completes.

#18. How do you debug memory leaks in Node.js?

Memory leaks occur when memory that is no longer needed is not released.

Common causes include unreferenced variables, event listeners not being removed, or large objects being unintentionally kept in scope.

Steps to debug memory leaks:

  1. Monitor memory usage: Use process.memoryUsage() to track memory over time
  2. Capture heap snapshots: Use Chrome DevTools or the v8 module to analyze memory usage
  3. Use diagnostic tools: Tools like clinic.js, memwatch, or node-inspect help identify memory leaks
  4. Remove unused listeners: Ensure event listeners are properly removed using removeListener or off

By proactively profiling and monitoring your application, you can identify and fix memory leaks before they impact performance.

How did you do?

There you have it - 18 of the most common Node.js questions and answers that you might encounter in your interview.

What did you score? Did you nail all 18 questions? If so, it might be time to move from studying to actively interviewing!

Didn't get them all? Got tripped up on a few or some of the details? Don't worry; I'm here to help.

If you want to fast-track your Node.js knowledge and interview prep, and get as much hands-on practice as possible, then check out my complete Node.js course:

Learn Node.js in 2025

Like I said earlier, this is the only Node.js course you need to learn Node, build advanced large-scale apps from scratch, and get hired as a Backend Developer or Node JS Developer in 2025!

Plus, once you join, you'll have the opportunity to ask questions in our private Discord community from me, other students and working tech professionals.


If you join or not, I just want to wish you the best of luck with your interview!

More from Zero To Mastery

Want to be a Web Developer? Learn Node.js not PHP preview
Want to be a Web Developer? Learn Node.js not PHP

In this article, I show you a framework for deciding on what tools, programming languages, frameworks, and libraries you should learn next throughout your career as a developer.

Top 5 Node.js Projects: Beginner To Advanced preview
Top 5 Node.js Projects: Beginner To Advanced

Want to up your skills & build a badass project portfolio? Build these 5 NodeJS projects to show prospective employers you know the most important Node skills.

[Guide] Computer Science For Beginners preview
[Guide] Computer Science For Beginners

You DO NOT need a CS Degree to get hired as a Developer. Learn Computer Sciences Basics today with this free guide by a Senior Dev with 10+ years of experience.