Node.js & Express

Node.js Environment Setup

25 min Lesson 2 of 40

Node.js Environment Setup

Before you can start building Node.js applications, you need to set up your development environment. In this lesson, we'll walk through installing Node.js, understanding npm (Node Package Manager), setting up your first project, and learning essential tools that will make your development workflow more efficient.

Installing Node.js

There are several ways to install Node.js on your system. We'll cover the most common methods for different operating systems.

Method 1: Official Installer (Recommended for Beginners)

The simplest way to install Node.js is through the official installer:

  1. Visit nodejs.org
  2. Download the LTS (Long Term Support) version for stability
  3. Run the installer and follow the installation wizard
  4. The installer includes both Node.js and npm
LTS vs Current:
  • LTS (Long Term Support): Stable, recommended for production applications. Receives updates for 30 months.
  • Current: Latest features, but may have breaking changes. Good for experimentation.

Verify Installation

After installation, verify that Node.js and npm are installed correctly:

# Check Node.js version node --version # Output: v20.11.0 (or your installed version) # Check npm version npm --version # Output: 10.2.4 (or your installed version) # Run Node.js REPL (Read-Eval-Print Loop) node > console.log('Hello Node.js!'); Hello Node.js! > .exit

Method 2: Using NVM (Node Version Manager)

NVM allows you to install and manage multiple Node.js versions on the same machine. This is extremely useful when working on different projects that require different Node.js versions.

Why Use NVM?
  • Switch between Node.js versions instantly
  • Test your application on different Node.js versions
  • Avoid permission issues with npm global packages
  • Essential for professional development workflows

Installing NVM on macOS/Linux:

# Install NVM using curl curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.7/install.sh | bash # Or using wget wget -qO- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.7/install.sh | bash # Reload shell configuration source ~/.bashrc # or ~/.zshrc for zsh # Verify NVM installation nvm --version

Installing NVM on Windows:

# Download and install nvm-windows from: # https://github.com/coreybutler/nvm-windows/releases # After installation, verify in PowerShell or CMD nvm version

Using NVM Commands

# List available Node.js versions nvm ls-remote # macOS/Linux nvm list available # Windows # Install specific Node.js version nvm install 20.11.0 # Install latest LTS version nvm install --lts # List installed versions nvm ls # Switch to specific version nvm use 20.11.0 # Set default Node.js version nvm alias default 20.11.0 # Check current version nvm current

Practice: Managing Multiple Node.js Versions

# Install two different versions nvm install 18.19.0 nvm install 20.11.0 # Create a test file echo "console.log(process.version);" > version-test.js # Test with different versions nvm use 18.19.0 node version-test.js # Output: v18.19.0 nvm use 20.11.0 node version-test.js # Output: v20.11.0

Understanding npm (Node Package Manager)

npm is the default package manager for Node.js. It allows you to install, update, and manage third-party packages (libraries and frameworks) for your projects.

What is npm?

  • Package Registry: The world's largest software registry with over 2 million packages
  • Command-Line Tool: Installed automatically with Node.js
  • Dependency Manager: Manages project dependencies and their versions

Essential npm Commands

# Initialize a new Node.js project npm init # Interactive setup npm init -y # Quick setup with defaults # Install packages npm install express # Install locally npm install -g nodemon # Install globally npm install lodash --save-dev # Install as dev dependency # Install all dependencies from package.json npm install # Update packages npm update # Update all packages npm update express # Update specific package # Uninstall packages npm uninstall express npm uninstall -g nodemon # List installed packages npm list # Project dependencies npm list -g --depth=0 # Global packages # Check for outdated packages npm outdated # Run scripts defined in package.json npm run start npm run test npm run build
Global vs Local Installation:
  • Local: Installed in project's node_modules folder. Used for project dependencies.
  • Global: Installed system-wide. Use sparingly, mainly for CLI tools like nodemon, typescript, create-react-app.

Understanding package.json

