Установка Docker в Linux

Введение

В Linux есть нативная поддержка Docker, поэтому установка довольно прямолинейна.

Про установку Docker в Windows читайте здесь

Ubuntu

sudo apt -y update sudo apt install -y ca-certificates curl gnupg lsb-release sudo mkdir -m 0755 -p /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 sudo apt install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin

С помощью скрипта

Скачаем и установим Docker с помощью скрипта

Изучить скрипт можно перейдя на get.docker.com

wget -qO- https://get.docker.com/ | sh

# Executing docker install script, commit: 26ff363bcf3b3f5a00498ac43694bf1c7d9ce16c + sudo -E sh -c apt-get update -qq >/dev/null + sudo -E sh -c DEBIAN_FRONTEND=noninteractive apt-get install -y -qq apt-transport-https ca-certificates curl >/dev/null + sudo -E sh -c curl -fsSL "https://download.docker.com/linux/ubuntu/gpg" | apt-key add -qq - >/dev/null Warning: apt-key output should not be parsed (stdout is not a terminal) + sudo -E sh -c echo "deb [arch=amd64] https://download.docker.com/linux/ubuntu focal stable" > /etc/apt/sources.list.d/docker.list + sudo -E sh -c apt-get update -qq >/dev/null + [ -n ] + sudo -E sh -c apt-get install -y -qq --no-install-recommends docker-ce >/dev/null + sudo -E sh -c docker version Client: Docker Engine - Community Version: 19.03.12 API version: 1.40 Go version: go1.13.10 Git commit: 48a66213fe Built: Mon Jun 22 15:45:44 2020 OS/Arch: linux/amd64 Experimental: false Server: Docker Engine - Community Engine: Version: 19.03.12 API version: 1.40 (minimum version 1.12) Go version: go1.13.10 Git commit: 48a66213fe Built: Mon Jun 22 15:44:15 2020 OS/Arch: linux/amd64 Experimental: false containerd: Version: 1.2.13 GitCommit: 7ad184331fa3e55e52b890ea95e65ba581ae3429 runc: Version: 1.0.0-rc10 GitCommit: dc9208a3303feef5b3839f4323d9beb36df0a9dd docker-init: Version: 0.18.0 GitCommit: fec3683 If you would like to use Docker as a non-root user, you should now consider adding your user to the "docker" group with something like: sudo usermod -aG docker andrei Remember that you will have to log out and back in for this to take effect! WARNING: Adding a user to the "docker" group will grant the ability to run containers which can be used to obtain root privileges on the docker host. Refer to https://docs.docker.com/engine/security/security/#docker-daemon-attack-surface for more information.

docker --version

Docker version 20.10.3, build 48d30b5

systemctl

Может потребоваться установка свежего containerd

sudo apt -y install containerd

Reading package lists... Done Building dependency tree Reading state information... Done The following additional packages will be installed: runc The following packages will be REMOVED: containerd.io docker-ce The following NEW packages will be installed: containerd runc 0 upgraded, 2 newly installed, 2 to remove and 0 not upgraded. Need to get 36.9 MB of archives. After this operation, 45.6 MB disk space will be freed. Get:1 http://fi.archive.ubuntu.com/ubuntu focal-updates/main amd64 runc amd64 1.1.0-0ubuntu1~20.04.1 [3,892 kB] Get:2 http://fi.archive.ubuntu.com/ubuntu focal-updates/main amd64 containerd amd64 1.5.9-0ubuntu1~20.04.4 [33.0 MB] Fetched 36.9 MB in 5s (7,316 kB/s) (Reading database ... 254483 files and directories currently installed.) Removing docker-ce (5:20.10.18~3-0~ubuntu-focal) ... Warning: Stopping docker.service, but it can still be activated by: docker.socket Removing containerd.io (1.6.8-1) ... Selecting previously unselected package runc. (Reading database ... 254461 files and directories currently installed.) Preparing to unpack .../runc_1.1.0-0ubuntu1~20.04.1_amd64.deb ... Unpacking runc (1.1.0-0ubuntu1~20.04.1) ... Selecting previously unselected package containerd. Preparing to unpack .../containerd_1.5.9-0ubuntu1~20.04.4_amd64.deb ... Unpacking containerd (1.5.9-0ubuntu1~20.04.4) ... Setting up runc (1.1.0-0ubuntu1~20.04.1) ... Setting up containerd (1.5.9-0ubuntu1~20.04.4) ... Processing triggers for man-db (2.9.1-1) ...

