Docker for Beginners: Complete Guide (2026)

 

Docker for Beginners: Complete Guide (2026)

Last Updated: March 2026 | 18 min read | For DevOps Beginners & Developers

If you're learning DevOps in 2026, Docker is non-negotiable. Every modern application runs in containers. Every CI/CD pipeline builds Docker images. Every Kubernetes cluster runs Docker containers. Yet most beginners find Docker confusing at first — what exactly is a container? How is it different from a virtual machine? How do you actually use it?

This guide covers everything you need to know about Docker — from installing it to deploying real applications — with hands-on examples you can follow along with right now.


Table of Contents

  1. What is Docker?
  2. Containers vs Virtual Machines
  3. Key Docker Concepts
  4. Installing Docker
  5. Essential Docker Commands
  6. Writing Your First Dockerfile
  7. Docker Volumes — Persisting Data
  8. Docker Networking
  9. Docker Compose — Multi-Container Apps
  10. Docker in CI/CD Pipelines
  11. Docker Best Practices
  12. Common Docker Interview Questions
  13. Quick Reference Cheat Sheet

1. What is Docker?

Docker is an open-source platform that allows you to package applications and their dependencies into portable, lightweight units called containers. These containers can run consistently on any machine — your laptop, a colleague's computer, a staging server, or a production cloud instance — without the dreaded "it works on my machine" problem.

Before Docker, deploying applications was painful:

  • Different environments had different software versions
  • "Works on my machine" was a constant problem
  • Setting up a new server took hours or days
  • Scaling applications required provisioning entire new servers

Docker solves all of this by bundling your application code, runtime, libraries, and configuration into a single container image that runs identically everywhere.

Simple analogy: Think of a Docker container like a shipping container. Before standardised shipping containers, every ship, truck, and warehouse had to be custom-built for different cargo. Standardised containers changed everything — the same container moves by ship, truck, and train without repacking. Docker does the same for software.

2. Containers vs Virtual Machines

This is one of the most common interview questions — and one of the most misunderstood concepts for beginners.

Virtual Machines (VMs)

A VM includes a full operating system on top of a hypervisor. Each VM has its own kernel, OS libraries, and application. They are heavy — typically 10–20GB each — and take minutes to start.

┌─────────────────────────────────┐
│         Your Application        │
├─────────────────────────────────┤
│         Guest OS (Full)         │
├─────────────────────────────────┤
│           Hypervisor            │
├─────────────────────────────────┤
│        Host Operating System    │
├─────────────────────────────────┤
│           Hardware              │
└─────────────────────────────────┘

Docker Containers

Containers share the host OS kernel. They only package the application and its dependencies — not a full OS. They are lightweight (typically 100MB–500MB), start in seconds, and run in isolation.

┌──────────┐ ┌──────────┐ ┌──────────┐
│  App A   │ │  App B   │ │  App C   │
│  + Deps  │ │  + Deps  │ │  + Deps  │
├──────────┴─┴──────────┴─┴──────────┤
│           Docker Engine            │
├────────────────────────────────────┤
│         Host Operating System      │
├────────────────────────────────────┤
│              Hardware              │
└────────────────────────────────────┘

Comparison Table

FeatureVirtual MachineDocker Container
Size10–20 GB100MB–500MB
Startup timeMinutesSeconds
OSFull guest OSShares host OS kernel
IsolationStrongGood (process-level)
PerformanceSlower (overhead)Near-native
PortabilityLimitedRuns anywhere
Use caseFull OS isolationApp packaging & scaling

3. Key Docker Concepts

Before jumping into commands, understand these five core concepts:

Docker Image

A read-only template used to create containers. Think of it as a blueprint or a class in programming. Images are built from a Dockerfile and stored in a registry.

Docker Container

A running instance of an image. Think of it as an object created from a class. You can run multiple containers from the same image simultaneously.

Dockerfile

A text file with instructions for building a Docker image — what base image to use, what files to copy, what commands to run.

