Как машина узнаёт, где находится образ Linux (например, для контейнера)?

Ответ

Система находит образ контейнера по его полному имени (FQDN), которое включает адрес реестра (registry), имя репозитория и тег или диджест. Механизм поиска зависит от контекста.

В Docker команда docker pull сначала проверяет локальный кеш. Если образа нет, Docker обращается к публичному Docker Hub (это registry по умолчанию) или к приватному registry, указанному в полном имени.

# Ищет в локальном кеше, затем качает с Docker Hub (registry-1.docker.io)
docker pull nginx:alpine

# Ищет и качает из приватного реестра GitLab
docker pull registry.gitlab.com/mygroup/myapp:latest

В Kubernetes путь к образу указывается в манифесте Pod или Deployment в поле spec.containers[].image. Kubelet на узле, используя Container Runtime Interface (CRI), выполняет аналогичную логику: проверяет локальный кеш и при необходимости обращается к удаленному registry.

apiVersion: v1
kind: Pod
metadata:
  name: myapp
spec:
  containers:
  - name: app
    image: nginx:1.25 # Скачается с Docker Hub
    # image: myprivateregistry.local:5000/app:v2 # Скачается с кастомного registry

Ключевые нюансы:

  • Аутентификация: Для приватных registry необходимо настроить секреты. В Kubernetes это imagePullSecrets, в Docker — логин через docker login.
  • Теги vs Диджесты: Тег (:latest) — это изменяемая метка. Диджест (nginx@sha256:a1b2c3...) — это криптографический хэш конкретного слоя образа, гарантирующий неизменность.
  • Локальные образы: Можно загрузить образ из tar-архива (docker load -i image.tar) или собрать локально (docker build). В этом случае registry не используется.

Ответ 18+ 🔞

А, ну это же про то, как вся эта ваша оркестрация ищет картинки, чтобы запустить! Ёпта, история знакомая, как свои пять пальцев.

Смотри, тут всё просто, как три копейки. У каждого контейнера есть полное имя, этакая визитка — адрес реестра, имя проекта и версия (тег или диджест). И система, будь то тупой Docker или навороченный K8s, по этой визитке ищет, где скачать эту хрень.

Вот смотри на Docker. Ты пишешь docker pull nginx. А он что делает? Первым делом лезет в свой локальный кеш, как хомяк в кладовку: «А нет ли у меня уже такого nginx'а?». Если нет — тогда уже начинает дергать удаленный реестр. По умолчанию это Docker Hub, но если ты указал свой — пойдет туда.

# Полезет в кеш, потом потащит с дефолтного Docker Hub'а
docker pull nginx:alpine

# А тут уже полезет в твой кастомный реестр, например, на GitLab
docker pull registry.gitlab.com/mygroup/myapp:latest

А в Kubernetes — та же песня, только в профиль. Ты в манифесте для пода в поле image прописываешь этот самый адрес. А потом kubelet на рабочей ноде, через свой CRI (это такой универсальный адаптер для рантаймов), делает ровно то же самое: проверяет локально, нет ли? Нет? Ну тогда пошел скачивать с того реестра, который ты написал.

apiVersion: v1
kind: Pod
metadata:
  name: myapp
spec:
  containers:
  - name: app
    image: nginx:1.25 # Потянет с Docker Hub
    # image: myprivateregistry.local:5000/app:v2 # Полезет на твой внутренний реестр

Но тут, бля, есть нюансы, на которых все обжигаются! Запоминай, ёперный театр:

  • Доступ к приватному реестру. Это не просто так, «ой, дай-ка я скачаю». Для приватных штук нужны ключи! В Docker — это docker login, а в K8s — специальные секреты типа imagePullSecrets. Без них тебе просто покажут фигу, доверия ебать ноль.
  • Теги против диджестов. Вот это важно! Тег (:latest) — это просто бумажка на коробке, которую можно переклеить. Сегодня :latest — это одна версия, завтра — другая. А диджест (nginx@sha256:a1b2c3...) — это как отпечаток пальца, криптографическая подпись конкретного билда. Гарантия, что скачаешь именно то, что было. Хуй с горы его не изменит.
  • Локальные образы. А бывает и так, что registry вообще не нужен. Собрал образ сам (docker build) или загрузил из архива (docker load -i image.tar) — и всё, он уже у тебя на машине. Система его найдет и запустит, не дергая никакую сеть.