Skip to content

Node.js Basics

Before building servers and APIs, you need a working mental model of what a Node.js program is made of. This lesson covers globals, the process object, modules, and how execution flows through a Node.js file.

The Building Blocks of a Node.js Program

Every Node.js file is treated as a module. At the top of that module you have access to Node-specific globals, process, console, __dirname/__filename (in CommonJS), Buffer, and timer functions like setTimeout, without importing anything.

The process object is your window into the running Node.js instance: command-line arguments (process.argv), environment variables (process.env), and the ability to exit the program (process.exit()) or react to signals.

console.log('Script started');
console.log('Arguments:', process.argv.slice(2));
console.log('Node env:', process.env.NODE_ENV || 'development');

process.on('exit', (code) => {
  console.log('Exiting with code', code);
});

process.argv is an array where the first two entries are the node binary path and the script path; anything after that is your actual command-line arguments.

Common Global Objects

console.log(...)     // logging
process.env           // environment variables
process.argv          // command-line arguments
__dirname             // current directory (CommonJS)
setTimeout(fn, ms)    // schedule work later
  • console provides log, error, warn, info, and table for structured output.
  • process exposes runtime information and control (env, argv, exit, platform).
  • __dirname and __filename exist only in CommonJS modules, not ES modules.
  • Timers (setTimeout, setInterval, setImmediate) are globals, not imports.

Node.js Basics Cheatsheet

Globals and objects you will reach for constantly while writing Node.js scripts.

Global Example Purpose
Logging console.log('hi') Print output to stdout
Env vars process.env.PORT Read configuration from the environment
Args process.argv Read command-line arguments
Exit code process.exit(1) Stop the process with a status code
Timer setTimeout(fn, 1000) Run code after a delay
Binary data Buffer.from('hi') Work with raw binary data

The process Object

process is a global instance that represents the currently running Node.js process. It is available everywhere without an import and is one of the most frequently used objects in real applications, especially for reading configuration and handling shutdown.

console.log(process.platform);  // 'darwin', 'linux', 'win32'
console.log(process.version);   // 'v22.12.0'
console.log(process.pid);       // process id

process.on('SIGINT', () => {
  console.log('Received SIGINT, shutting down gracefully...');
  process.exit(0);
});

Listening for SIGINT lets your program clean up (close database connections, finish in-flight requests) before exiting when a user presses Ctrl+C.

Every File Is a Module

Node.js does not run files in one shared global scope the way browser <script> tags can. Each file is wrapped as its own module with its own scope, and you explicitly export values from one file and import/require them in another. Modules are covered in depth in the next lessons.

  • Variables declared in one file are not automatically visible in another.
  • You share code between files using module.exports/require (CommonJS) or export/import (ES modules).
  • This module boundary is what makes large Node.js codebases maintainable.

Common Mistakes

  • Assuming variables from one file leak into another file without an explicit import.
  • Using __dirname inside an ES module file, where it is not defined by default.
  • Forgetting that process.env values are always strings, even for numbers and booleans.
  • Calling process.exit() before asynchronous cleanup (like closing a database) has finished.

Key Takeaways

  • Node.js gives you globals like console, process, and timers without any imports.
  • process exposes environment variables, arguments, and process control.
  • Every file is its own module with its own scope.
  • process.env values are always strings and need explicit parsing for numbers or booleans.

Pro Tip

Wrap process.env.PORT (and similar values) with Number(...) or a small config-parsing helper at startup, so the rest of your app can trust that PORT is already a number, not a string.