The package.json file is the heart of any Node.js project. It contains metadata about your project and manages dependencies.

Creating package.json

# Interactive creation npm init # Sample questions: # package name: (my-project) # version: (1.0.0) # description: My awesome Node.js project # entry point: (index.js) # test command: jest # git repository: https://github.com/username/my-project # keywords: nodejs, express, api # author: Your Name # license: (ISC) MIT

Sample package.json Structure

{ "name": "my-nodejs-project", "version": "1.0.0", "description": "A sample Node.js application", "main": "index.js", "scripts": { "start": "node index.js", "dev": "nodemon index.js", "test": "jest", "build": "webpack --mode production" }, "keywords": ["nodejs", "express", "api"], "author": "Your Name <your.email@example.com>", "license": "MIT", "dependencies": { "express": "^4.18.2", "dotenv": "^16.4.1" }, "devDependencies": { "nodemon": "^3.0.3", "jest": "^29.7.0" }, "engines": { "node": ">=18.0.0", "npm": ">=9.0.0" } }

Understanding Dependencies

Types of Dependencies:
  • dependencies: Packages required for production (e.g., express, mongoose)
  • devDependencies: Packages needed only during development (e.g., testing tools, bundlers)
  • peerDependencies: Packages that your package expects the consumer to have
  • optionalDependencies: Packages that won't break installation if they fail

Semantic Versioning (SemVer)

npm uses semantic versioning for package versions: MAJOR.MINOR.PATCH

// Version format: MAJOR.MINOR.PATCH "express": "4.18.2" // ^ ^ ^ // | | └─ Patch: Bug fixes (4.18.2 → 4.18.3) // | └───── Minor: New features, backward compatible (4.18.x → 4.19.0) // └──────── Major: Breaking changes (4.x.x → 5.0.0) // Version range symbols: "express": "^4.18.2" // Install 4.x.x (allows minor and patch updates) "lodash": "~4.17.21" // Install 4.17.x (allows only patch updates) "axios": "1.6.5" // Install exactly 1.6.5 "jest": "*" // Install latest version (not recommended) "react": ">=18.0.0" // Install 18.0.0 or higher
Best Practice: Use ^ for dependencies to get bug fixes and new features automatically, but be careful with major version updates as they may contain breaking changes.

npm Scripts

npm scripts allow you to automate common tasks in your development workflow.