Docker Registry

A storage system for Docker images. Docker Hub is the public registry. AWS ECR, Azure ACR, and Google GCR are private enterprise registries.

Docker Engine

The runtime that runs containers on your machine. It includes the Docker daemon (background service) and the Docker CLI (command line tool).

Dockerfile → docker build → Image → docker run → Container
                                  ↓
                             Docker Registry
                          (Docker Hub / ECR / ACR)

4. Installing Docker

On Ubuntu/Debian Linux

# Update package index
$ sudo apt update

# Install required packages
$ sudo apt install -y apt-transport-https ca-certificates curl software-properties-common

# Add Docker's official GPG key
$ curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -

# Add Docker repository
$ sudo add-apt-repository "deb [arch=amd64] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable"

# Install Docker
$ sudo apt update
$ sudo apt install -y docker-ce

# Start Docker service
$ sudo systemctl start docker
$ sudo systemctl enable docker

# Run Docker without sudo
$ sudo usermod -aG docker $USER
$ newgrp docker

# Verify installation
$ docker --version
Docker version 26.0.0, build abc1234

On Windows / Mac

Download and install Docker Desktop from docker.com/products/docker-desktop. It includes everything you need including the Docker CLI and a GUI dashboard.

Verify Installation

# Check Docker version
$ docker --version

# Run your first container
$ docker run hello-world

# Output:
Hello from Docker!
This message shows that your installation appears to be working correctly.

5. Essential Docker Commands

Working with Images

# Pull an image from Docker Hub
$ docker pull nginx

# Pull a specific version (tag)
$ docker pull nginx:1.25

# List all local images
$ docker images

# Remove an image
$ docker rmi nginx

# Remove all unused images
$ docker image prune -a

# Search for images on Docker Hub
$ docker search nginx

# Build an image from Dockerfile
$ docker build -t myapp:latest .

# Build with a specific Dockerfile
$ docker build -f Dockerfile.prod -t myapp:prod .

Working with Containers

# Run a container
$ docker run nginx

# Run in detached mode (background)
$ docker run -d nginx

# Run with a name
$ docker run -d --name my-nginx nginx

# Run with port mapping (host:container)
$ docker run -d -p 8080:80 nginx

# Run with environment variables
$ docker run -d -e APP_ENV=production myapp

# Run interactively with a terminal
$ docker run -it ubuntu bash

# List running containers
$ docker ps

# List all containers (including stopped)
$ docker ps -a

# Stop a container
$ docker stop my-nginx

# Start a stopped container
$ docker start my-nginx

# Restart a container
$ docker restart my-nginx

# Remove a container
$ docker rm my-nginx

# Force remove a running container
$ docker rm -f my-nginx

# Remove all stopped containers
$ docker container prune

Inspecting Containers

# View container logs
$ docker logs my-nginx

# Follow logs in real time
$ docker logs -f my-nginx

# Show last 50 lines of logs
$ docker logs --tail 50 my-nginx

# Execute a command inside running container
$ docker exec -it my-nginx bash

# Execute a single command
$ docker exec my-nginx nginx -t

# View container resource usage
$ docker stats

# Inspect container details
$ docker inspect my-nginx

# View container processes
$ docker top my-nginx

# Copy files from container to host
$ docker cp my-nginx:/etc/nginx/nginx.conf ./nginx.conf

# Copy files from host to container
$ docker cp ./nginx.conf my-nginx:/etc/nginx/nginx.conf

6. Writing Your First Dockerfile

A Dockerfile is a set of instructions that Docker follows to build your image. Each instruction creates a new layer in the image.

Dockerfile Instructions

InstructionWhat it does
FROMSets the base image
WORKDIRSets the working directory
COPYCopies files from host to image
ADDLike COPY but also handles URLs and tar files
RUNExecutes commands during build
ENVSets environment variables
EXPOSEDocuments which port the app uses
CMDDefault command when container starts
ENTRYPOINTMain command that always runs
VOLUMECreates a mount point for volumes
ARGBuild-time variables