sudo apt install -y docker.io

sudo systemctl enable --now docker

Добавьте своего пользователя в группу docker. Замените YOUR_USERNAME на ваше имя пользователя.

sudo usermod -aG docker YOUR_USERNAME

Перелогинтесь

docker --version

Все способы установки Docker на Ubuntu перечислены на docs.docker.com/engine/install/ubuntu/

Изображение баннера

Настройка после установки

Управляйте Docker от имени пользователя без полномочий root

Демон Docker привязывается к сокету Unix вместо TCP-порта. По умолчанию этот сокет Unix принадлежит пользователю root, и другие пользователи могут получить к нему доступ только с помощью sudo .

Демон Docker всегда запускается от имени пользователя root.

Если вы не хотите постоянно писать sudo docker, создайте группу docker и добавьте в нее пользователей .

Когда демон Docker запускается, он создает сокет Unix, доступный членам группы docker.

Внимание:

Группа docker даёт права, равные правам пользователя root. Как это влияет на безопасность системы, читайте в разделе документации Docker Daemon Attack Surface.

Примечание:

Как запускать Docker без прав root, читайте в разделе документации Docker Rootless mode.

Создайте группу docker.

sudo groupadd docker

Добавьте текущего пользователя в группу docker.

sudo usermod -aG docker $USER

Выйдите из системы и войдите снова, чтобы ваше членство в группе было пересмотрено.

При тестировании на виртуальной машине может потребоваться перезагрузить виртуальную машину, чтобы изменения вступили в силу.

На десктопной версии Линукс , например X Windows , полностью выйдите из сеанса, а затем войдите снова.

В Linux вы также можете запустить следующую команду, чтобы активировать изменения в группах:

newgrp docker

Убедитесь, что вы можете запускать команды docker без sudo.

docker run hello-world

Эта команда загружает тестовый образ и запускает его в контейнере. Когда контейнер запускается, он печатает сообщение и завершает работу.

Если вы изначально запускали команды Docker CLI с помощью sudo перед добавлением пользователя в группу docker, вы можете увидеть следующую ошибку, которая указывает на то, что ваш каталог ~/.docker/ был создан с неправильными разрешениями из-за команд sudo.

WARNING: Error loading config file: /home/user/.docker/config.json - stat /home/user/.docker/config.json: permission denied

Чтобы это исправить, удалите каталог ~/.docker/ (он создастся заново автоматически, но ваши настройки пропадут) или смените его владельца и права следующими командами:

sudo chown "$USER":"$USER" /home/"$USER"/.docker -R

sudo chmod g+rwx "$HOME/.docker" -R

Автозапуск Docker при загрузке системы

Большинство современных дистрибутивов Linux ( RHEL, CentOS, Fedora, Debian , Ubuntu 16.04 и новее) управляют запуском служб при загрузке через systemd. В Debian и Ubuntu служба Docker по умолчанию запускается при загрузке. Чтобы Docker и containerd запускались автоматически в других дистрибутивах, выполните команды:

sudo systemctl enable docker.service

sudo systemctl enable containerd.service

Чтобы отключить автозапуск, используйте disable вместо enable.

sudo systemctl disable docker.service

sudo systemctl disable containerd.service

Если нужно добавить HTTP-прокси, перенести файлы Docker в другой каталог или раздел или изменить другие настройки, читайте раздел документации Docker о настройке параметров демона через systemd.

Другой драйвер хранилища

О разных драйверах хранилища читайте в разделе документации Docker Storage drivers. Драйвер по умолчанию и список поддерживаемых драйверов зависят от дистрибутива Linux на хосте и доступных драйверов ядра.

