Sed 用于等待特定字符串或超时后退出的Unix to-tail解决方案

Sed 用于等待特定字符串或超时后退出的Unix to-tail解决方案,sed,grep,tail,Sed,Grep,Tail,我试图改进一个服务(守护进程)脚本,以显示tomcat输出(从tty运行时),直到应用程序有效启动 Tomcat应用程序启动可能需要10分钟,看看会发生什么非常有用 但是,如果启动确认消息没有出现在日志中,我们需要确保这个启动脚本不会无限期运行 我知道互联网上充满了类似的问题,但到目前为止,我还没有找到一个明确的解决方案,尤其是一个不需要默认情况下不可用的实用程序就能工作的解决方案 要求: 无需在最新的Debian、Ubuntu、RedHat和OS X上安装任何东西即可运行 结束时没有留下任何进

我试图改进一个服务(守护进程)脚本,以显示tomcat输出(从tty运行时),直到应用程序有效启动

Tomcat应用程序启动可能需要10分钟,看看会发生什么非常有用

但是,如果启动确认消息没有出现在日志中,我们需要确保这个启动脚本不会无限期运行

我知道互联网上充满了类似的问题,但到目前为止,我还没有找到一个明确的解决方案,尤其是一个不需要默认情况下不可用的实用程序就能工作的解决方案

要求:

  • 无需在最新的Debian、Ubuntu、RedHat和OS X上安装任何东西即可运行
  • 结束时没有留下任何进程(由于任何原因)
  • 将记录的行显示到标准输出
  • 日志文件是只读的,您不能触摸它
  • 日志文件可以在不破坏工具的情况下旋转
  • 如果你能让它在一行中工作,那就额外的荣誉了
  • 迄今发现的问题:

    • read-t
      在当前Debian上不可用,
      非法选项-t
    迄今为止对部分解决方案的引用:


    如果您想要一个脚本来监视等待特定字符串的tomcat输出,下面的解决方案应该可以工作,并且它不使用
    read-t

    ( tail -f server.log & ( (tail -f server.log | grep -l STARTED && kill -9 `pstree -pa $$ | grep -E '\-(tail|sleep),' | sed 's/^[^0-9]*\([0-9]*\).*/\1/' | grep -vw $$ | xargs` ) & sleep 900 && kill -9 `pstree -pa $$ | grep -E '\-(tail|sleep),' | sed 's/^[^0-9]*\([0-9]*\).*/\1/' | grep -vw $$ | xargs` && exit 3 ) ) ; [ $? -eq 3 ]  && echo 'server not up after 5 min'  || echo 'server up'
    
    它正在日志文件server.log中搜索字符串“STARTED”,超时时间为15分钟(900秒)。 我不确定你的Debian有什么可用的。您应该有
    pstree
    ,其输出应该类似于:

    $ pstree -pa 1803
    bash,1803
      └─bash,7850
          ├─bash,7852
          │   ├─bash,7853
          │   │   ├─grep,7856 --color=auto -l STARTED
          │   │   └─tail,7855 -f server.log
          │   └─sleep,7854 20
          └─tail,7851 -f server.log
    
    剩下的我相信你应该有:
    kill
    sed
    sleep
    grep
    echo
    xargs

    对正在发生的事情的一些解释。这一行包含一个命令和命令结果的最终评估,以便在服务器是否启动时打印。该命令分为3部分:

  • 只需根据请求输出日志内容
  • 监视输出,查找特定字符串“已启动”;如果找到,
    kill
    第1部分和第3部分
  • 等待15分钟,如果15分钟过后,
    kill
    第1部分和第2部分, 以代码3退出,向外部评估发出信号,表示 由于超时,整个命令已结束 谨此陈辞:

    ( tail -f server.log & # part 1 - just output the log content
      ( # part 2
        (tail -f server.log | grep -l STARTED # search for the string
         && kill -9 `pstree -pa $$ | grep -E '\-(tail|sleep),' | 
            sed 's/^[^0-9]*\([0-9]*\).*/\1/' | grep -vw $$ | 
            xargs` # if found, kill the remaining tails and sleeps
        ) & # if the command ends in part 2, exit code is not 3
      sleep 900 # part 3: sleep 15 minutes
      && kill -9 `pstree -pa $$ | grep -E '\-(tail|sleep),' | 
                  sed 's/^[^0-9]*\([0-9]*\).*/\1/' | grep -vw $$ | 
                  xargs` # if time passed, kill the remaining tails and sleeps
      && exit 3 # exit with code 3, so that the outside evaluation 
                # knows it ended by timeout
      )
    ) ; # end of command; whenever it finishes, the evaluation below is executed, 
        # checking the exit code to print the appropriate message
    [ $? -eq 3 ]  && echo 'server not up after 5 min'  || echo 'server up'
    

    请注意,由于
    bash
    pipes的工作方式,如果找到“STARTED”字符串,则该命令实际上只会在带有“STARTED”的行之后向server.log添加额外的行后退出并打印消息“server up”。这是因为当打印行“STARTED”时,
    grep将找到它,打印它的输出并退出,关闭它的输入。但是,相应的
    tail
    将继续运行,直到它有其他东西要写;只有
    tail
    会意识到它的输出是关闭的,然后会消失,继续执行导致求值的
    kill
    命令。没有解决办法,阿福。您应该确保在“启动”消息之后打印到日志中,如果尚未打印。

    为了澄清:您需要一个“命令字符串”,它在退出之前监视(日志)文件一段时间,并将找到的字符串打印到stdout,如果找到则退出。你需要超时输出吗?我跟踪了你的链接。关于Tony K给出的解决方案,您不喜欢什么?它似乎符合您的所有标准,因此我遗漏了一些内容。我更新的解决方案有效吗?我很好奇……:)@我想谢谢你。从某种程度上说,它是有效的,但我有一些奇怪的问题,这就是为什么我目前没有使用它。我将不得不进一步挖掘它。现在,我认为不需要将其作为单线的要求。不管怎样,我修好后会回来的。很好,很乐意帮忙。你还可以得到进一步的帮助。。。你可以告诉我你遇到了什么问题的更多细节,或者如果你认为这是一个会改变这个问题本质的问题,你可以接受我的答案并打开另一个。我不确定这是否有效,我试过了,但我没有看到日志中的任何输出,我想是出了问题。在字符串出现之前,命令不会输出任何内容日志中出现“已启动”或已达到超时时间。当日志文件中出现字符串“已启动”时,它将仅输出“服务器已启动”;或在5分钟后输出“服务器未启动”“如果5分钟过去了,但没有看到字符串。您还需要什么其他输出?如果您可以添加一个将日志输出到stdout的版本,这样您就可以看到发生了什么。@sorin我将其更改为包含输出,并添加了一些对正在发生的事情的解释,以便您可以自己调整它,以防需要稍微不同的内容。