Example 1 — Simple Node.js App

# Use official Node.js image as base
FROM node:18-alpine

# Set working directory
WORKDIR /app

# Copy package files first (for layer caching)
COPY package*.json ./

# Install dependencies
RUN npm install --production

# Copy application code
COPY . .

# Expose the port the app runs on
EXPOSE 3000

# Command to start the app
CMD ["node", "server.js"]

Example 2 — Python Flask App

FROM python:3.11-slim

WORKDIR /app

# Install dependencies first (better caching)
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

# Copy app code
COPY . .

EXPOSE 5000

CMD ["python", "app.py"]

Example 3 — Multi-Stage Build (Production Best Practice)

# Stage 1: Build
FROM node:18-alpine AS builder
WORKDIR /app
COPY package*.json ./
RUN npm install
COPY . .
RUN npm run build

# Stage 2: Production image (much smaller)
FROM nginx:alpine
COPY --from=builder /app/dist /usr/share/nginx/html
EXPOSE 80
CMD ["nginx", "-g", "daemon off;"]

Why multi-stage builds? The first stage installs all build tools and dependencies (large). The second stage only copies the final built files into a minimal image. Final image is 10x smaller with no build tools or source code exposed.

Build and Run Your Image

# Build the image
$ docker build -t myapp:latest .

# Run a container from your image
$ docker run -d -p 3000:3000 --name myapp myapp:latest

# Test it
$ curl http://localhost:3000

7. Docker Volumes — Persisting Data

By default, when a container is deleted, all data inside it is lost. Volumes solve this by storing data outside the container.

Types of Storage in Docker

  • Volumes — managed by Docker, stored in /var/lib/docker/volumes/. Best for production.
  • Bind mounts — maps a host directory directly into a container. Best for development.
  • tmpfs mounts — stored in memory only. Best for sensitive temporary data.

Working with Volumes

# Create a named volume
$ docker volume create mydata

# List volumes
$ docker volume ls

# Run container with a volume
$ docker run -d -v mydata:/var/lib/postgresql/data postgres

# Run container with a bind mount (dev use)
$ docker run -d -v $(pwd):/app myapp

# Inspect a volume
$ docker volume inspect mydata

# Remove a volume
$ docker volume rm mydata

# Remove all unused volumes
$ docker volume prune

Real World Example — PostgreSQL with Persistent Data

# Without volume — data lost when container is removed!
$ docker run -d postgres

# With volume — data persists across container restarts
$ docker run -d \
  --name postgres-db \
  -e POSTGRES_PASSWORD=mypassword \
  -e POSTGRES_DB=myapp \
  -v postgres-data:/var/lib/postgresql/data \
  -p 5432:5432 \
  postgres:15

8. Docker Networking

Docker networking allows containers to communicate with each other and with the outside world.

Default Network Drivers

  • bridge — default network for containers on the same host. Containers can communicate by container name.
  • host — container shares the host's network stack. No isolation.
  • none — no networking. Fully isolated container.
  • overlay — connects containers across multiple Docker hosts. Used in Docker Swarm.

Working with Networks

# List networks
$ docker network ls

# Create a custom network
$ docker network create myapp-network

# Run containers on the same network
$ docker run -d --network myapp-network --name db postgres
$ docker run -d --network myapp-network --name app myapp

# Now "app" container can reach "db" container using hostname "db"
$ docker exec app ping db

# Connect a running container to a network
$ docker network connect myapp-network my-nginx

# Inspect a network
$ docker network inspect myapp-network

# Remove a network
$ docker network rm myapp-network

9. Docker Compose — Multi-Container Apps

Real applications rarely run as a single container. A typical web app needs a web server, a database, a cache, and maybe a queue. Docker Compose lets you define and run multi-container applications using a single YAML file.

docker-compose.yml — Full Web App Example