Драйвер логирования по умолчанию

Docker собирает и показывает логи всех контейнеров хоста через драйверы логирования. Драйвер по умолчанию, json-file, пишет логи в файлы формата JSON в файловой системе хоста. Со временем эти файлы растут и могут занять всё место на диске.

Чтобы этого избежать, включите ротацию логов в драйвере json-file, или возьмите другой драйвер, например local, который ротирует логи по умолчанию, или драйвер, который отправляет логи на удалённый сервер сбора логов.

Где демон Docker принимает подключения

По умолчанию демон Docker принимает запросы локальных клиентов через сокет UNIX. Docker может принимать запросы и с удалённых хостов: для этого демон должен слушать IP-адрес и порт в дополнение к сокету UNIX. Подробнее об этой настройке читайте в разделе «Bind Docker to another host/port or a unix socket» справочника Docker CLI.

Защитите подключение

Прежде чем разрешать Docker принимать подключения с удалённых хостов, разберитесь, чем грозит открытие Docker в сеть. Если подключение не защищено, удалённые пользователи без прав root могут получить права root на хосте. Как защитить это подключение сертификатами TLS, читайте в статье документации Docker о защите сокета демона.

Удалённые подключения настраиваются в юнит-файле docker.service для дистрибутивов с systemd, например свежих версий RedHat, CentOS, Ubuntu и SLES, или в файле daemon.json, который рекомендуется для дистрибутивов без systemd.

systemd или daemon.json

Если настроить подключения и в юнит-файле systemd, и в daemon.json, возникнет конфликт, и Docker не запустится.

Удалённый доступ через юнит-файл systemd

Откройте файл переопределения для docker.service в текстовом редакторе командой sudo systemctl edit docker.service.

Добавьте или измените следующие строки, подставив свои значения.

[Service] ExecStart= ExecStart=/usr/bin/dockerd -H fd:// -H tcp://127.0.0.1:2375

Сохраните файл.

Перечитайте конфигурацию systemd.

sudo systemctl daemon-reload

Перезапустите Docker.

sudo systemctl restart docker.service

Проверьте, что изменение применилось: в выводе netstat dockerd должен слушать заданный порт.

sudo netstat -lntp | grep dockerd

Удалённый доступ через daemon.json

Задайте массив hosts в файле /etc/docker/daemon.json, чтобы демон слушал и сокет UNIX, и IP-адрес:

{ "hosts": ["unix:///var/run/docker.sock", "tcp://127.0.0.1:2375"] }

Перезапустите Docker.

Проверьте, что изменение применилось: в выводе netstat dockerd должен слушать заданный порт.

sudo netstat -lntp | grep dockerd

IPv6 в демоне Docker

Как включить IPv6 в демоне Docker, читайте в разделе документации Docker Enable IPv6 support.

Решение проблем

Совместимость ядра

Docker не работает правильно, если ядро старше версии 3.10 или в нём нет нужных модулей. Чтобы проверить совместимость ядра, скачайте и запустите скрипт check-config.sh.

curl https://raw.githubusercontent.com/docker/docker/master/contrib/check-config.sh > check-config.sh

bash ./check-config.sh

Скрипт работает только в Linux, в macOS он не работает.

Cannot connect to the Docker daemon

Если вы видите такую ошибку, возможно, клиент Docker настроен на подключение к демону Docker на другом хосте, и этот хост недоступен.

Cannot connect to the Docker daemon. Is 'docker daemon' running on this host?

Чтобы узнать, к какому хосту подключается клиент, проверьте значение переменной окружения DOCKER_HOST.

env | grep DOCKER_HOST

Если команда вернула значение, клиент Docker подключается к демону на этом хосте. Если переменная не задана, клиент подключается к демону на локальном хосте. Если она задана по ошибке, сбросьте её командой:

unset DOCKER_HOST

Чтобы переменная DOCKER_HOST больше не задавалась по ошибке, возможно, придётся поправить файлы окружения, например ~/.bashrc или ~/.profile .

