Docker for Developers: Images, Containers, and Compose

DevOps2026-10-09TryQuickToolBox

You've probably heard about Docker and containers, but maybe you're not sure how they fit into your daily development workflow. Or perhaps you've tried Docker, but the concepts of images, containers, and Compose feel confusing. This guide will walk you through the essentials with practical examples, so you can start using Docker effectively in your projects.

What Are Docker Images and Containers?

Think of a Docker image as a blueprint for your application. It contains everything needed to run your code: the operating system, runtime, libraries, and your application files. Images are immutable and built from a Dockerfile.

A container is a running instance of an image. When you start a container, Docker creates an isolated environment from the image. You can run multiple containers from the same image, each with its own state.

Key Differences

Image Container
Read-only template Runnable instance
Built from Dockerfile Created from image
Stored in registry Runs on host
Immutable Ephemeral (can be stopped, started, deleted)

Building Your First Docker Image

Let's create a simple Node.js app and containerize it. Start with a Dockerfile in your project root:

# Use an official Node.js runtime as a parent image
FROM node:18-alpine

# Set the working directory
WORKDIR /app

# Copy package.json and package-lock.json
COPY package*.json ./

# Install dependencies
RUN npm ci --only=production

# Copy the rest of the application code
COPY . .

# Expose the port the app runs on
EXPOSE 3000

# Define the command to run the app
CMD ["node", "server.js"]

Build the image with:

docker build -t my-node-app .

Run a container from the image:

docker run -p 3000:3000 -d my-node-app

Your app is now accessible at http://localhost:3000.

Managing Containers

Here are essential commands to manage containers:

Simplifying Multi-Container Apps with Docker Compose

Real applications often need multiple services: a web server, a database, a cache, etc. Managing these with individual docker run commands is tedious. Docker Compose lets you define and run multi-container applications using a YAML file.

Create a docker-compose.yml:

version: '3.8'
services:
  web:
    build: .
    ports:
      - "3000:3000"
    environment:
      - NODE_ENV=production
      - DB_HOST=db
    depends_on:
      - db
  db:
    image: postgres:15-alpine
    environment:
      - POSTGRES_USER=user
      - POSTGRES_PASSWORD=password
      - POSTGRES_DB=mydb
    volumes:
      - postgres_data:/var/lib/postgresql/data
volumes:
  postgres_data:

Start all services with:

docker compose up -d

Stop and remove them with:

docker compose down

Best Practices for Development

FAQ

What is the difference between an image and a container?

An image is a read-only template that defines the application and its dependencies. A container is a running instance of an image, with a writable layer on top.

Can I use Docker Compose in production?

Docker Compose is primarily designed for development and testing. For production, consider orchestration tools like Kubernetes or Docker Swarm.

How do I persist data in Docker?

Use volumes or bind mounts. Volumes are managed by Docker and are the preferred way to persist data generated by containers.

Ready to containerize your app? If you need to convert documentation or guides to PDF for your team, try our Word to PDF converter to share polished docs.