version: '3.8'

services:
  # Web application
  app:
    build: .
    ports:
      - "3000:3000"
    environment:
      - DATABASE_URL=postgresql://postgres:password@db:5432/myapp
      - REDIS_URL=redis://redis:6379
    depends_on:
      - db
      - redis
    volumes:
      - ./logs:/app/logs
    restart: unless-stopped

  # PostgreSQL database
  db:
    image: postgres:15
    environment:
      - POSTGRES_USER=postgres
      - POSTGRES_PASSWORD=password
      - POSTGRES_DB=myapp
    volumes:
      - postgres-data:/var/lib/postgresql/data
    restart: unless-stopped

  # Redis cache
  redis:
    image: redis:7-alpine
    restart: unless-stopped

  # Nginx reverse proxy
  nginx:
    image: nginx:alpine
    ports:
      - "80:80"
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf
    depends_on:
      - app
    restart: unless-stopped

volumes:
  postgres-data:

Docker Compose Commands

# Start all services
$ docker compose up

# Start in background
$ docker compose up -d

# Stop all services
$ docker compose down

# Stop and remove volumes (careful!)
$ docker compose down -v

# View logs
$ docker compose logs

# Follow logs for a specific service
$ docker compose logs -f app

# Scale a service
$ docker compose up -d --scale app=3

# Rebuild images
$ docker compose up -d --build

# View running services
$ docker compose ps

# Execute command in a service
$ docker compose exec app bash

10. Docker in CI/CD Pipelines

In real DevOps work, Docker is at the heart of every CI/CD pipeline. Here is how a typical pipeline uses Docker:

# GitHub Actions — Build, Test, and Push Docker Image
name: Docker CI/CD

on:
  push:
    branches: [main]

jobs:
  build-and-push:
    runs-on: ubuntu-latest
    steps:
    - name: Checkout code
      uses: actions/checkout@v3

    - name: Login to Docker Hub
      uses: docker/login-action@v2
      with:
        username: ${{ secrets.DOCKER_USERNAME }}
        password: ${{ secrets.DOCKER_PASSWORD }}

    - name: Build Docker image
      run: docker build -t myapp:${{ github.sha }} .

    - name: Run tests inside container
      run: docker run myapp:${{ github.sha }} npm test

    - name: Push to Docker Hub
      run: |
        docker tag myapp:${{ github.sha }} vishwa/myapp:latest
        docker push vishwa/myapp:latest

    - name: Deploy to server
      run: |
        docker pull vishwa/myapp:latest
        docker stop myapp || true
        docker rm myapp || true
        docker run -d --name myapp -p 80:3000 vishwa/myapp:latest

11. Docker Best Practices

Use specific image tags — never use latest in production

# Bad — unpredictable, could break with updates
FROM node:latest

# Good — pinned to a specific version
FROM node:18.19-alpine3.19

Use .dockerignore to keep images small

# .dockerignore
node_modules
.git
.env
*.log
dist
coverage
README.md

One process per container
Don't run your database and web server in the same container. Each container should do one thing. Use Docker Compose to link multiple single-purpose containers.

Run as non-root user

FROM node:18-alpine
WORKDIR /app
COPY . .
RUN npm install

# Create non-root user
RUN addgroup -S appgroup && adduser -S appuser -G appgroup
USER appuser

CMD ["node", "server.js"]

Use multi-stage builds for smaller production images
As shown earlier — build in one stage, copy only what you need to the final image.

Order Dockerfile instructions for better caching

# Bad — copies all files first, cache breaks on any file change
COPY . .
RUN npm install

# Good — copies package.json first, npm install is cached unless dependencies change
COPY package*.json ./
RUN npm install
COPY . .

Never store secrets in Docker images
Use environment variables, Docker secrets, or a secrets manager like AWS Secrets Manager or HashiCorp Vault.

Always add health checks

HEALTHCHECK --interval=30s --timeout=10s --start-period=5s --retries=3 \
  CMD curl -f http://localhost:3000/health || exit 1