Если DOCKER_HOST задана правильно, проверьте, что демон Docker запущен на удалённом хосте и что подключению не мешает файрвол или сбой сети.

Проблемы с пересылкой IP-пакетов

Если вы настраиваете сеть вручную через systemd-network с systemd версии 219 или новее, контейнеры Docker могут потерять доступ к сети. Начиная с systemd версии 220, пересылка пакетов для отдельной сети (net.ipv4.conf.<interface>.forwarding) по умолчанию выключена. Эта настройка запрещает пересылку IP-пакетов и конфликтует с тем, что Docker включает net.ipv4.conf.all.forwarding внутри контейнеров.

Чтобы обойти это в RHEL, CentOS или Fedora, откройте файл <interface>.network в каталоге /usr/lib/systemd/network/ на хосте Docker (например, /usr/lib/systemd/network/80-container-host0.network) и добавьте в секцию [Network] следующий блок.

[Network] ... IPForward=kernel # OR IPForward=true

Эта настройка разрешает пересылку IP-пакетов из контейнера.

Контейнеры не могут использовать DNS-резолвер из resolv.conf

В Linux с графическим интерфейсом часто работает сетевой менеджер, который кэширует DNS-запросы через dnsmasq на loopback-адресе, например 127.0.0.1 или 127.0.1.1, и прописывает этот адрес в /etc/resolv.conf. Служба dnsmasq ускоряет DNS-запросы и заодно работает как DHCP-сервер. В контейнере Docker такая настройка не работает: у контейнера своё сетевое пространство имён, loopback-адрес вроде 127.0.0.1 указывает на сам контейнер, а DNS-сервера на нём почти наверняка нет.

Если Docker видит, что ни один DNS-сервер из /etc/resolv.conf не работает полноценно, он выводит следующее предупреждение и использует публичные DNS-серверы Google 8.8.8.8 и 8.8.4.4.

WARNING: Local (127.0.0.1) DNS resolver found in resolv.conf and containers can't use it. Using default external servers : [8.8.8.8 8.8.4.4]

Если вы видите это предупреждение, сначала проверьте, работает ли dnsmasq:

ps aux |grep dnsmasq

Если контейнеру нужно разрешать имена хостов внутренней сети, публичных DNS-серверов недостаточно. Есть два варианта:

указать DNS-сервер, который будет использовать Docker, или

отключить dnsmasq в NetworkManager. Тогда NetworkManager пропишет в /etc/resolv.conf настоящий DNS-сервер, но вы потеряете преимущества dnsmasq.

Достаточно одного из этих способов.

DNS-серверы для Docker

По умолчанию файл конфигурации демона лежит в /etc/docker/daemon.json. Другое расположение задаёт флаг демона --config-file. Ниже считается, что файл лежит в /etc/docker/daemon.json.

Создайте или откройте файл конфигурации демона Docker /etc/docker/daemon.json.

sudo vi /etc/docker/daemon.json

Добавьте ключ dns с одним или несколькими IP-адресами. Если в файле уже есть настройки, достаточно добавить или изменить строку dns.

{ "dns": ["8.8.8.8", "8.8.4.4"] }

Если ваш внутренний DNS-сервер не разрешает публичные адреса, добавьте хотя бы один сервер, который их разрешает: иначе не получится подключиться к Docker Hub, а контейнеры не смогут разрешать интернет-домены.

Сохраните и закройте файл.

Перезапустите демон Docker.

sudo service docker restart

Проверьте, что Docker разрешает внешние адреса: скачайте образ.

docker pull hello-world

При необходимости проверьте, что контейнеры разрешают внутреннее имя хоста: пропингуйте его.

docker run --rm -it alpine ping -c4 <my_internal_host>

Изображение баннера

Отключение dnsmasq

Ubuntu:

Если вы не хотите прописывать конкретный IP-адрес в настройках демона Docker, отключите dnsmasq в NetworkManager.

Откройте файл /etc/NetworkManager/NetworkManager.conf .

