Ответ
Изоляция контейнеров Docker обеспечивается не виртуализацией, а функциями ядра Linux: namespaces и cgroups. Это делает контейнеры легковесными и быстрыми по сравнению с виртуальными машинами.
1. Namespaces (пространства имён) – изоляция представления: Каждый контейнер получает собственный изолированный экземпляр глобальных ресурсов. Основные типы:
- PID namespace: Изолирует дерево процессов. Процессы в контейнере начинаются с PID 1.
- Network namespace: Изолирует сетевой стек (интерфейсы, таблицы маршрутизации, iptables).
- Mount namespace: Изолирует точки монтирования файловой системы.
- UTS namespace: Изолирует hostname и domainname.
- IPC namespace: Изолирует межпроцессное взаимодействие (очереди сообщений, shared memory).
- User namespace: Изолирует mapping UID/GID (позволяет процессу иметь root внутри контейнера без привилегий снаружи).
2. Cgroups (control groups) – ограничение ресурсов: Ограничивают и учитывают использование ресурсов группой процессов.
- CPU: Ограничение доли CPU (
cpu.shares) или абсолютной мощности (cfs_quota_us). - Память: Жёсткий лимит памяти (
memory.limit_in_bytes), за превышение которого контейнер будет завершён (OOM Killer). - I/O: Ограничение на чтение/запись диска.
Примеры команд Docker:
# Запуск с ограничением ресурсов
docker run -it --cpus="0.5" --memory="100m" alpine:latest
# Запуск с изолированной сетью (по умолчанию используется bridge network namespace)
docker run -d --name my-app --network my-custom-network nginx
Важно для DevOps: Изоляция на уровне ядра не является полной, как в VM. Для workloads с высокими требованиями безопасности используются дополнительные меры: запуск контейнеров с флагом --user (не от root), использование security profiles (AppArmor, SELinux), или runtime с усиленной изоляцией (gVisor, Kata Containers).