12. Common Docker Interview Questions

Q: What is the difference between a Docker image and a container?
An image is a read-only template used to create containers. A container is a running instance of an image. You can run many containers from the same image, just like creating many objects from the same class.

Q: What is the difference between CMD and ENTRYPOINT?
ENTRYPOINT defines the main command that always runs when the container starts. CMD provides default arguments that can be overridden at runtime. If you use both together, CMD acts as default arguments to ENTRYPOINT.

Q: How do you reduce Docker image size?
Use minimal base images (alpine), multi-stage builds, .dockerignore files, combine RUN commands to reduce layers, and avoid installing unnecessary packages.

Q: What is Docker Compose and when would you use it?
Docker Compose is a tool for defining and running multi-container applications using a YAML file. You use it when your application needs multiple services — like a web app with a database and cache — that need to work together.

Q: How does Docker networking work?
By default containers use a bridge network and are isolated from each other. You can create custom networks where containers can communicate using their container names as hostnames. The host network removes isolation and shares the host's network stack.

Q: What is a Docker volume and why is it needed?
A volume is a mechanism for persisting data generated by containers. Without volumes, all data inside a container is lost when it is deleted. Volumes store data outside the container's filesystem so it survives container restarts and deletions.

Q: What is a multi-stage build?
A multi-stage build uses multiple FROM instructions in one Dockerfile. Early stages handle building and compiling the application. The final stage copies only the built artifacts into a minimal base image — resulting in much smaller, more secure production images.

Q: What is the difference between COPY and ADD in a Dockerfile?
COPY simply copies files from host to image. ADD does everything COPY does but also supports extracting tar archives and downloading files from URLs. Best practice is to use COPY unless you specifically need ADD's extra features.

Q: How do you check why a container is crashing?
Use docker logs container-name to see output. Use docker inspect container-name to see detailed state. Use docker events to see real-time events. Check the exit code with docker ps -a.

Q: How do you share an image without using a registry?

# Save image to a tar file
$ docker save myapp:latest | gzip > myapp.tar.gz

# Load image from tar file on another machine
$ docker load < myapp.tar.gz

13. Quick Reference Cheat Sheet

CommandWhat it does
docker pull imageDownload image from registry
docker build -t name .Build image from Dockerfile
docker run -d -p 80:80 imageRun container in background with port
docker psList running containers
docker ps -aList all containers
docker logs -f nameFollow container logs
docker exec -it name bashShell into running container
docker stop nameStop a container gracefully
docker rm nameRemove a stopped container
docker imagesList local images
docker rmi imageRemove an image
docker volume lsList volumes
docker network lsList networks
docker compose up -dStart all services in background
docker compose downStop and remove all services
docker statsLive resource usage
docker inspect nameDetailed container info
docker system pruneRemove all unused resources

Wrapping Up

Docker is one of the most important skills in modern DevOps and software development. Once you understand containers, images, Dockerfiles, volumes, and networking — everything else in the DevOps ecosystem (Kubernetes, CI/CD, cloud deployments) becomes much easier to understand because they all build on Docker concepts.

Your Docker learning path:

  • Week 1: Install Docker, run containers, learn basic commands
  • Week 2: Write Dockerfiles, build and push your own images
  • Week 3: Set up Docker Compose for a multi-container app
  • Week 4: Integrate Docker into a CI/CD pipeline
  • Month 2: Learn Kubernetes — the next step after Docker

Found this helpful? Share it with someone learning DevOps. Have a question or suggestion? Reach out at vishwasekar43@gmail.com

— Vishwa, DevOpsVault

Comments

Popular posts from this blog

Linux Commands Every DevOps Engineer Must Know (2026 Complete Guide)

Docker Day 1: Containers Explained — VM vs Docker, Lifecycle & Buildah

Kubernetes Day 7: ConfigMaps & Secrets — Managing Config the Right Way