滚动日志文件

16

我有一个文件夹,里面装满了滚动日志文件,我希望能够使用tail命令查看这些文件。

这些文件的命名规则如下:

name      modified
00A.txt   Dec 27 19:00
00B.txt   Dec 27 19:01
00C.txt   Dec 27 19:02
00D.txt   Dec 27 19:03

在一个较老的Unix系统上,我正在尝试编写一个Shell脚本,以便跟踪特定目录中最近修改的文件,并且如果该文件被管理员关闭(滚动到下一个文件),我希望程序能够自动开始跟踪新文件,而不需要我退出tail命令重新运行。
tail -100f `ls -t | head -1` 

给定以上文件名,期望的行为如下:

./logtailer.sh

然后脚本将开始追踪00D.txt。当记录器完成对00D.txt的写入并最新的日志文件现在命名为00E.txt时,程序将自动开始追踪该文件。
可以通过观察tail输出中的文本“文件已被管理员关闭”,然后再运行以下命令来编写此脚本。
tail -100f `ls -t | head -1`

有没有比监听“文件已被管理员关闭”文本更优雅的方法?如何在shell脚本中逐行读取tail的输出?
补充说明:在我的系统上,tail的-F选项不可用。它使用的是不包含此功能的不同版本的tail。 操作系统版本-Solaris 10
2个回答

20
你可以使用-F选项来调用tail,这意味着--follow=name --retry
man页面中得知:
-F      
The -F option implies the -f option, but tail will also check to see if the 
file being followed has been renamed or rotated.  The file is closed and 
reopened when tail detects that the filename being read from has a new inode 
number. The -F option is ignored if reading from standard input rather than 
a file.

我希望我能使用这个标志,但是我的tail版本没有这个功能,而且我也没有升级的选项。(没有管理员权限) - user1118047
请提供您正在使用的tailbox(Unix / Linux)版本信息,谢谢。 - jaypal singh
2
-1,这不是OP所要求的。tail --follow=name适用于当输入文件被日志轮换脚本截断时,但OP想要在新文件出现时开始读取它。 - tripleee
我建议使用 tail -F 选项,它正是这样做的。OP 的 Solaris 系统上没有该选项。 - jaypal singh
我给这个+1。也许不完全是楼主想要的,但却正好是我想要的... - Adam Lerman
显示剩余3条评论

3

你可能需要使用inotify来检测新文件的创建,一个解决方法是在后台运行tail命令时持续轮询文件系统:

#!/bin/bash

get_latest() {
    local files=(*.log)
    local latest=${files[${#files[@]}-1]}
    echo "$latest"
    [[ $latest == $1 ]]
}
run_tail() {
    tail -c +0 -f "$1"
}

while true; do
    while current=$(get_latest "$current"); do
        sleep 1
    done
    [[ $pid ]] && kill $pid
    run_tail "$current" & pid=$!
done

(未经测试,不必要的hacky,而且要小心您旧系统的限制!)

1
我喜欢这个答案的方向...我无法直接将其插入到shell脚本中,并使其按照我的意愿执行,但我会在这里尝试一下代码并看看能做些什么让它工作。 - user1118047

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接