Docker под Windows — не то же самое, что Docker на Linux. Под капотом WSL2, виртуализация и неочевидные ограничения. Разбираем установку, настройку и грабли, которые ждут на каждом шаге.
WSL2 установлен и обновлён. Если ещё нет:
powershell# Открой PowerShell от администратора
wsl --installЭта команда установит WSL2 и Ubuntu (операционная система Linux) как дефолтный дистрибутив. После установки — перезагрузка.
Если WSL уже был, но первой версии:
powershell# Обновить WSL до версии 2
wsl --update
# Установить WSL2 как версию по умолчанию
wsl --set-default-version 2Скачать Docker Desktop для Windows можно с официального сайта docker.com — раздел Products → Docker Desktop. Актуальную версию проверяй там же, они обновляются регулярно.
Установщик стандартный — .exe, запустил, прокликал. Из важного на этапе установки:
После установки Docker Desktop попросит перезагрузку. После перезагрузки — первый запуск. В трее появится иконка кита.
И вот тут начинается интересное.
Самая частая причина — WSL2 не обновлён. Docker покажет что-то вроде:
Docker Desktop - WSL kernel version too lowРешение:
powershellwsl --updateЕсли не помогает — проверь, что WSL2 вообще работает:
powershellwsl --list --verboseДолжен быть хотя бы один дистрибутив с VERSION 2. Если стоит VERSION 1:
powershellwsl --set-version Ubuntu 2Типичная картина: Docker Desktop вроде запущен, а docker ps в терминале выдаёт:
error during connect: This error may indicate that the docker daemon is not runningПричины:
Если проблема повторяется — попробуй перезапустить Docker Desktop: правый клик на иконке в трее → Restart.
Docker Desktop покажет ошибку про Hardware assisted virtualization. Путь один — в BIOS, включить VT-x/AMD-V. На ноутбуках это бывает отключено по умолчанию.
После установки Docker Desktop команды docker и docker compose (инструмент для описания многоконтейнерных приложений) доступны в PowerShell, CMD и терминале WSL2.
powershell# Проверить, что Docker работает
docker version
# Запустить тестовый контейнер
docker run hello-world
# Посмотреть запущенные контейнеры
docker psВсё стандартно. Команды те же, что и на Linux — разницы в синтаксисе нет.
Но есть нюанс с путями. В PowerShell и CMD пути Windows-стиля:
powershelldocker run -v C:\Users\user\project:/app alpine ls /appВ терминале WSL2:
bashdocker run -v /mnt/c/Users/user/project:/app alpine ls /appОба варианта работают, но производительность отличается радикально. Об этом — следующий раздел.
Вот где Docker на Windows проигрывает Linux-установке по-настоящему. И причина — файловая система.
Когда контейнер работает с файлами, которые лежат на NTFS-разделе Windows (например, C:\Users\...), каждая операция ввода-вывода проходит через прослойку 9P-протокола между WSL2 и Windows. На больших проектах (Node.js с тысячами файлов в node_modules, или PHP-фреймворк с автоподгрузкой классов) это ощущается сильно. Сборка, которая на Linux занимает 20 секунд, на Windows через примонтированный том может занять минуту-две.
Решение — хранить проект внутри файловой системы WSL2:
bash# В терминале WSL2
cd ~
mkdir projects
cd projects
git clone https://github.com/your/repo.gitФайлы будут лежать в ext4 (файловая система Linux) внутри WSL2. Docker будет работать с ними без прослойки — скорость как на нативном Linux.
Доступ к этим файлам из Windows:
\\wsl$\Ubuntu\home\user\projectsВ проводнике Windows слева появится раздел «Linux» — можно открывать файлы в VS Code (редактор кода) или любом другом редакторе.
На практике разница может быть в 5–10 раз. Это не преувеличение. На одном из тестов (по обсуждениям на GitHub) сборка фронтенд-проекта с webpack занимала 90 секунд через примонтированный NTFS-том и 12 секунд с файлами внутри WSL2. Просто перенос файлов — и всё.
Volumes (именованные тома Docker) — рекомендуемый способ хранения данных контейнеров. На Windows они работают, но с нюансами.
powershell# Создать volume
docker volume create mydata
# Использовать в контейнере
docker run -v mydata:/data postgres:16Физически volumes живут внутри WSL2, в файловой системе docker-desktop-data. Найти их на диске Windows:
\\wsl$\docker-desktop-data\data\docker\volumes\Bind mounts (проброс папки с хоста) — тут и проявляется проблема производительности. Если пробрасываешь папку с NTFS:
powershelldocker run -v C:\myproject:/app node:20 npm installБудет медленно. Если с WSL2:
bashdocker run -v ~/myproject:/app node:20 npm installБудет быстро. Разница именно в том, где физически лежат файлы.
Docker Compose (инструмент для оркестрации контейнеров через YAML-файл) на Windows работает из коробки — он входит в Docker Desktop.
yaml# docker-compose.yml
services:
web:
image: nginx:alpine
ports:
- "8080:80"
volumes:
- ./html:/usr/share/nginx/html
db:
image: postgres:16
environment:
POSTGRES_PASSWORD: YOUR_PASSWORD_HERE
volumes:
- pgdata:/var/lib/postgresql/data
volumes:
pgdata:powershelldocker compose up -dРаботает. Но если docker-compose.yml лежит на NTFS, а volumes указывают на локальные папки — снова упираемся в производительность.
Совет: держи docker-compose.yml и данные проекта внутри WSL2. Запускай docker compose up из терминала WSL2, не из PowerShell. Результат — тот же Docker, но без тормозов файловой системы.
До этого момента речь шла о Linux-контейнерах на Windows. Но Docker на Windows умеет запускать и Windows-контейнеры — контейнеры на базе Windows Server Core или Nano Server.
Docker Desktop позволяет переключаться между режимами: правый клик на иконке в трее → Switch to Windows containers.
Зачем это нужно:
На практике Windows-контейнеры в домашнем окружении — экзотика. Образы тяжёлые (Windows Server Core — несколько гигабайт), запуск медленнее, экосистема скуднее. Но если ты разрабатываешь под Windows Server — пригодится.
powershell# После переключения в режим Windows containers
docker pull mcr.microsoft.com/windows/servercore:ltsc2022
docker run -it mcr.microsoft.com/windows/servercore:ltsc2022 cmdВажно: Windows-контейнеры требуют совместимости версий ядра. Контейнер на базе LTSC2022 не запустится на Windows 10 — нужен Windows 11 или Windows Server 2022. Или режим Hyper-V isolation, который решает проблему совместимости ценой дополнительной прослойки виртуализации.
Жалоба номер один на Docker Desktop для Windows — он жрёт память. И это не баг, а архитектурная особенность.
WSL2 по умолчанию забирает до 50% оперативной памяти (но не более 8 ГБ на старых сборках). Linux-ядро внутри WSL2 кеширует файлы в RAM — как и любой нормальный Linux. Проблема в том, что Windows видит эту память как занятую и не может её забрать обратно.
Ограничить аппетит WSL2:
ini# Файл: C:\Users\<username>\.wslconfig
[wsl2]
memory=4GB
processors=2
swap=2GBПосле сохранения:
powershellwsl --shutdownWSL2 перезапустится с новыми лимитами. Для машины с 16 ГБ RAM ограничение в 4 ГБ для Docker — разумный компромисс.
Тут нюанс: если у тебя запущено десять контейнеров и каждый хочет по гигабайту, 4 ГБ не хватит. Подбирай лимит под свою нагрузку. Но оставь Windows хотя бы 8 ГБ — иначе система начнёт свопить и всё станет тормозить.
Docker Desktop — удобно, но есть два момента. Во-первых, для коммерческого использования в компаниях с более чем 250 сотрудников нужна платная подписка (условия уточняй на сайте Docker, они менялись). Во-вторых, кто-то просто не хочет GUI-обёртку.
Альтернатива — установить Docker Engine (движок Docker) прямо внутри WSL2:
bash# В терминале WSL2 (Ubuntu)
sudo apt update
sudo apt install -y ca-certificates curl gnupg
# Добавить GPG-ключ Docker
sudo install -m 0755 -d /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
# Добавить репозиторий
echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable" | sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
# Установить Docker
sudo apt update
sudo apt install -y docker-ce docker-ce-cli containerd.io docker-compose-pluginЗапуск Docker daemon в WSL2:
bashsudo service docker start
# Проверка
docker run hello-worldРаботает. Без Docker Desktop, без GUI, без подписки. Docker daemon запускается внутри WSL2, команды доступны из терминала WSL2.
Минус: daemon не стартует автоматически при запуске Windows. Нужно либо запускать вручную, либо настроить автозапуск через systemd (в свежих версиях WSL2 systemd поддерживается — нужно включить в /etc/wsl.conf):
ini# /etc/wsl.conf
[boot]
systemd=trueПосле wsl --shutdown и повторного входа Docker будет стартовать автоматически.
Обновления Windows иногда ломают WSL2 или компоненты виртуализации. Первое, что стоит попробовать:
powershellwsl --update
wsl --shutdownПотом перезапустить Docker Desktop. Если не помогло — переустановка WSL2:
powershellwsl --unregister docker-desktop
wsl --unregister docker-desktop-dataИ перезапуск Docker Desktop — он пересоздаст свои дистрибутивы. Контейнеры и volumes при этом потеряются, так что бэкап заранее.
В WSL2 сеть — NAT (трансляция сетевых адресов) поверх виртуального адаптера. Контейнеры получают IP из внутренней подсети. Обращение к localhost из Windows попадает в контейнер (Docker Desktop пробрасывает порты автоматически), но обращение из контейнера к сервисам на Windows — сложнее.
Специальный DNS-адрес для доступа к хосту из контейнера:
host.docker.internalНапример, если на Windows крутится PostgreSQL на порту 5432:
bash# Из контейнера
psql -h host.docker.internal -U postgresWSL2-дистрибутив Docker хранит все образы и контейнеры в виртуальном диске (файл .vhdx). По умолчанию он лежит в профиле пользователя и растёт динамически. Но не сжимается сам.
Проверить размер:
powershellwsl --list --verbose
# Путь к .vhdx: %LOCALAPPDATA%\Docker\wsl\data\ext4.vhdxПочистить неиспользуемые образы и контейнеры:
powershelldocker system prune -a --volumesСжать виртуальный диск:
powershellwsl --shutdown
# Открой diskpart
diskpart
select vdisk file="C:\Users\<username>\AppData\Local\Docker\wsl\data\ext4.vhdx"
compact vdisk
exitDocker на Windows Server — это не Docker Desktop. Тут нет WSL2, нет GUI-приложения. Docker Engine устанавливается как Windows-сервис и работает с Windows-контейнерами нативно.
powershell# Установка на Windows Server 2019/2022
Install-Module -Name DockerMsftProvider -Repository PSGallery -Force
Install-Package -Name docker -ProviderName DockerMsftProvider -Force
Restart-ComputerПосле перезагрузки:
powershelldocker version
docker run mcr.microsoft.com/windows/servercore:ltsc2022 hostnameLinux-контейнеры на Windows Server тоже можно запустить — через LCOW (Linux Containers on Windows) или WSL2 (на Server 2022 и новее). Но это не самый стабильный сценарий. Если нужны Linux-контейнеры на сервере — проще поставить Linux.
Честный ответ: если Docker — твой основной рабочий инструмент и ты проводишь в нём часы каждый день, Windows — не лучшая хост-система для этого. Производительность файловой системы, потребление RAM, периодические поломки после обновлений — всё это трение, которого на Linux нет.
Но если Windows — основная система по другим причинам (игры, специфический софт, привычка), Docker Desktop + WSL2 работает вполне сносно. Особенно если следовать двум правилам:
.wslconfigИ всё будет работать. Не идеально — но работать.