⚙️ DevOps

How Docker Works: Architecture & Containers

📅 July 03, 2026NEW7 min readITVedas

<p>Docker packages your entire application—code, libraries, settings—into a lightweight container that runs identically on any computer. Since Docker launched in 2013, over 13 million developers have adopted it because containers solve a massive problem: "it works on my laptop but breaks on the server." This guide explains the architecture behind containers without assuming you know what a kernel is.</p>

ADVANCED
⏱ 7 min read
Prerequisites:
Key Facts
  • Docker was released in 2013 and now has over 13 million developers using the platform globally
  • Docker uses Linux kernel namespaces and cgroups to isolate containers with minimal overhead compared to virtual machines
  • Docker images are built in layers using a Dockerfile, with each instruction creating a new immutable layer that can be reused and cached

What Is a Container? Start Here.

Forget the jargon for a moment. A container is like a shrink-wrapped box containing everything your app needs to run: the code, the Python interpreter, the database driver, even the specific version of Linux libraries.

When you ship a physical product, you put it in a box. The box protects it during transport. A software container works the same way—it isolates your application from the outside world. Inside the container, your app thinks it owns the entire computer. Outside, multiple containers share the same machine without interfering with each other. Think of it this way: your laptop might have Python 3.9 installed, but a container might need Python 3.11. Both versions run side-by-side without conflict.

The magic happens because Docker uses Linux kernel features called namespaces and cgroups. Namespaces create isolated views of system resources—each container sees its own file system, network interfaces, and process IDs. Cgroups limit how much CPU and memory each container can use. Together, they isolate containers with minimal overhead, which is why Docker is so much faster than traditional virtual machines.

Docker vs. Virtual Machines: Why Containers Win

Before Docker, teams used virtual machines (VMs) to isolate applications.

A VM is heavy. It emulates an entire computer—it needs its own operating system, which eats ~2GB of RAM and takes minutes to boot. If you run 10 VMs on one server, you're running 10 operating systems. Docker containers share the host's operating system kernel, so each container uses only ~5-15MB of RAM and starts in milliseconds. A single server can run 50+ containers where it might run only 3-4 VMs.

Here's the practical difference:

We'll dive deeper into this comparison in our Docker vs Virtual Machines guide, but the short version: containers let you pack more applications on less hardware.

The Docker Architecture: Layers You Should Know

Docker's architecture has three key parts: the Docker Engine, images, and containers.

The Docker Engine is software that runs on your computer or server. It manages images and runs containers. When you type a Docker command, it talks to the Engine, which does the actual work. The Engine includes a daemon (a background process) and a CLI (command-line interface). You don't need to know about this to use Docker, but it's good to know something is managing containers behind the scenes.

A Docker image is a blueprint. It's a read-only template that says: "To run my app, start with Ubuntu Linux, install Python 3.11, copy my code, and run this command." Images are built in layers. Each instruction in a Dockerfile creates a new layer. This layering system is crucial—Docker caches layers, so rebuilding an image is fast. If only your code changed, Docker reuses the layers for the OS and dependencies.

A Docker container is a running instance of an image. You can create 100 containers from one image, just like you can print 100 copies of a blueprint. Each container has its own file system, network, and isolated process space, but they all share the host's operating system kernel through namespaces and cgroups.

Building a Docker Image: The Dockerfile Explained

This is where Docker gets concrete.

A Dockerfile is a text file with instructions. Each instruction creates a layer. Here's a real example:

FROM python:3.11-slim
WORKDIR /app
COPY requirements.txt .
RUN pip install -r requirements.txt
COPY . .
CMD ["python", "app.py"]

Breaking this down:

When you build this image with docker build -t myapp ., Docker executes each instruction, creates each layer, and stacks them. The beauty: if you rebuild and only Layer 5 (your code) changed, Docker reuses Layers 1-4 from cache. No need to reinstall Python or packages.

Each layer is immutable. Once created, it never changes. This immutability makes Docker reliable and predictable.

How Containers Run: Namespaces and cgroups in Action

This is the technical heart of Docker, explained simply.

When Docker starts a container, it uses Linux kernel features to isolate it. Namespaces create separate views of resources. There are six types:

Then there are cgroups (control groups). These limit resources. You can tell Docker: "This container gets maximum 512MB RAM and 0.5 CPU cores." The kernel enforces these limits. One container can't starve others by hogging memory.

Together, namespaces and cgroups create isolation with minimal overhead. That's why Docker containers are so fast and efficient compared to virtual machines.

Container Networking: How Containers Talk to Each Other

By default, Docker creates a bridge network.

