我希望在一个容器中运行RabbitMQ,在另一个容器中运行一个工作进程。辅助进程需要访问RabbitMQ。
我想通过docker-compose
来管理这些。
到目前为止,这是我的docker-compose.yml
文件:
version: "3"
services:
rabbitmq:
image: rabbitmq
command: rabbitmq-server
expose:
- "5672"
- "15672"
worker:
build: ./worker
depends_on:
- rabbitmq
# Allow access to docker daemon
volumes:
- /var/run/docker.sock:/var/run/docker.sock
所以我公开了RabbitMQ端口。工作进程使用以下URL访问RabbitMQ:
amqp://guest:guest@rabbitmq:5672/
这是他们在官方教程中使用的,但是localhost
被替换为rabbitmq
,因为容器应该是可以使用与容器名称相同的主机名发现:。
默认情况下,Compose为您的应用程序设置一个网络。服务的每个容器都加入了默认网络,并且可以被该网络上的其他容器访问,并且可以在与容器名称相同的主机名上被它们发现。
每当我运行它时,我都会得到一个连接被拒绝的错误:
Recreating ci_rabbitmq_1 ... done
Recreating ci_worker_1 ... done
Attaching to ci_rabbitmq_1, ci_worker_1
worker_1 | dial tcp 127.0.0.1:5672: connect: connection refused
ci_worker_1 exited with code 1
我觉得这很有趣,因为它使用的是IP 127.0.0.1
(我认为)是localhost
,尽管我将rabbitmq
指定为主机名。我不是码头人关系网的专家,所以这也许是我想要的。
如果需要,我很乐意提供更多的信息!
编辑
有一个几乎相同的问题,这里。我认为我需要等到rabbitmq
启动并运行之后才能启动worker
。我试着做了健康检查:
version: "2.1"
services:
rabbitmq:
image: rabbitmq
command: rabbitmq-server
expose:
- "5672"
- "15672"
healthcheck:
test: [ "CMD", "nc", "-z", "localhost", "5672" ]
interval: 10s
timeout: 10s
retries: 5
worker:
build: .
depends_on:
rabbitmq:
condition: service_healthy
(注意不同的版本)。然而,这是行不通的--它总是失败的,因为它不健康。
发布于 2018-10-28 18:17:00
啊哈!我修好了。@Ijaz是完全正确的-- RabbitMQ服务需要一段时间才能启动,我的工作人员试图在它运行之前进行连接。
我试着使用延迟,但是当RabbitMQ比平常花费更长的时间时,它失败了。
这也表明了一个更大的架构问题--如果队列服务(在我的例子中是RabbitMQ)在生产过程中脱机会发生什么?现在我的整个网站都失败了。需要有一些内置的冗余和轮询。
如本这个相关的答案所述,我们可以在docker-compose 3+
中使用健康检查。
version: "3"
services:
rabbitmq:
image: rabbitmq
command: rabbitmq-server
expose:
- 5672
- 15672
healthcheck:
test: [ "CMD", "nc", "-z", "localhost", "5672" ]
interval: 5s
timeout: 15s
retries: 1
worker:
image: worker
restart: on-failure
depends_on:
- rabbitmq
现在,worker
容器将重新启动几次,而rabbitmq
容器将保持不健康状态。当rabbitmq
成功时,nc -z localhost 5672
立即变得健康--即当队列处于活动状态时!
发布于 2021-05-29 07:53:53
以下是正确的工作示例:
version: "3.8"
services:
rabbitmq:
image: rabbitmq:3.7.28-management
#container_name: rabbitmq
volumes:
- ./etc/rabbitmq/conf:/etc/rabbitmq/
- ./etc/rabbitmq/data/:/var/lib/rabbitmq/
- ./etc/rabbitmq/logs/:/var/log/rabbitmq/
environment:
RABBITMQ_ERLANG_COOKIE: ${RABBITMQ_ERLANG_COOKIE:-secret_cookie}
RABBITMQ_DEFAULT_USER: ${RABBITMQ_DEFAULT_USER:-admin}
RABBITMQ_DEFAULT_PASS: ${RABBITMQ_DEFAULT_PASS:-admin}
ports:
- 5672:5672 #amqp
- 15672:15672 #http
- 15692:15692 #prometheus
healthcheck:
test: [ "CMD", "rabbitmqctl", "status"]
interval: 5s
timeout: 20s
retries: 5
mysql:
image: mysql
restart: always
volumes:
- ./etc/mysql/data:/var/lib/mysql
- ./etc/mysql/scripts:/docker-entrypoint-initdb.d
environment:
MYSQL_ROOT_PASSWORD: root
MYSQL_DATABASE: mysqldb
MYSQL_USER: ${MYSQL_DEFAULT_USER:-testuser}
MYSQL_PASSWORD: ${MYSQL_DEFAULT_PASSWORD:-testuser}
ports:
- "3306:3306"
healthcheck:
test: ["CMD", "mysqladmin" ,"ping", "-h", "localhost"]
timeout: 20s
retries: 10
trigger-batch-process-job:
build: .
environment:
- RMQ_USER=${RABBITMQ_DEFAULT_USER:-admin}
- RMQ_PASS=${RABBITMQ_DEFAULT_PASS:-admin}
- RMQ_HOST=${RABBITMQ_DEFAULT_HOST:-rabbitmq}
- RMQ_PORT=${RABBITMQ_DEFAULT_PORT:-5672}
- DB_USER=${MYSQL_DEFAULT_USER:-testuser}
- DB_PASS=${MYSQL_DEFAULT_PASSWORD:-testuser}
- DB_SERVER=mysql
- DB_NAME=mysqldb
- DB_PORT=3306
depends_on:
mysql:
condition: service_healthy
rabbitmq:
condition: service_healthy
发布于 2018-10-28 05:16:24
如果您只是从另一个容器访问服务,则可能不需要公开/映射主机上的端口。
从文件中:
公开公开端口,而不将它们发布到主机上--它们只能被链接的服务访问。只能指定内部端口。 曝光:- "3000“- "8000”
所以应该是这样的:
version: "3"
services:
rabbitmq:
image: rabbitmq
command: rabbitmq-server
expose:
- "5672"
- "15672"
worker:
build: ./worker
depends_on:
- rabbitmq
# Allow access to docker daemon
volumes:
- /var/run/docker.sock:/var/run/docker.sock
也要确保连接到rabitmq,只有当它准备好服务器在端口上。
https://stackoverflow.com/questions/53031439
复制