我有一个安装和设置流量服务器的脚本:
yum install -y trafficserver
systemctl start trafficserver
traffic_line -s proxy.config.url_remap.remap_required -v 0
traffic_line -s proxy.config.reverse_proxy.enabled -v 0
问题是,traffic_line
失败了:
[connect] ERROR (main_socket_fd 3): No such file or directory error: could not connect to management port,确保traffic_manager正在运行
这是因为systemctl start
立即返回,无需等待流量服务器实际启动。
有没有办法告诉systemctl start
只有在服务启动后才返回?
如果这是不可能的,是否有一个我可以运行的命令systemctl start
来实际等待服务启动?
systemctl start
确实等待服务准备好(除非使用 调用--no-block
),服务只需要正确指示(即,不使用Type=simple
)。如果服务没有告诉 systemd 什么时候准备好了,那么 , 等的任何变化都systemctl is-active
不会systemctl show
帮助你。正如评论中提到的,最优雅的解决方案是套接字单元。systemd 启动套接字,
traffic_line
连接到它,systemd 启动服务,并traffic_line
阻塞,直到服务开始接受它从 systemd 继承的文件描述符上的连接。或者,您可以使用
Type=forking
(服务分叉,一旦分叉服务准备好主 PID 退出)或(服务一旦准备好就Type=notify
调用)。sd_notify(0, "READY=1")
不幸的是,所有这些解决方案都需要一些支持
trafficserver
——使用 systemd 的套接字而不是分配自己的套接字,在主进程中适当地分叉和等待,或者调用sd_notify
. 如果服务器不合作,systemd 无法神奇地猜测服务器何时准备就绪 :)稍微看了一下
trafficserver
的源代码,看起来它可能真的支持Type=forking
——服务器是由一个专用traffic_cop
命令生成的,它似乎要等到服务器启动并执行一些基本测试(至少代码看起来像这样) . 因此,如果您更改服务类型,它可能会起作用:经过几次尝试,我终于让它工作了。
第一次尝试
在深入研究 systemctl help 后,我找到了
is-active
命令:因此,我编写了一个 shell 脚本来等待服务激活:
不幸的是,即使当我使用启动/停止测试此脚本时,它按预期工作,但在它之后运行命令时,我仍然遇到相同的错误。
traffic_line
我认为该服务在实际进程完全启动之前报告为活动状态(可能是几毫秒)。第二次尝试
所以我尝试了另一种方法。知道这是服务的第一次启动,我可以等到流量服务器管理器的 PID 文件存在。这是我尝试过的:
同样的问题:在写入流量服务器管理器的 PID 文件时,管理器实际上还没有准备好接收订单,所以我仍然收到错误消息。
该死的,我不想用盲人
sleep
。第三次尝试
所以我最终检查了
traffic_line
命令本身没有失败:这行得通!
不错,但是...
不幸的是,答案非常具体到我正在使用的服务(trafficserver),并且不会直接适用于其他服务。
如果您知道此问题的更通用答案,请随时分享。
我不擅长 shell 脚本,但我认为如果分别返回active和running ,你会想要测试ActiveState和SubState属性。
之后,您应该能够运行脚本的第二部分。
最简单的方法是在脚本中添加一个睡眠:
或者你可以在这里做一些工作控制