我已经阅读并尝试过这个
- https://www.ctl.io/developers/blog/post/gracefully-stopping-docker-containers/
- Gracefully Stopping Docker Containers
- https://docs.docker.com/engine/reference/commandline/stop/
- https://www.linuxjournal.com/content/bash-trap-command
- 并向我的 Dockerfile 添加了一个 SIGTERM
- 更何况我不记得了
我无法优雅地停止我的 docker 容器,容器只是停止并杀死里面的所有内容,而不是运行我的陷阱处理程序,我已经尝试解决这个问题一年或更长时间了。
这是我的入口点
ENTRYPOINT ["/home/sdtdserver/user.sh", "/home/sdtdserver/install.sh"]
这是做准备工作然后继续其他的脚本之一,user.sh
#!/bin/bash
exit_handler() {
# Execute the shutdown commands
echo "[INFO] Stopping 7 Days To Die Server" >> /home/sdtdserver/log/console/sdtdserver-console.log
su-exec sdtdserver /home/sdtdserver/sdtdserver stop
exit
}
set -eu
# Print info
echo "
=======================================================================
USER INFO:
UID: $PUID
GID: $PGID
MORE INFO:
If you have permission problems remember to use same user UID and GID.
Check it with "id" command
If problem persist check:
https://github.com/vinanrra/Docker-7DaysToDie/blob/master/README.md
=======================================================================
"
# Set user and group ID to sdtdserver user
groupmod -o -g "$PGID" sdtdserver > /dev/null 2>&1
usermod -o -u "$PUID" sdtdserver > /dev/null 2>&1
# Locale, Timezone
localedef -i en_US -c -f UTF-8 -A /usr/share/locale/locale.alias en_US.UTF-8 && \
ln -snf /usr/share/zoneinfo/$TimeZone /etc/localtime && echo $TimeZone > /etc/timezone
# Apply owner to the folder to avoid errors
chown -R sdtdserver:sdtdserver /home/sdtdserver
# Start cron
service cron start
# Change user to sdtdserver
su-exec sdtdserver "$@"
# Trap specific signals and forward to the exit handler
trap exit_handler SIGTERM
# Keep script alive to trap SIGTERM
while true; do
sleep 10
done
我认为我的问题在这里:su-exec sdtdserver "$@"- 第 43 行
我正在使用 su-exec 执行交换用户并以其他用户身份执行下一个脚本,也许这就是问题所在,我也一直在考虑将 user.sh 脚本移动到该脚本所在的位置在启动时执行,不使用 Dockerfile 中的入口点,而是交换到我的其他脚本 install.sh甚至删除 su-exec 的使用并重新格式化一个脚本中的所有内容(我不喜欢这个想法)
#!/bin/bash
rootDir=$(dirname "$(readlink -f "${BASH_SOURCE[0]}")")
scriptsDir="${rootDir}/scripts"
# Show log function
show_log () {
i="0"
# -F = --follow=name --retry
tail -F /home/sdtdserver/log/console/sdtdserver-console.log
}
test_alert () {
if [ "${TEST_ALERT,,}" == 'yes' ]; then
source $scriptsDir/server_alerts.sh
fi
}
# Check requeriments
# Check if script is missing
if [ ! -f sdtdserver ]; then
source $scriptsDir/check_script.sh
fi
# Check if server have been installed
if [ ! -f serverfiles/DONT_REMOVE.txt ]; then
source $scriptsDir/first_install.sh
fi
# Crontab
echo "# Crontab file" > crontab.txt
if [ "${BACKUP,,}" == 'yes' ]; then
source $scriptsDir/crontab/backup.sh
fi
if [ "${MONITOR,,}" == 'yes' ]; then
source $scriptsDir/crontab/monitor.sh
fi
echo "# Don't remove the empty line at the end of this file. It is required to run the cron job" >> crontab.txt
crontab crontab.txt
rm crontab.txt
# Use of case to avoid errors if used wrong START_MODE
case $START_MODE in
0)
exit
;;
1)
source $scriptsDir/server_start.sh
test_alert
show_log
;;
2)
source $scriptsDir/server_update.sh
exit
;;
3)
source $scriptsDir/server_update.sh
source $scriptsDir/server_start.sh
test_alert
show_log
;;
4)
source $scriptsDir/server_backup.sh
exit
;;
*)
source $scriptsDir/check_startMode.sh
exit
;;
esac
这是容器内的顶级命令:
这是我正在进行测试的 GitHub 分支:fix-exit
首先感谢每个试图帮助我的人,其次我只是不想复制和粘贴代码,我想了解为什么不起作用,因为这就是我遇到的问题,我一无所知,那就是为什么我无法修复它,即使是文档也是如此。
最佳答案
问题是我没有异步运行脚本,并且 bash 正在等待结束 install.sh 末尾的 tail 命令(这是“无尽的”),这是更改的代码部分:
# Change user to sdtdserver
su-exec sdtdserver bash /home/sdtdserver/install.sh &
# If bash is waiting for a command to complete and receives a signal for which a trap has been set, the trap will not be executed until the command completes.
# When bash is waiting for an asynchronous command via the wait builtin,
# the reception of a signal for which a trap has been set will cause the 'wait' builtin to return immediately with an exit status greater than 128,
# immediately after which the trap is executed.
wait $!
另外,这个人也有同样的问题,但我不知道是尾部的问题。
关于bash - 捕获 docker 信号并停止 bash 中的进程不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70770104/