В этом уроке мы будем использовать зал для развертывания нашего приложения в Docker Swarm.
Поток
- Наш код приложения находится на GitHub
- Трубопровод запускается, когда коммит выдвигается в главную ветку
- Трубопровод автоматически развернут в стационарной среде
- Трубопровод требует ручного триггера для развертывания для Prod
- Примечание: постановка и протокол на одном и том же роя для демонстрации
Код для этого урока доступен на моем Репозиторий GitHub
Структура приложения
Структура приложения для нашего кода выглядит следующим образом:
Прохождение трубопровода
Наш ci/pipeline.yml
resources:
- name: main-repo
type: git
source:
uri: git@github.com:ruanbekker/concourse-swarm-app-demo.git
branch: master
private_key: ((github_private_key))
- name: main-repo-staging
type: git
source:
uri: git@github.com:ruanbekker/concourse-swarm-app-demo.git
branch: master
private_key: ((github_private_key))
paths:
- config/staging/*
- name: main-repo-prod
type: git
source:
uri: git@github.com:ruanbekker/concourse-swarm-app-demo.git
branch: master
private_key: ((github_private_key))
paths:
- config/prod/*
- name: slack-alert
type: slack-notification
source:
url: ((slack_notification_url))
- name: version-staging
type: semver
source:
driver: git
uri: git@github.com:ruanbekker/concourse-swarm-app-demo.git
private_key: ((github_private_key))
file: version-staging
branch: version-staging
- name: version-prod
type: semver
source:
driver: git
uri: git@github.com:ruanbekker/concourse-swarm-app-demo.git
private_key: ((github_private_key))
file: version-prod
branch: version-prod
resource_types:
- name: slack-notification
type: docker-image
source:
repository: cfcommunity/slack-notification-resource
tag: v1.3.0
jobs:
- name: bump-staging-version
plan:
- get: main-repo-staging
trigger: true
- get: version-staging
- put: version-staging
params:
bump: major
- name: bump-prod-version
plan:
- get: main-repo-prod
trigger: true
- get: version-prod
- put: version-prod
params:
bump: major
- name: deploy-staging
plan:
- get: main-repo-staging
- get: main-repo
- get: version-staging
passed:
- bump-staging-version
trigger: true
- task: deploy-staging
params:
DOCKER_SWARM_HOSTNAME: ((docker_swarm_staging_host))
DOCKER_SWARM_KEY: ((docker_swarm_key))
DOCKER_HUB_USER: ((docker_hub_user))
DOCKER_HUB_PASSWORD: ((docker_hub_password))
SERVICE_NAME: app-staging
SWARM: staging
ENVIRONMENT: staging
AWS_ACCESS_KEY_ID: ((aws_access_key_id))
AWS_SECRET_ACCESS_KEY: ((aws_secret_access_key))
AWS_DEFAULT_REGION: ((aws_region))
config:
platform: linux
image_resource:
type: docker-image
source:
repository: rbekker87/build-tools
tag: latest
username: ((docker_hub_user))
password: ((docker_hub_password))
inputs:
- name: main-repo-staging
- name: main-repo
- name: version-staging
run:
path: /bin/sh
args:
- -c
- |
./main-repo/ci/scripts/deploy.sh
on_failure:
put: slack-alert
params:
channel: '#system_events'
username: 'concourse'
icon_emoji: ':concourse:'
silent: true
text: |
*$BUILD_PIPELINE_NAME/$BUILD_JOB_NAME* ($BUILD_NAME) FAILED :rage: - TestApp Deploy to staging-swarm failed
http://ci.example.local/teams/$BUILD_TEAM_NAME/pipelines/$BUILD_PIPELINE_NAME/jobs/$BUILD_JOB_NAME/builds/$BUILD_NAME
on_success:
put: slack-alert
params:
channel: '#system_events'
username: 'concourse'
icon_emoji: ':concourse:'
silent: true
text: |
*$BUILD_PIPELINE_NAME/$BUILD_JOB_NAME* ($BUILD_NAME) SUCCESS :aww_yeah: - TestApp Deploy to staging-swarm succeeded
http://ci.example.local/teams/$BUILD_TEAM_NAME/pipelines/$BUILD_PIPELINE_NAME/jobs/$BUILD_JOB_NAME/builds/$BUILD_NAME
- name: deploy-prod
plan:
- get: main-repo-prod
- get: main-repo
- get: version-prod
passed:
- bump-prod-version
- task: deploy-prod
params:
DOCKER_SWARM_HOSTNAME: ((docker_swarm_prod_host))
DOCKER_SWARM_KEY: ((docker_swarm_key))
DOCKER_HUB_USER: ((docker_hub_user))
DOCKER_HUB_PASSWORD: ((docker_hub_password))
SERVICE_NAME: app-prod
SWARM: prod
ENVIRONMENT: production
AWS_ACCESS_KEY_ID: ((aws_access_key_id))
AWS_SECRET_ACCESS_KEY: ((aws_secret_access_key))
AWS_DEFAULT_REGION: ((aws_region))
config:
platform: linux
image_resource:
type: docker-image
source:
repository: rbekker87/build-tools
tag: latest
username: ((docker_hub_user))
password: ((docker_hub_password))
inputs:
- name: main-repo-prod
- name: main-repo
- name: version-prod
run:
path: /bin/sh
args:
- -c
- |
./main-repo/ci/scripts/deploy.sh
on_failure:
put: slack-alert
params:
channel: '#system_events'
username: 'concourse'
icon_emoji: ':concourse:'
silent: true
text: |
*$BUILD_PIPELINE_NAME/$BUILD_JOB_NAME* ($BUILD_NAME) FAILED :rage: - TestApp Deploy to prod-swarm failed
http://ci.example.local/teams/$BUILD_TEAM_NAME/pipelines/$BUILD_PIPELINE_NAME/jobs/$BUILD_JOB_NAME/builds/$BUILD_NAME
on_success:
put: slack-alert
params:
channel: '#system_events'
username: 'concourse'
icon_emoji: ':concourse:'
silent: true
text: |
*$BUILD_PIPELINE_NAME/$BUILD_JOB_NAME* ($BUILD_NAME) SUCCESS :aww_yeah: - TestApp Deploy to prod-swarm succeeded
http://ci.example.local/teams/$BUILD_TEAM_NAME/pipelines/$BUILD_PIPELINE_NAME/jobs/$BUILD_JOB_NAME/builds/$BUILD_NAME
Наш ci/detrentys.yml который будет хранить всю нашу секретную информацию, которая останется местной:
username: yourdockerusername password: yourdockerpassword docker_swarm_prod_host: 10.20.30.40 ...
Первый шаг нашего развертывания вызовет сценарий оболочки, который установит туннель SSH для хоста Docker, установив гнездо Docker в локальный порт TCP, а затем экспорт порт хоста Docker в туннельный порт, ci/scripts/deploy.sh :
#!/usr/bin/env sh
export DOCKER_HOST="localhost:2376"
echo "${DOCKER_SWARM_KEY}" | sed -e 's/\(KEY-----\)\s/\1\n/g; s/\s\(-----END\)/\n\1/g' | sed -e '2s/\s\+/\n/g' > key.pem
chmod 600 key.pem
screen -S \
sshtunnel -m -d sh -c \
"ssh -oStrictHostKeyChecking=no -oUserKnownHostsFile=/dev/null -i ./key.pem -NL localhost:2376:/var/run/docker.sock root@$DOCKER_SWARM_HOSTNAME"
sleep 5
docker login -u "${DOCKER_HUB_USER}" -p "${DOCKER_HUB_PASSWORD}"
docker stack deploy --prune -c ./main-repo/ci/docker/docker-compose.${ENVIRONMENT}.yml $SERVICE_NAME --with-registry-auth
if [ $? != "0" ]
then
echo "deploy failure for: $SERVICE_NAME"
screen -S sshtunnel -X quit
exit 1
else
set -x
echo "deploy success for: $SERVICE_NAME"
screen -S sshtunnel -X quit
fi
Скрипт развертывания ссылается на файлы Docker-Compose, сначала наш ci/docker/docker-compose.staging.yml :
version: "3.4"
services:
web:
image: ruanbekker/web-center-name
environment:
- APP_ENVIRONMENT=Staging
ports:
- 81:5000
networks:
- web_net
deploy:
mode: replicated
replicas: 2
networks:
web_net: {}
Кроме того, наша докера для производства, ci/docker/docker-compose.production.yml :
version: "3.4"
services:
web:
image: ruanbekker/web-center-name
environment:
- APP_ENVIRONMENT=Production
ports:
- 80:5000
networks:
- web_net
deploy:
mode: replicated
replicas: 10
networks:
web_net: {}
Установите трубопровод в зале
Создайте 2 филиала в вашем репозитории GitHub для использования версий: Постановка версии и Версия-прод , затем войдите в заговор и сохраните цель:
$ fly -t ci login -n main -c http://
Установите конвейер, укажите конфигурацию, определение локальных переменных и назовите трубопровод:
$ fly -t ci sp -n main -c ci/pipeline.yml -p-l ci/ .yml
Вы обнаружите, что трубопровод будет выглядеть ниже и что он будет в приостановленном состоянии:
Неужели трубопровод:
$ fly -t ci up -p swarm-demo
Трубопровод должен начать автоматически из-за триггера, который установлен на True:
Развернуто автоматически к постановке, Prod — это ручный триггер:
Тестирование наше приложение
Для демонстрационных целей мы развернули постановку на порту 81 и производство на порту 80.
Проверка тестирования на http://: 81/
Производство тестирования на http://: 80/
Оригинал: «https://dev.to/ruanbekker/using-concourse-ci-to-deploy-to-docker-swarm-5g4b»