Закомментируйте строку dns=dnsmasq: добавьте символ # в её начало.

# dns=dnsmasq

Сохраните и закройте файл.

Перезапустите NetworkManager и Docker. Можно вместо этого перезагрузить систему.

sudo systemctl restart network-manager

sudo systemctl restart docker

RHEL, CentOS или Fedora:

Чтобы отключить dnsmasq в RHEL, CentOS или Fedora,

остановите и отключите службу dnsmasq:

sudo systemctl stop dnsmasq

sudo systemctl disable dnsmasq

Затем настройте DNS-серверы вручную по документации Red Hat.

Доступ к удалённому API через файрвол

Если на хосте с Docker работает файрвол, удалённый доступ включён и вы хотите обращаться к удалённому API Docker с другого хоста, разрешите в файрволе входящие подключения на порт Docker: по умолчанию это 2376 при шифровании TLS и 2375 без него.

Два распространённых файрвола: UFW (Uncomplicated Firewall), его часто используют в Ubuntu, и firewalld , его часто используют в системах на основе RPM. Сверьтесь с документацией своей ОС и файрвола, а сведения ниже помогут начать. Эти настройки довольно свободные, возможно, вам нужна более строгая конфигурация.

UFW: задайте DEFAULT_FORWARD_POLICY="ACCEPT" в конфигурации.

firewalld: добавьте в политику правила вроде следующих, одно для входящих запросов и одно для исходящих. Проверьте имена интерфейсов и цепочек.

<direct> [ <rule ipv="ipv6" table="filter" chain="FORWARD_direct" priority="0"> -i zt0 -j ACCEPT </rule> ] [ <rule ipv="ipv6" table="filter" chain="FORWARD_direct" priority="0"> -o zt0 -j ACCEPT </rule> ] </direct>

Ядро не поддерживает ограничение swap через cgroup

На хостах Ubuntu или Debian при работе с образом могут появляться сообщения вроде следующего.

WARNING: Your kernel does not support swap limit capabilities. Limitation discarded.

В системах на основе RPM этого предупреждения нет: там эти возможности включены по умолчанию.

Если они вам не нужны, предупреждение можно игнорировать. Включить их в Ubuntu или Debian можно по инструкции ниже. Учёт памяти и swap занимает около 1% всей доступной памяти и снижает общую производительность на 10%, даже когда Docker не запущен.

Войдите на хост Ubuntu или Debian под пользователем с правами sudo.

Откройте файл /etc/default/grub . Добавьте или измените строку GRUB_CMDLINE_LINUX, чтобы в ней были две пары ключ-значение:

GRUB_CMDLINE_LINUX="cgroup_enable=memory swapaccount=1"

Сохраните и закройте файл.

Обновите GRUB.

sudo update-grub

Если в файле конфигурации GRUB есть синтаксическая ошибка, update-grub завершится с ошибкой. Тогда снова откройте /etc/default/grub, исправьте строку и повторите update-grub.

Изменения вступят в силу после перезагрузки системы.

Удаление старых версий

sudo apt-get remove docker docker-engine docker.io containerd runc

Установка Docker в CentOS

Инструкция

Скрипт для установки

Скрипт для установки docker и настройки работы с хостом по ssh

#!/bin/bash sudo apt-get update -y sudo apt-get upgrade -y sudo apt-get install -y ssh openssh-server sudo ufw enable sudo ufw allow 22 sudo ufw allow 29092 sudo apt-get install -y ca-certificates bzip2 tar curl git kafkacat vim sudo install -m 0755 -d /etc/apt/keyrings sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc sudo chmod a+r /etc/apt/keyrings/docker.asc echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/ubuntu $(. /etc/os-release && echo "$VERSION_CODENAME") stable" | sudo tee /etc/apt/sources.list.d/docker.list > /dev/null sudo apt-get update sudo apt-get install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin sudo groupadd docker sudo usermod -aG docker $USER newgrp docker

Автор статьи: Андрей Олегович

Изображение баннера