Imagine a private network switch inside your computer. Each container plugs into this switch and gets an internal IP address (like 172.17.0.2). Containers can ping each other by name. A web server container named "api" can reach a database container named "postgres" by calling "postgres:5432" without knowing its IP.

Docker also supports three other networking modes: host (container shares the host's network), overlay (for containers across multiple servers), and macvlan (containers get their own MAC addresses). For beginners, the default bridge network is enough.

Port publishing is how the outside world reaches containers. If your web server listens on port 80 inside the container, you can publish it to port 8080 on the host. External traffic goes to port 8080 → Docker routes it to port 80 inside the container. This isolation means you can run five different web servers, each on port 80 inside their containers, all published to different host ports (8080, 8081, 8082, etc.).

Running Your First Container: Commands That Work

You don't need to build an image to run a container.

Docker Hub hosts millions of pre-made images. Let's run a simple one:

docker run -d -p 8080:80 --name webserver nginx

This command:

Now visit http://localhost:8080 in your browser, and you'll see the Nginx welcome page. The web server is running inside a container. To stop it: docker stop webserver. To see running containers: docker ps. To see all containers (running and stopped): docker ps -a.

That's the basic workflow. Build or pull an image, run a container, map ports, and interact with it.

Docker Compose: Managing Multiple Containers

Real applications need multiple services. A typical app has a web server, a database, a cache, a message queue.

Running them individually with docker run commands gets messy fast. Docker Compose solves this with a YAML file. You define all services, networks, and volumes in one file, then start everything with one command: docker-compose up. All containers start in the correct order and connect to each other automatically. Check out our full guide on Docker Compose for Multi-Container Apps for details, but know that Compose is the standard tool for local development and small deployments.

Container Orchestration: What Kubernetes Does

Docker Compose works great on one machine. But what if you need to run 100 containers across 10 servers?

That's where orchestration comes in. Kubernetes (often called K8s) automatically manages containers across clusters. It handles scaling (spin up 10 more containers if traffic spikes), load balancing (distribute traffic evenly), and failure recovery (restart containers that crash). Learn more in our Kubernetes and Container Orchestration guide, but the key point: Docker containers are the building blocks, and orchestrators like Kubernetes manage them at scale.

Key Takeaways

  • Docker containers isolate applications using Linux namespaces and cgroups, achieving ~5-15MB footprint and ~50ms startup time per container versus virtual machines at 2GB and 3-5 minutes
  • Docker images are built in layers from a Dockerfile; each instruction creates an immutable layer that Docker caches, making rebuilds fast when only code changes
  • Containers share the host's OS kernel through namespace isolation (PID, network, mount, IPC, UTS, user) while cgroups limit CPU and memory per container, enabling 50+ containers on hardware that would run only 3-4 VMs
  • Docker Compose manages multiple containers locally with a single YAML file, while Kubernetes orchestrates containers at scale across server clusters
  • Port publishing and bridge networks allow containers to communicate with each other and the outside world without exposing their internal IP addresses

Frequently Asked Questions

What's the difference between a Docker image and a Docker container?

A Docker image is a read-only blueprint or template—like a recipe. A Docker container is a running instance of that image—like a cake made from the recipe. You build one image and create hundreds of containers from it. Images are immutable; containers are temporary and can be modified while running.

Why is Docker faster than virtual machines?

Docker containers share the host's operating system kernel, using only ~5-15MB RAM and starting in ~50ms. Virtual machines emulate an entire OS, consuming 2GB+ RAM and taking 3-5 minutes to boot. Containers achieve isolation through namespaces and cgroups, not full OS emulation, making them dramatically faster and more efficient.

What are Docker layers and why do they matter?

Each instruction in a Dockerfile creates an immutable layer. Docker caches layers, so rebuilding an image reuses unchanged layers instantly. If only your code changed, Docker rebuilds only that layer instead of re-running all previous steps, saving minutes of build time on large projects.

How do containers on the same host communicate with each other?

Docker creates a bridge network where each container gets an internal IP. Containers reach each other by service name (e.g., a web app container can call 'postgres:5432' to reach a database container). The Docker daemon handles name resolution automatically, so you never need to know IPs.

Can I run Docker on Windows or Mac?

Yes. Docker Desktop for Windows and Mac includes a lightweight Linux VM that runs the Docker Engine. On Windows 10/11, you can also use WSL 2 (Windows Subsystem for Linux 2) for native Linux integration. On Linux, Docker runs directly without a VM, making it slightly faster.

What's the difference between Docker and Kubernetes?

Docker containerizes single applications; Kubernetes orchestrates hundreds of containers across multiple servers. Docker is about packaging, Kubernetes is about managing at scale. Most teams use Docker containers inside Kubernetes clusters, so they complement each other.