使用 APP_ENV=prod 时 Symfony Messenger 无法正常关闭
Symfony Messenger not shutting down gracefully when using APP_ENV=prod
我们在 AWS ECS 上的 Docker 容器中将 Symfony Messenger 与主管 运行 结合使用。我们注意到 worker 没有正常关闭。调试后,它似乎在使用 APP_ENV=dev
时按预期工作,但在 APP_ENV=prod
.
时却没有
我做了一个简单的sleepMessage,它休眠1秒然后打印一条消息60秒。这是 运行 APP_ENV=dev
如您所见,它显然在等待程序停止 运行。
现在 APP_ENV=prod
:
无需等待,立即停止。
在 Docker 文件中,我们配置了以下内容来启动 supervisor。它基于 php:8.1-apache
,所以这就是为什么配置了 STOPSIGNAL
RUN apt-get update && apt-get install -y --no-install-recommends \
# for supervisor
python \
supervisor
start-worker.sh 脚本包含这个
#!/usr/bin/env bash
cp config/worker/messenger-worker.conf ../../../etc/supervisor/supervisord.conf
exec /usr/bin/supervisord
我们这样做是因为某些环境变量仅在启动时可用。
出于调试目的,配置已被硬编码以进行测试。
下面是 messenger-worker.conf
[unix_http_server]
file=/tmp/supervisor.sock
[supervisord]
nodaemon=true ; start in foreground if true; default false
[rpcinterface:supervisor]
supervisor.rpcinterface_factory = supervisor.rpcinterface:make_main_rpcinterface
[program:messenger-consume]
stderr_logfile_maxbytes=0
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
command=bin/console messenger:consume async -vv --env=prod --time-limit=129600
process_name=%(program_name)s_%(process_num)02d
autostart=true
autorestart=true
numprocs=1
environment=
MESSENGER_TRANSPORT_DSN="https://sqs.eu-central-1.amazonaws.com/{id}/dev-
symfony-messenger-queue"
简而言之,当在上面的配置中使用 --env=prod
时,它不会等待 worker 停止,而使用 --env=dev
它会。有人知道如何解决这个问题吗?
原来它与 SQS 传输相关的 wait_time
option 有关。它可能导致在容器退出之前启动的请求,并在容器不再存在时被发回。所以,wait_time
到 0 解决了这个问题。
然后 this 可能会导致同样的问题
我不知道为什么 dev
和 prod
环境会有所不同,但您似乎没有设置 宽限期(在至少 主管 )。正如我在 docs 中添加的:
- 工人将能够handle the
SIGTERM
signal if you have the PCNTL PHP extension
- 您需要将
stopwaitsecs
添加到您的 Supervisor 程序配置中
因为你也使用Docker,你也可以设置默认为10s的graceful period at the service level:
services:
my_app:
stop_grace_period: 20s
# ...
使用此配置,运行 docker-compose down
(仅举个例子):
- Docker 向服务入口点 (Supervisor) 发送一个
SIGTERM
信号并等待 20s退出
- Supervisor 向它的程序(
messenger:consume
命令)发送一个 SIGTERM
信号并等待 20 秒让它们退出
messenger:consume
进程将“捕获” 信号,完成处理当前消息并停止
- 每个程序都停止了,Supervisor可以停止,然后DockerComposestack
我们在 AWS ECS 上的 Docker 容器中将 Symfony Messenger 与主管 运行 结合使用。我们注意到 worker 没有正常关闭。调试后,它似乎在使用 APP_ENV=dev
时按预期工作,但在 APP_ENV=prod
.
我做了一个简单的sleepMessage,它休眠1秒然后打印一条消息60秒。这是 运行 APP_ENV=dev
如您所见,它显然在等待程序停止 运行。
现在 APP_ENV=prod
:
无需等待,立即停止。
在 Docker 文件中,我们配置了以下内容来启动 supervisor。它基于 php:8.1-apache
,所以这就是为什么配置了 STOPSIGNAL
RUN apt-get update && apt-get install -y --no-install-recommends \
# for supervisor
python \
supervisor
start-worker.sh 脚本包含这个
#!/usr/bin/env bash
cp config/worker/messenger-worker.conf ../../../etc/supervisor/supervisord.conf
exec /usr/bin/supervisord
我们这样做是因为某些环境变量仅在启动时可用。 出于调试目的,配置已被硬编码以进行测试。 下面是 messenger-worker.conf
[unix_http_server]
file=/tmp/supervisor.sock
[supervisord]
nodaemon=true ; start in foreground if true; default false
[rpcinterface:supervisor]
supervisor.rpcinterface_factory = supervisor.rpcinterface:make_main_rpcinterface
[program:messenger-consume]
stderr_logfile_maxbytes=0
stdout_logfile=/dev/stdout
stdout_logfile_maxbytes=0
command=bin/console messenger:consume async -vv --env=prod --time-limit=129600
process_name=%(program_name)s_%(process_num)02d
autostart=true
autorestart=true
numprocs=1
environment=
MESSENGER_TRANSPORT_DSN="https://sqs.eu-central-1.amazonaws.com/{id}/dev-
symfony-messenger-queue"
简而言之,当在上面的配置中使用 --env=prod
时,它不会等待 worker 停止,而使用 --env=dev
它会。有人知道如何解决这个问题吗?
原来它与 SQS 传输相关的 wait_time
option 有关。它可能导致在容器退出之前启动的请求,并在容器不再存在时被发回。所以,wait_time
到 0 解决了这个问题。
然后 this 可能会导致同样的问题
我不知道为什么 dev
和 prod
环境会有所不同,但您似乎没有设置 宽限期(在至少 主管 )。正如我在 docs 中添加的:
- 工人将能够handle the
SIGTERM
signal if you have the PCNTL PHP extension - 您需要将
stopwaitsecs
添加到您的 Supervisor 程序配置中
因为你也使用Docker,你也可以设置默认为10s的graceful period at the service level:
services:
my_app:
stop_grace_period: 20s
# ...
使用此配置,运行 docker-compose down
(仅举个例子):
- Docker 向服务入口点 (Supervisor) 发送一个
SIGTERM
信号并等待 20s退出 - Supervisor 向它的程序(
messenger:consume
命令)发送一个SIGTERM
信号并等待 20 秒让它们退出 messenger:consume
进程将“捕获” 信号,完成处理当前消息并停止- 每个程序都停止了,Supervisor可以停止,然后DockerComposestack