{ "scripts": { // Start production server "start": "node server.js", // Development with auto-restart "dev": "nodemon server.js", // Run tests "test": "jest --coverage", "test:watch": "jest --watch", // Linting "lint": "eslint .", "lint:fix": "eslint . --fix", // Build for production "build": "webpack --mode production", // Database migrations "migrate": "node migrate.js", // Custom scripts "seed": "node database/seed.js", "deploy": "npm run build && npm run migrate" } }

Running npm scripts:

# Special scripts (no 'run' needed) npm start npm test # Custom scripts (require 'run') npm run dev npm run build npm run lint # Pass arguments to scripts npm run dev -- --port=4000 npm test -- --verbose

Setting Up Your First Node.js Project

Let's create a complete Node.js project from scratch:

# Step 1: Create project directory mkdir my-first-nodejs-app cd my-first-nodejs-app # Step 2: Initialize npm npm init -y # Step 3: Create project structure mkdir src touch src/index.js touch .gitignore # Step 4: Install dependencies npm install express npm install --save-dev nodemon # Step 5: Create .gitignore file echo "node_modules/" >> .gitignore echo ".env" >> .gitignore echo "*.log" >> .gitignore

Create Your First Server (src/index.js)

// src/index.js const express = require('express'); const app = express(); const PORT = process.env.PORT || 3000; // Middleware app.use(express.json()); // Routes app.get('/', (req, res) => { res.json({ message: 'Welcome to my Node.js app!', timestamp: new Date().toISOString() }); }); app.get('/api/hello/:name', (req, res) => { const { name } = req.params; res.json({ greeting: `Hello, ${name}!`, version: '1.0.0' }); }); // Start server app.listen(PORT, () => { console.log(`Server is running on http://localhost:${PORT}`); });

Update package.json Scripts

{ "scripts": { "start": "node src/index.js", "dev": "nodemon src/index.js" } }

Run Your Application

# Development mode (auto-restart on file changes) npm run dev # Production mode npm start # Test the endpoints: # Open browser: http://localhost:3000 # Or use curl: curl http://localhost:3000 curl http://localhost:3000/api/hello/Node

Essential Development Tools

1. Nodemon - Auto-Restart Server

# Install nodemon npm install --save-dev nodemon # Create nodemon.json for configuration { "watch": ["src"], "ext": "js,json", "ignore": ["src/**/*.test.js"], "exec": "node src/index.js" } # Use in package.json "dev": "nodemon src/index.js"

2. dotenv - Environment Variables

# Install dotenv npm install dotenv # Create .env file PORT=3000 DATABASE_URL=mongodb://localhost:27017/myapp API_KEY=your-secret-api-key NODE_ENV=development # Load in your app require('dotenv').config(); const PORT = process.env.PORT || 3000; const dbUrl = process.env.DATABASE_URL;
Security: Never commit .env files to version control! Always add them to .gitignore.

3. ESLint - Code Linting

# Install ESLint npm install --save-dev eslint # Initialize ESLint npx eslint --init # Run ESLint npm run lint # Auto-fix issues npm run lint:fix

Understanding node_modules

The node_modules folder contains all installed packages and their dependencies.

Important Facts:
  • Can grow very large (100s of MB)
  • Should NEVER be committed to version control
  • Can be regenerated using npm install
  • Contains nested dependencies (dependencies of dependencies)

package-lock.json

This file locks the exact versions of all dependencies and sub-dependencies:

  • Ensures consistent installations across different environments
  • Improves installation speed
  • Should be committed to version control
  • Automatically generated by npm

Complete Project Setup Exercise

Create a complete Node.js API project with the following requirements:

  1. Initialize a new project with npm
  2. Install express and dotenv as dependencies
  3. Install nodemon as a dev dependency
  4. Create a .env file with PORT and APP_NAME variables
  5. Create an Express server with these endpoints:
    • GET / - Returns welcome message with app name from .env
    • GET /health - Returns server health status
    • POST /api/echo - Returns the request body
  6. Add npm scripts for development and production
  7. Create a proper .gitignore file
  8. Test all endpoints

Troubleshooting Common Issues

Issue 1: npm Permission Errors (macOS/Linux)

# Problem: EACCES errors when installing global packages # Solution: Use nvm (recommended) or fix npm permissions # Fix npm permissions (if not using nvm) mkdir ~/.npm-global npm config set prefix '~/.npm-global' echo 'export PATH=~/.npm-global/bin:$PATH' >> ~/.bashrc source ~/.bashrc

Issue 2: Module Not Found Errors

# Problem: Cannot find module 'express' # Solution: Install missing dependencies npm install # Install all dependencies from package.json # or npm install express # Install specific package

Issue 3: Port Already in Use

# Problem: Error: listen EADDRINUSE :::3000 # Solution: Kill the process using the port # Find process using port 3000 lsof -i :3000 # macOS/Linux netstat -ano | findstr :3000 # Windows # Kill the process kill -9 <PID> # macOS/Linux taskkill /PID <PID> /F # Windows

Summary

In this lesson, you've learned:

  • How to install Node.js using official installer or NVM
  • NVM allows managing multiple Node.js versions
  • npm is the package manager for installing and managing dependencies
  • package.json contains project metadata and dependencies
  • npm scripts automate common development tasks
  • Essential tools: nodemon, dotenv, ESLint
  • How to create and run your first Node.js project

In the next lesson, we'll explore Node.js core modules and learn how to work with the file system, HTTP servers, and more!