Публикация образов в GHCR, GitLab Registry, управление версиями и тегами.
Docker-реестры — центральное звено CI/CD для хранения и распространения образов. Изучите работу с GHCR, GitLab Registry и управление версиями образов.
Docker Registry — сервер для хранения и распространения Docker-образов.
┌──────────────────────────────────────────────────────────────┐
│ CI/CD Pipeline │
│ │
│ ┌──────────┐ ┌─────────────┐ ┌─────────────┐ │
│ │ Build │ → │ Registry │ → │ Deploy │ │
│ │ Image │ push│ (GHCR, │ pull │ to Prod │ │
│ │ │ │ GitLab) │ │ │ │
│ └──────────┘ └─────────────┘ └─────────────┘ │
└──────────────────────────────────────────────────────────────┘
Популярные реестры:
| Реестр | URL | Особенности |
|---|---|---|
| Docker Hub | docker.io | Публичный, бесплатный с ограничениями |
| GHCR | ghcr.io | Интеграция с GitHub, приватные образы |
| GitLab Registry | registry.gitlab.com | Встроен в GitLab, пер-проект реестр |
| AWS ECR | <account>.dkr.ecr.<region>.amazonaws.com | Интеграция с AWS |
| GCP Artifact Registry | <location>-docker.pkg.dev | Интеграция с GCP |
| Azure ACR | <name>.azurecr.io | Интеграция с Azure |
# Логин с токеном
echo $GITHUB_TOKEN | docker login ghcr.io -u $GITHUB_ACTOR --password-stdin
# Логин с PAT (Personal Access Token)
echo $PAT | docker login ghcr.io -u $USERNAME --password-stdinname: Build and Push to GHCR
on:
push:
branches: [main]
tags:
- 'v*'
env:
REGISTRY: ghcr.io
IMAGE_NAME: ${{ github.repository }}
jobs:
build-and-push:
runs-on: ubuntu-latest
permissions:
contents: read
packages: write # Важно для записи в GHCR
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Log in to GHCR
uses: docker/login-action@v3
with:
registry: ${{ env.REGISTRY }}
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Extract metadata
id: meta
uses: docker/metadata-action@v5
with:
images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
tags: |
type=sha,prefix=
type=semver,pattern={{version}}
type=raw,value=latest,enable=${{ github.ref == 'refs/heads/main' }}
- name: Build and push
uses: docker/build-push-action@v5
with:
context: .
push: true
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}Важно: По умолчанию образы приватные. Для публичного доступа:
# Для организации добавьте permissions
permissions:
packages: write
contents: readGitLab CI автоматически предоставляет переменные для доступа к реестру:
# .gitlab-ci.yml
variables:
# Доступно автоматически в GitLab CI
# CI_REGISTRY: registry.gitlab.com
# CI_REGISTRY_IMAGE: registry.gitlab.com/group/project
# CI_REGISTRY_USER: username
# CI_REGISTRY_PASSWORD: token
build:
stage: build
image: docker:24-dind
services:
- docker:24-dind
variables:
DOCKER_TLS_CERTDIR: ""
script:
- docker login -u $CI_REGISTRY_USER -p $CI_REGISTRY_PASSWORD $CI_REGISTRY
- docker build -t $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA .
- docker push $CI_REGISTRY_IMAGE:$CI_COMMIT_SHAВ GitLab UI:
build:
script:
# Тег с SHA коммита
- docker build -t $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA .
# Тег с ветки
- docker tag $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA $CI_REGISTRY_IMAGE:$CI_COMMIT_REF_NAME
# Тег latest для main
- |
if [ "$CI_COMMIT_REF_NAME" = "main" ]; then
docker tag $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA $CI_REGISTRY_IMAGE:latest
fi
# Push всех тегов
- docker push -a $CI_REGISTRY_IMAGEMAJOR.MINOR.PATCH
│ │ └─ Исправления обратной совместимости
│ └──────── Новые функции с обратной совместимостью
└─────────────── Breaking changes
# GitHub Actions для semver
on:
push:
tags:
- 'v*' # v1.0.0, v2.1.3, etc.
jobs:
build:
steps:
- name: Extract version from tag
id: version
run: echo "VERSION=${GITHUB_REF#refs/tags/v}" >> $GITHUB_OUTPUT
- name: Build with version tag
uses: docker/build-push-action@v5
with:
tags: |
ghcr.io/user/app:${{ steps.version.outputs.VERSION }}
ghcr.io/user/app:latest# Уникальный тег для каждого коммита
tags: |
type=sha,prefix=
type=sha,prefix=,format=longРезультат:
ghcr.io/user/app:a1b2c3d (короткий SHA)ghcr.io/user/app:a1b2c3d4e5f6... (полный SHA)# Несколько тегов для одного образа
tags: |
type=ref,event=branch
type=ref,event=pr
type=semver,pattern={{version}}
type=semver,pattern={{major}}.{{minor}}
type=semver,pattern={{major}}
type=sha
type=raw,value=latest,enable=${{ github.ref == 'refs/heads/main' }}Пример для тега v1.2.3 на main:
user/app:1.2.3user/app:1.2user/app:1user/app:latestuser/app:a1b2c3dЧерез GitHub UI:
Через API:
# Получить список untagged образов
curl -H "Authorization: Bearer $TOKEN" \
https://ghcr.io/v2/user/app/tags/list
# Удалить конкретный тег
curl -X DELETE -H "Authorization: Bearer $TOKEN" \
https://ghcr.io/v2/user/app/manifests/<digest>name: Cleanup Old Images
on:
schedule:
- cron: '0 0 * * 0' # Каждое воскресенье
workflow_dispatch:
jobs:
cleanup:
runs-on: ubuntu-latest
steps:
- name: Delete untagged images
uses: actions/delete-package-versions@v5
with:
package-name: 'my-app'
package-type: 'container'
min-versions-to-keep: 10
delete-only-untagged-versions: true
token: ${{ secrets.GITHUB_TOKEN }}
- name: Delete old tagged versions
uses: actions/delete-package-versions@v5
with:
package-name: 'my-app'
package-type: 'container'
min-versions-to-keep: 5
delete-only-untagged-versions: false# .gitlab-ci.yml
cleanup:
stage: cleanup
image: curlimages/curl:latest
rules:
- if: $CI_COMMIT_BRANCH == $CI_DEFAULT_BRANCH
script:
# Удалить старые теги через API
- |
curl --request DELETE --header "PRIVATE-TOKEN: $CI_JOB_TOKEN" \
"$CI_API_V4_URL/projects/$CI_PROJECT_ID/registry/repositories/$REGISTRY_ID/tags/$TAG_NAME"name: Push to Multiple Registries
on: [push]
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
# Логин в GHCR
- name: Login to GHCR
uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
# Логин в Docker Hub
- name: Login to Docker Hub
uses: docker/login-action@v3
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
# Логин в ECR
- name: Login to ECR
uses: docker/login-action@v3
with:
registry: ${{ secrets.AWS_ACCOUNT_ID }}.dkr.ecr.${{ secrets.AWS_REGION }}.amazonaws.com
username: AWS
password: ${{ secrets.AWS_ECR_TOKEN }}
- name: Build and push to all registries
uses: docker/build-push-action@v5
with:
tags: |
ghcr.io/user/app:${{ github.sha }}
user/app:${{ github.sha }}
${{ secrets.AWS_ACCOUNT_ID }}.dkr.ecr.${{ secrets.AWS_REGION }}.amazonaws.com/app:${{ github.sha }}
push: truename: Scan for Vulnerabilities
on:
push:
branches: [main]
jobs:
scan:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Build image
run: docker build -t app:${{ github.sha }} .
- name: Run Trivy vulnerability scanner
uses: aquasecurity/trivy-action@master
with:
image-ref: 'app:${{ github.sha }}'
format: 'sarif'
output: 'trivy-results.sarif'
- name: Upload to GitHub Security tab
uses: github/codeql-action/upload-sarif@v3
with:
sarif_file: 'trivy-results.sarif'name: Sign Container Image
on:
push:
tags:
- 'v*'
jobs:
build-and-sign:
runs-on: ubuntu-latest
permissions:
contents: read
packages: write
id-token: write # Для OIDC
steps:
- uses: actions/checkout@v4
- name: Login to GHCR
uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Build and push
uses: docker/build-push-action@v5
with:
tags: ghcr.io/user/app:${{ github.ref_name }}
push: true
- name: Sign image with Cosign
uses: sigstore/cosign-installer@v3
with:
cosign-release: 'v2.2.2'
- name: Sign the image
run: |
cosign sign --yes ghcr.io/user/app@${{ steps.digest.outputs.digest }}# Плохо — тег может измениться
image: myapp:latest
# Хорошо — уникальный тег
image: myapp:a1b2c3d
image: myapp:v1.2.3latest для production# Избегайте в production
tags:
- latest # Только для dev/test
# Используйте для production
tags:
- ${{ github.sha }}
- ${{ github.ref_name }}# Автоматическое удаление старых версий
- name: Cleanup
uses: actions/delete-package-versions@v5
with:
min-versions-to-keep: 10# Для AWS ECR с OIDC
- name: Configure AWS credentials
uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: arn:aws:iam::123456789:role/github-role
aws-region: us-east-1
- name: Login to ECR
id: login-ecr
uses: aws-actions/amazon-ecr-login@v2- name: Scan before push
run: |
docker scan app:latest || exit 1Ключевые моменты работы с реестрами:
GITHUB_TOKENlatest в productionВ следующей теме вы изучите оптимизацию Docker-сборок для ускорения CI-пайплайнов.
Вопросы ещё не добавлены
Вопросы для этой подтемы ещё не добавлены.