场景:我有运行 Web 应用程序的负载平衡服务器。为了进行调试,我希望看到同一日志文件(例如 nginx 日志)的输出合并为单个流,例如tail -f
同一集群中的所有服务器上的流,其中一台是我当前登录的服务器。
这是一个使用后台进程的简单方法,例如有三个服务器 app-server-01、app-server-02、app-server-03,其中我登录到第一个服务器:
ssh -t "jneutron@app-server-02" "tail -f /var/log/nginx/access.log" &
ssh -t "jneutron@app-server-03" "tail -f /var/log/nginx/access.log" &
tail -f /var/log/nginx/access.log
这会根据需要合并多个服务器的日志输出,但按下 Ctrl-C 后,最终会出现后台进程徘徊的情况。
我正在寻找一种自动化的方法来清理这些后台进程,并想出了一个脚本,在这里分享作为答案。
答案1
这是一个按 Ctrl-C 清除后台进程的 bash 脚本。它可以配置用户和服务器列表。它假定您在列表中的其中一台服务器上运行该脚本。
#!/bin/bash
# Purpose: Continuously tail and combine log files on current and other servers
# configuration:
# servers, need to be hostname:
servers=("jimmy-neutron-01" "jimmy-neutron-02" "jimmy-neutron-03")
# remote user:
user="jneutron"
function ctrl_c_cleanup() {
echo
echo 'Ctrl-C trap: kill remote tail processes:'
plist=`ps -eaf | egrep "ssh .* $user[@].* tail \-f" | awk '{print $2}' | xargs echo`
echo "kill -9 $plist"
echo $plist | xargs kill -9
}
if [ $# -lt 1 ]; then
echo "Purpose: Continuously tail and combine log files on current and other servers"
echo "Example: $ xtail /var/log/nginx/access.log"
else
echo "tail -f $1 across servers: ${servers[@]}"
trap ctrl_c_cleanup INT # trap Ctrl-C and call ctrl_c_cleanup()
host=`uname --nodename`
for server in ${servers[@]}; do
if [[ $server != $host ]]; then
ssh -t "$user@$server" "tail -f $1" &
fi
done
tail -f "$1" # tail local log and wait for Ctrl-C
fi
#EOF
将其保存为xtail
,使其可执行,并可通过路径访问。
使用示例:
$ xtail /var/log/nginx/access.log
tail -f /var/log/nginx/access.log across servers: jimmy-neutron-01 jimmy-neutron-02 jimmy-neutron-03
...continuous log output...
^C
Ctrl-C trap: kill remote tail processes:
kill -9 116919 116921