Skip to main content
COSMICBYTEZLABS
NewsSecurityHOWTOsToolsStudyTraining
ProjectsChecklistsAI RankingsNewsletterStatusTagsAbout
Subscribe

Press Enter to search or Esc to close

News
Security
HOWTOs
Tools
Study
Training
Projects
Checklists
AI Rankings
Newsletter
Status
Tags
About
RSS Feed
Reading List
Subscribe

Stay in the Loop

Get the latest security alerts, tutorials, and tech insights delivered to your inbox.

Subscribe NowFree forever. No spam.
COSMICBYTEZLABS

Your trusted source for IT intelligence, cybersecurity insights, and hands-on technical guides.

429+ Articles
114+ Guides

CONTENT

  • Latest News
  • Security Alerts
  • HOWTOs
  • Projects
  • Exam Prep

RESOURCES

  • Search
  • Browse Tags
  • Newsletter Archive
  • Reading List
  • RSS Feed

COMPANY

  • About Us
  • Contact
  • Privacy Policy
  • Terms of Service

© 2026 CosmicBytez Labs. All rights reserved.

System Status: Operational
  1. Home
  2. HOWTOs
  3. Docker Security Fundamentals: Protecting Your Containers
Docker Security Fundamentals: Protecting Your Containers
HOWTOIntermediate

Docker Security Fundamentals: Protecting Your Containers

Learn essential Docker security practices including image scanning, runtime protection, network isolation, and secrets management for production environments.

Security Team

Security Engineering

January 25, 2026
6 min read

Prerequisites

  • Basic Docker knowledge
  • Linux fundamentals
  • Understanding of networking

Overview

This guide covers essential security practices for Docker environments in production. Containers share the host kernel, making security boundaries different from traditional VMs and requiring specific hardening measures.

Who Should Use This Guide

  • DevOps engineers deploying containerized applications
  • Security teams auditing container infrastructure
  • System administrators managing Docker hosts

What You Will Learn

  • Securing container images from build to deployment
  • Runtime protection and isolation techniques
  • Network segmentation for containers
  • Secrets management best practices

Requirements

System Requirements

ComponentRequirement
Docker Engine20.10 or later
Operating SystemLinux (Ubuntu 22.04+, RHEL 8+) or Windows Server 2022
PrivilegesRoot/sudo access on Docker host

Prerequisites

  • Docker installed and running
  • Basic understanding of Dockerfile syntax
  • Familiarity with docker-compose

Tools Referenced

ToolPurposeInstallation
TrivyImage vulnerability scanningapt install trivy or container
Docker ScoutBuilt-in vulnerability scanningIncluded with Docker Desktop
GrypeAlternative image scannercurl -sSfL https://raw.githubusercontent.com/anchore/grype/main/install.sh | sh

Process

Step 1: Secure Base Images

Use official, verified base images and pin specific versions.

Configuration:

# Recommended: Official image with specific version
FROM python:3.12-slim-bookworm
 
# Avoid: Unverified sources or latest tags
# FROM random-user/python:latest

Verification:

# Check image source and history
docker inspect <your-image> | grep -A 5 "RepoTags"
docker history <your-image>

Expected Output: Image should trace back to official Docker Hub repositories.


Step 2: Scan Images for Vulnerabilities

Integrate scanning into your CI/CD pipeline before deployment.

Using Trivy:

trivy image <your-image>:<tag>

Using Docker Scout:

docker scout cves <your-image>:<tag>

Using Grype:

grype <your-image>:<tag>

Expected Output: Vulnerability report with severity levels (CRITICAL, HIGH, MEDIUM, LOW).

Acceptance Criteria: No CRITICAL or HIGH vulnerabilities in production images.


Step 3: Implement Multi-Stage Builds

Reduce attack surface by excluding build tools from production images.

Configuration:

# Build stage
FROM golang:1.22 AS builder
WORKDIR /app
COPY . .
RUN CGO_ENABLED=0 go build -o main .
 
# Production stage - minimal image
FROM gcr.io/distroless/static-debian12
COPY --from=builder /app/main /
USER nonroot
ENTRYPOINT ["/main"]

Verification:

# Compare image sizes
docker images | grep <your-image>

Expected Result: Production image significantly smaller than build image.


Step 4: Run Containers as Non-Root

Never run containers as root user.

Dockerfile Configuration:

# Create non-root user
RUN groupadd -r appgroup && useradd -r -g appgroup appuser
 
# Set ownership
COPY --chown=appuser:appgroup . /app
 
# Switch to non-root user
USER appuser

Verification:

# Check running user inside container
docker exec <container-id> whoami

Expected Output: appuser (or your defined non-root user)


Step 5: Drop Unnecessary Capabilities

Remove Linux capabilities that containers don't need.

docker-compose.yml Configuration:

services:
  app:
    image: <your-image>
    cap_drop:
      - ALL
    cap_add:
      - NET_BIND_SERVICE  # Only if binding to ports below 1024

