RabbitMQ
Пароль указан в переменных Гитлаба и хэшируется при сборке. В definitions.json указаны слова-маркеры, которые будут заменены sed
-ом в зависимости от окружения, куда будет деплой Реббита.
- .gitlab-ci.yml
stages: - build - deploy variables: IMAGE_DEV: $CI_REGISTRY_IMAGE/rabbitmq_dev IMAGE_STAGE: $CI_REGISTRY_IMAGE/rabbitmq_stage IMAGE_PROD: $CI_REGISTRY_IMAGE/rabbitmq_prod VERSION: 1.0.$CI_PIPELINE_ID DOCKER_HOST: ssh://cicd@${DEPLOY_HOST} # Set default docker context in docker:cli container before_script: - eval $(ssh-agent -s) - cat $SSH_PRIVATE_KEY | tr -d '\r' | ssh-add - - sed -i '/StrictHostKeyChecking /c StrictHostKeyChecking no' /etc/ssh/ssh_config || true - echo "$CI_REGISTRY_PASSWORD" |docker login -u $CI_REGISTRY_USER --password-stdin $CI_REGISTRY # Task templates .build: stage: build tags: - shell variables: IMAGE_NAME: "" DEPLOY_HOST: "" RABBITMQ_USER: "" RABBITMQ_PASS: "" script: - RABBITMQ_PASS_HASH=`docker run --rm --name rabbit-hash-gen rabbitmq:management-alpine rabbitmqctl hash_password $RABBITMQ_PASS |grep -v $RABBITMQ_PASS` - sed -i "s|RABBITMQ_USER|$RABBITMQ_USER|g" definitions.json - sed -i "s|RABBITMQ_PASS_HASH|$RABBITMQ_PASS_HASH|" definitions.json - docker build -t $IMAGE_NAME:$VERSION . - docker push $IMAGE_NAME:$VERSION - docker tag $IMAGE_NAME:$VERSION $IMAGE_NAME:latest - docker push $IMAGE_NAME:latest .deploy: stage: deploy tags: - docker image: docker:cli variables: STACK: "" IMAGE_NAME: "" NETWORK: "" DEPLOY_HOST: "" RABBITMQ_STORAGE: "" RABBITMQ_PORT: "" RABBITMQ_ADMIN_PORT: "" script: - docker pull $IMAGE_NAME:$VERSION - docker stack rm $STACK - docker network create --driver=overlay --scope=swarm $NETWORK || true - docker stack deploy -c ./docker-compose.yml $STACK # Build build_dev: extends: .build rules: - if: $CI_COMMIT_BRANCH == "dev" - if: $BUILD == "yes" variables: IMAGE_NAME: $IMAGE_DEV DEPLOY_HOST: 10.1.0.138 RABBITMQ_USER: $RABBITMQ_USER_DEV RABBITMQ_PASS: $RABBITMQ_PASS_DEV # build_stage: # build_prod: # Deploy deploy_dev: extends: .deploy rules: - if: $CI_COMMIT_BRANCH == "dev" - if: $BUILD == "yes" - if: $DEPLOY == "dev" variables: VERSION: latest variables: STACK: rabbitmq_dev IMAGE_NAME: $IMAGE_DEV NETWORK: ${STACK} DEPLOY_HOST: 10.1.0.138 RABBITMQ_STORAGE: /docker/rabbitmq/dev/rabbitmq_storage RABBITMQ_PORT: 8088 RABBITMQ_ADMIN_PORT: 8089 environment: name: dev url: https://${DEPLOY_HOST}:${RABBITMQ_ADMIN_PORT} # deploy_stage: # deploy_prod:
# Админка через TLS (порт 15671)
- docker-compose.yml
version: "3.9" services: rabbitmq: image: ${IMAGE_NAME}:${VERSION} hostname: rabbitmq healthcheck: test: ["CMD", "rabbitmq-diagnostics", "-q", "ping"] ports: - ${RABBITMQ_PORT}:5672 - ${RABBITMQ_ADMIN_PORT}:15671 volumes: - ${RABBITMQ_STORAGE}:/var/lib/rabbitmq networks: - rabbitmq networks: rabbitmq: external: true name: ${NETWORK}
В Докерфайле генерится сертификат для шифрования канала к админке
- Dockerfile
FROM rabbitmq:management-alpine COPY --chown=rabbitmq:rabbitmq rabbitmq.conf /etc/rabbitmq/ COPY --chown=rabbitmq:rabbitmq definitions.json /etc/rabbitmq/ RUN \ mkdir -p -m 700 /etc/ssl/rabbitmq && \ cd /etc/ssl/rabbitmq && \ openssl genrsa -out ca.key 2048 && \ openssl req -new -x509 -days 36500 -key ca.key -subj "/C=CN/ST=GD/L=SZ/O=rabbitmq/CN=rabbitmq Root CA" -out ca.crt && \ openssl req -newkey rsa:2048 -nodes -keyout rabbitmq.key -subj "/C=CN/ST=GD/L=SZ/O=rabbitmq/CN=rabbitmq" -out rabbitmq.csr && \ openssl x509 -req -extfile <(printf "subjectAltName=DNS:rabbitmq") -days 36500 -in rabbitmq.csr -CA ca.crt -CAkey ca.key -CAcreateserial -out rabbitmq.crt && \ chown -R rabbitmq:rabbitmq /etc/ssl/rabbitmq
- rabbitmq.conf
load_definitions = /etc/rabbitmq/definitions.json # https://www.rabbitmq.com/management.html#single-listener-https management.ssl.port = 15671 management.ssl.cacertfile = /etc/ssl/rabbitmq/ca.crt management.ssl.certfile = /etc/ssl/rabbitmq/rabbitmq.crt management.ssl.keyfile = /etc/ssl/rabbitmq/rabbitmq.key
definitions.json (часть)
- definitions.json
{ "users": [ { "name": "RABBITMQ_USER", "password_hash": "RABBITMQ_PASS_HASH", "hashing_algorithm": "rabbit_password_hashing_sha256", "tags": "administrator", "limits": {} } ], "vhosts": [ { "name": "/" } ], "permissions": [ { "user": "RABBITMQ_USER", "vhost": "/", "configure": ".*", "write": ".*", "read": ".*" } ], "topic_permissions": [], "parameters": [], "global_parameters": [], "policies": [], "queues": [ { "name": "queue1", "vhost": "/", "durable": true, "auto_delete": false, "arguments": { "x-ha-policy": "all" } },
Очередь пустая после перезапуска RabbitMQ
In the class of your producer you should set delivery mode to “2” which is “persistent”.
You can do that using php-amqplib/rabbitmq-bundle
by extending your producer class with OldSound\RabbitMqBundle\RabbitMq\Producer
which, itself extends BaseAmqp
.
Once you’ve extended your producer class with OldSound\RabbitMqBundle\RabbitMq\Producer
it’s already by default setting the “persistent” delivery mode and you will see it stored both in “Persistent” and “In memory”.
Now even after a restart the messages are still int the queue, ready to be consumed.