Docker - первый опыт
Установка Windows server 2019.
Сразу после установки сконфигурировать основные параметры системы (имя, адрес, RDP и тд)
> sconfig
Быстро установить IP и тд можно из PS:
>netsh interface ipv4 show config
>netsh interface ipv4 set address name="vEthernet (Ethernet)" static 10.10.10.145 255.255.255.0 10.10.10.1
>netsh interface ip set dns "vEthernet (Ethernet)" static 8.8.8.8
, где "vEthernet (Ethernet)" - интерфейс вывода netsh interface ipv4 show config
Для управления через WWW можно установить WAC
PS> Start-BitsTransfer -Source http://10.10.10.5/soft/WindowsAdminCenter2009.msi -Destination C:\Windows\Temp\wac.msi
PS> msiexec /i C:\Windows\Temp\wac.msi /qn /L*v log.txt SME_PORT=443 SSL_CERTIFICATE-OPTION=generate
Можно отключить firewall на время эксперементов
PS> Set-NetFirewallProfile -Profile Domain,Public,Private -Enabled false
И дефолтный антивирус
PS> Uninstall-WindowsFeature Windows-Defender
Добавить нового пользователя "ork" и завести его в группу администраторов
PS> New-LocalUser -Name "ork"
PS> Add-LocalGroupMember -Group “Administrators” -Member ork
И перезапустить сервер по завершении конфигурации
PS> Restart-Computer
Если установка выполняется на WM под HYPER-V, то необходимо включить вложенную виртуализацию скриптом:
#replace with the virtual machine name
$vm = ""
#configure virtual processor
Set-VMProcessor -VMName $vm -ExposeVirtualizationExtensions $true -Count 2
#disable dynamic memory
Set-VMMemory -VMName $vm -DynamicMemoryEnabled $false
#enable mac spoofing
Get-VMNetworkAdapter -VMName $vm | Set-VMNetworkAdapter -MacAddressSpoofing On
Установка docker
Установить роли: hyper-V, контейнеризации
PS>Enable-WindowsOptionalFeature -Online -FeatureName Microsoft-Hyper-V -All
PS>Enable-WindowsOptionalFeature -Online -FeatureName containers
Установить сам docker
PS>Install-PackageProvider -Name nuget -force
PS>Install-Module -Name DockerMsftProvider -Repository PSGallery -Force
PS>Install-Package -Name docker -ProviderName DockerMsftProvider
PS>Restart-Computer
Установить docker-compose
PS>[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12
PS>Invoke-WebRequest "https://github.com/docker/compose/releases/download/1.27.4/docker-compose-Windows-x86_64.exe" -UseBasicParsing -OutFile $Env:ProgramFiles\Docker\docker-compose.exe
-test
PS>docker-compose --version
Настроить дефолтную сеть NAT, чтобы ее адресаци не прыгала при перезапуске сервера (полезно, если контейнерам присваиваются IP)
PS>stop-service docker
В ветке реестра HKEY_LOCAL_MACHINE - SYSTEM - CurrentControlSet - Services - Tcpip - Parameters - Interfaces найти по текущему IP и удалить сеть дефолтного NAT. (Get-ContainerNetwork | Remove-ContainerNetwork - на моей версии уже не работает )
Создать, если отсутствует, файл C:\ProgramData\docker\config\daemon.json с минимальным наполнением, указав желаемую адресацию сети nat:
{
"fixed-cidr": "10.10.10.1/24",
}
Перезапуститься
PS>Restart-Computer
Основные примеры работы с docker
Версия docker
>docker -v
Показать список имиджей
>docker images
Загрузить определенный имидж определенной версии
>docker pull mcr.microsoft.com/windows/nanoserver:1903
Посмотреть список запущеных контейров (-a - всех контейнеров)
>docker ps
Запустить контейнер
>docker run microsoft/iis
Запустить контейнер с имененм container2, пробросом порта 82 наружу,запуском после перезагрузки хоста, установленным IP 10.10.10.102 и включить в сеть nat
>docker run -itd --name container2 -p 82:80 --net nat --restart always --ip 10.10.10.102 microsoft/iis ping -t localhost
Подключиться к запущенному контейнеру container2 (выходить желательно вводя exit)
>docker exec -i -t container2 cmd
Узменить настройки контейнера
>docker update container2 --net nat --ip 10.10.10.202
Посмотреть настройки контейнера
>docker inspect container2
Запустить контейнер
>docker start container2
Остановить контейнер
>docker stop container2
Удалить контейнер
>dcoker rm container2
Удалить имидж
docker rmi microsoft/iis
Сети в docker
Контейнерные сети в windows и linux НЕ ПОХОЖИ, поэтому рассматриваются отдельно
Windows
Есть сети nat, transparent, overlay, L2Bridge, L2Tunnel.
Nat - дефолтная сеть. Пакеты натируются через интерфейс хоста.
>docker network create -d nat --subnet=10.10.10.0/24 docker-lan-nat
Transparent - прозрачная
>docker network create -d transparent --subnet 10.10.50.0/24 --gateway 10.10.50.1 -o com.docker.network.windowsshim.vlanid=7 -o com.docker.network.windowsshim.dnsservers="10.10.50.3" docker-lan-transparent
и так далее.
Стоит отметить, что после перезагрузки хоста мы с удивлением и негодованием отмечам пропадания всех созданных сетей, кроме дефолтной nat, overlay сетей и недокументированных private сетей, а также смену subnet IP у дефолной сети nat. Как это исправить описано выше.
Overlay сеть будет рассмотрена в рамках раздела SWARM.
Linux
Всё проще и понятней (без подводных камней).
# (Default. Сеть автономных контейнеров, которые должны взаимодействовать)
docker network create -d bridge --subnet=10.10.20.0/24 docker-lan-bridge
# (сеть автономных контейнеров, без доступа к хосту)
docker network create -d host --subnet=10.10.30.0/24 docker-lan-host
# (как bridge + связь нескольких докеров и их контейнеров. swarm)
docker network create -d overlay --subnet=10.10.40.0/24 docker-lan-overlay
# (сеть с назначенными MAC контейнерам. Можно выставлять в физическую сеть как хост)
docker network create -d macvlan --subnet=10.10.50.0/24 docker-lan-macvlan
# (сеть без сетевого взаимодействия)
docker network create -d none --subnet=10.10.60.0/24 docker-lan-none
Подключение контейнера к сети
>docker network connect --alias host1 --ip 10.10.10.202 nat container2
Отключение контейнера
>docker network disconnect nat container2
SWARM (рой)
Кластеризация контейнеров.
Понятие контейнера как такового отсутствует. Есть сервисы и их таски.
Сети внутри роя - типа overlay (для всех операционных сетей).
Создание роя.
>docker swarm init --advertise-addr=10.10.10.145 --listen-addr 10.10.10.145:2377
, при создании появится подсказка для подключения ноды в рой:
>docker swarm join --token SWMTKN-1-2q421at8pal8xg73dwlozqeehfvw7xcduei484w67r813eireq-e51nr07hc2im6zi8xcjbq3p8b 10.10.10.145:2377
Список swarm нод и статусов
>docker node ls
Сделать ноду менеджером управления
>docker node update --role manager
вывод ноду из роя
>docker swarm leave
Создание сервиса
>docker service create --name service1 --network docker-lan-overlay -p 81:80 microsoft/iis
По умолчанию при создании роя создается сеть ingress для внутриройного управления сервисами и тд.
Можно создать собственную overlay сеть для взаимодействия между сервисами, в том числе, расположенными на разных нодах.
>docker network create -d overlay --attachable --subnet 100.10.40.0/24 docker-lan-overlay
Отдельно нужно отметить, что если Вы мечтаете идентифицировать сервисы внутри оверлэй сети на ноде под управлением Windows server, то будьте готовы к тому, что после перезагрузки встроенный DNS превращается в тыкву - неверно резослвит имя сервиса в IP запущенного таска. Возможно со временем это пофиксят.
Portainer
Иструмент управления docker из WEB интерфейса.
По прежнему не всё радостно в windows королевстве.
Устанавливать portainer пришлось так
Создание volume:
>docker volume create portainer_data
Выкачивание имиджа -ce:
>docker pull portainer/portainer-ce
Перезапуск хоста:
PS>Restart-Computer
Запуск контейнера:
>docker run -d -p 9000:9000 --name portainer --network docker-lan-nat --restart always -v \\.\pipe\docker_engine:\\.\pipe\docker_engine' --isolation hyperv -v portainer_data:C:\data portainer/portainer
В противном случае, докер пытается выкачать не тот образ и portainer не запускается с ошибкой несовместимости хостовой системы.
В режиме роя требуется запуск агента portainer и самого portainer, но сделать это корректно из-за вышеописанной проблемы мне не удалось.
Текущие проблемы.
Сравнение организации сетей на Wind Server 2019 и Linux
Windows | Linux | |
Сохранение сетей | нет (кроме дефолт.NAT и overlay | да |
Доступность контейнера с хоста по IP |
только дефолтный nat | да |
Сохранение ip контейнера (не overlay) после reboot |
нет (сети пропадают) | да (не overlay) |
Корректная работа DNS в overlay |
нет | да |
Отработка смешанного windows + linux SWARM, где win19 server был leader и был перезапущен, приводит в смещению лидера на Linux и дальнейшему разрушению кластера.
Поднятие Registry
# установка Docker
$ sudo apt install apt-transport-https ca-certificates curl software-properties-common
$ curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add -
$ sudo add-apt-repository "deb [arch=amd64] https://download.docker.com/linux/ubuntu focal stable"
$ sudo apt update
$ sudo apt install docker-ce
$ sudo systemctl status docker
# установка compose
$ sudo curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
$ sudo chmod +x /usr/local/bin/docker-compose
$ docker ps - список запущенных
$ docker images - список имиджей
$ docker run -t -i ubuntu /bin/bash - запустить образ и войти в оболочку
$ docker-compose up - запуск контейнера из docker-compose.yml
$ docker rm -f c23aa3b622fb - удалить контейнер
$ docker rmi image-name - удаление образа
$ docker tag image-namee registry.domain/image-name:v2 - перименовать образа и присвоение тэга
запуск registry
mkdir -p /mnt/registry; chown 777 /mnt/registry
sudo docker run -p 5000:5000 --name registry -v /mnt/registry:/var/lib/registry -e REGISTRY_STORAGE_DELETE_ENABLED=true --rm registry:2
nginx:
map $upstream_http_docker_distribution_api_version $docker_distribution_api_version {
'' 'registry/2.0';
}
upstream docker-registry {
server 127.0.0.1:5000;
}
server {
listen 443 ssl;
server_name registry.domain;
ssl_certificate /etc/letsencrypt/live/registry.example.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/registry.example.com/privkey.pem;
client_max_body_size 0; #обязательно
chunked_transfer_encoding on; #обязательно
location /v2/ {
if ($http_user_agent ~ "^(docker\/1\.(3|4|5(?!\.[0-9]-dev))|Go ).*$" ) {
return 404;
}
add_header 'Docker-Distribution-Api-Version' $docker_distribution_api_version always;
proxy_pass http://docker-registry;
proxy_set_header Host $http_host; # required for docker client's sake
proxy_set_header X-Real-IP $remote_addr; # pass on real client's IP
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_read_timeout 900;
}
}
получить образ
$ docker pull registry.domain/image-name
отправить образ
$ docker push registry.domain/image-name
#!/bin/bash
registry="https://registry.domain"
image="image-name"
tag="mytag"
# список репозиториев
curl -X GET $registry/v2/_catalog
# список тагов в репозитории
curl -X GET "${registry}/v2/${image}/tags/list"
# списолк хэшей для тагов
curl -sI -k -H "Accept: application/vnd.docker.distribution.manifest.v2+json" \
"${registry}/v2/${image}/manifests/${tag}" \
| tr -d '\r' | sed -En 's/^Docker-Content-Digest: (.*)/\1/pi'
# удаление
$ curl -X DELETE -sI -k "${registry}/v2/${image}/manifests/sha256:f83ec85324b43e4ea9cf613fecdc1cd167725513767df562170b4e6a22227fb3"
..to be continued
Надеюсь кому-то это всё будет полезным.
URLs:
https://ruvds.com/ru/helpcenter/docker-registry-ubuntu/
https://perfect-inc.com/journal/docker-registry-ustanovka-i-ispol-zovanie/
Lisolog (C) / 2021