Verification:

# Check container capabilities
docker inspect <container-id> | grep -A 20 "CapDrop"

Step 6: Enable Read-Only File System

Prevent runtime modifications to container filesystem.

docker-compose.yml Configuration:

services:
  app:
    image: <your-image>
    read_only: true
    tmpfs:
      - /tmp
      - /var/run

Verification:

# Attempt to write to filesystem (should fail)
docker exec <container-id> touch /testfile

Expected Output: touch: cannot touch '/testfile': Read-only file system


Step 7: Set Resource Limits

Prevent resource exhaustion attacks.

docker-compose.yml Configuration:

services:
  app:
    image: <your-image>
    deploy:
      resources:
        limits:
          cpus: '0.5'
          memory: 512M
        reservations:
          cpus: '0.25'
          memory: 256M

Verification:

docker stats <container-id>

Step 8: Implement Network Segmentation

Isolate containers using custom networks.

docker-compose.yml Configuration:

services:
  frontend:
    networks:
      - frontend-net
 
  backend:
    networks:
      - frontend-net
      - backend-net
 
  database:
    networks:
      - backend-net  # Not accessible from frontend
 
networks:
  frontend-net:
  backend-net:
    internal: true  # No external access

Verification:

# List networks
docker network ls
 
# Inspect network connectivity
docker network inspect <network-name>

Step 9: Secure Secrets Management

Never hardcode secrets in images or compose files.

Incorrect (Never Do This):

# BAD - Never hardcode secrets
ENV DATABASE_PASSWORD=<password>

Correct - Using Docker Secrets (Swarm Mode):

services:
  app:
    secrets:
      - db_password
 
secrets:
  db_password:
    external: true

Correct - Using Environment Files:

# Create .env file (never commit to git)
echo "DB_PASSWORD=<your-secure-password>" > .env
chmod 600 .env
services:
  app:
    env_file:
      - .env

Step 10: Configure Docker Daemon Security

Harden the Docker daemon configuration.

Create /etc/docker/daemon.json:

{
  "icc": false,
  "userns-remap": "default",
  "no-new-privileges": true,
  "live-restore": true,
  "userland-proxy": false,
  "log-driver": "json-file",
  "log-opts": {
    "max-size": "10m",
    "max-file": "3"
  }
}

Apply Configuration:

sudo systemctl restart docker

Verification:

docker info | grep -E "Security|Logging"

Troubleshooting

SymptomPossible CauseSolution
Container won't start with read_only: trueApplication writes to filesystemAdd tmpfs mounts for required write paths
Permission denied errorsNon-root user lacks file permissionsEnsure COPY --chown sets correct ownership
Container exits immediatelyEntrypoint requires rootModify application to run as non-root
Network connectivity issuesICC disabled or wrong networkVerify containers are on correct networks
Secrets not availableSecret not created or wrong pathCheck docker secret ls and mount paths

Verification Checklist

Before deploying to production, verify:

  • Using official/verified base images with pinned versions
  • Images scanned for vulnerabilities (no CRITICAL/HIGH)
  • Running as non-root user
  • Unnecessary capabilities dropped
  • Resource limits configured
  • Networks properly segmented
  • Secrets not hardcoded in images or compose files
  • Read-only filesystem where possible
  • Content trust enabled
  • Logging configured

Security Scanning Pipeline Example

Integrate security scanning into CI/CD:

# .github/workflows/security.yml
name: Container Security
 
on: [push, pull_request]
 
jobs:
  scan:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
 
      - name: Build image
        run: docker build -t app:${{ github.sha }} .
 
      - name: Run Trivy scan
        uses: aquasecurity/trivy-action@master
        with:
          image-ref: 'app:${{ github.sha }}'
          format: 'sarif'
          output: 'trivy-results.sarif'
          severity: 'CRITICAL,HIGH'
 
      - name: Upload results
        uses: github/codeql-action/upload-sarif@v3
        with:
          sarif_file: 'trivy-results.sarif'

References

  • Docker Security Best Practices
  • CIS Docker Benchmark
  • NIST Container Security Guide

Last Updated: January 2026

#Docker#Containers#Security#DevSecOps#Kubernetes

Related Articles

How to Deploy Falco for Kubernetes Runtime Security Monitoring

Step-by-step guide to deploying Falco as a Kubernetes runtime security engine. Covers Helm installation, custom rule authoring, Falcosidekick alerting...

12 min read

Docker Windows Containers: Native Engine Setup Guide

Deploy Docker Engine natively on Windows without Docker Desktop. Covers installation, Windows container mode, lifecycle management, and troubleshooting.

6 min read

Kubernetes Secrets Management with External Secrets Operator

Securely manage Kubernetes secrets using External Secrets Operator. Covers ESO installation, SecretStore configuration, syncing from Azure Key Vault and...

11 min read
Back to all HOWTOs