371

我正在寻找在 Mac OS X 上复制 Linux 'watch' 命令的最佳方法。我想每隔几秒运行一个命令,以使用 'tail' 和 'sed' 对输出文件的内容进行模式匹配.

在 Mac 上我最好的选择是什么,可以在不下载软件的情况下完成吗?

4

12 回答 12

724

安装Homebrew

brew install watch

于 2014-04-29T16:52:11.790 回答
411

您可以使用 shell 循环模拟基本功能:

while :; do clear; your_command; sleep 2; done

这将永远循环,清除屏幕,运行您的命令,然后等待两秒钟 - 基本watch your_command实现。

您可以更进一步,创建一个watch.sh可以接受your_commandsleep_duration作为参数的脚本:

#!/bin/bash
# usage: watch.sh <your_command> <sleep_duration>

while :; 
  do 
  clear
  date
  $1
  sleep $2
done
于 2012-03-05T21:17:44.733 回答
43

使用MacPorts

$ sudo port install watch
于 2013-01-24T23:45:46.040 回答
22

上面的 shell 可以解决问题,您甚至可以将它们转换为别名(您可能需要包装一个函数来处理参数):

alias myWatch='_() { while :; do clear; $2; sleep $1; done }; _'

例子:

myWatch 1 ls ## Self-explanatory
myWatch 5 "ls -lF $HOME" ## Every 5 seconds, list out home directory; double-quotes around command to keep its arguments together

或者,Homebrew可以从http://procps.sourceforge.net/安装手表:

brew install watch
于 2012-12-10T16:55:33.283 回答
15

可能“手表”不是你想要的。您可能想寻求帮助以解决您的问题,而不是实施您的解决方案!:)

如果您的真正目标是根据从command中看到的内容触发操作tail,那么您可以将其作为 tail 本身的一部分来执行。watch您可以按需运行代码,而不是“定期”运行。

#!/bin/sh

tail -F /var/log/somelogfile | while read line; do
  if echo "$line" | grep -q '[Ss]ome.regex'; then
    # do your stuff
  fi
done

请注意,tail -F即使它被 newsyslog 或 logrotate 轮换,它也会继续跟踪日志文件。您想使用它而不是小写字母tail -f。检查man tail详情。

也就是说,如果您确实想定期运行命令,则提供的其他答案可以转换为简短的 shell 脚本:

#!/bin/sh
if [ -z "$2" ]; then
  echo "Usage: $0 SECONDS COMMAND" >&2
  exit 1
fi

SECONDS=$1
shift 1
while sleep $SECONDS; do
  clear
  $*
done
于 2012-03-05T21:47:46.277 回答
11

我要回答这里得到答案:

bash -c 'while [ 0 ]; do <your command>; sleep 5; done'

但是你最好安装手表,因为这不是很干净......

于 2012-03-05T21:21:37.417 回答
9

如果手表不想通过安装

brew install watch

还有另一个类似/复制版本,为我安装并完美运行

brew install visionmedia-watch

https://github.com/tj/watch

于 2014-12-07T00:54:59.673 回答
6

Or, in your ~/.bashrc file:

function watch {
    while :; do clear; date; echo; $@; sleep 2; done
}
于 2013-11-19T00:23:37.137 回答
6

为了防止在您的主命令需要可感知的时间才能完成时闪烁,您可以捕获输出并仅在完成后清除屏幕。

function watch {while :; do a=$($@); clear; echo "$(date)\n\n$a"; sleep 1;  done}

然后通过以下方式使用它:

watch istats
于 2015-08-14T00:31:30.810 回答
2

尝试这个:

#!/bin/bash
# usage: watch [-n integer] COMMAND

case $# in
    0)
        echo "Usage $0 [-n int] COMMAND"
        ;;
    *)      
        sleep=2;
        ;;
esac    

if [ "$1" == "-n" ]; then
    sleep=$2
    shift; shift
fi


while :; 
    do 
    clear; 
    echo "$(date) every ${sleep}s $@"; echo 
    $@; 
    sleep $sleep; 
done
于 2014-11-15T20:40:40.503 回答
1

这是此答案的稍微更改的版本:

  • 检查有效参数
  • 在顶部显示日期和持续时间标题
  • 将“持续时间”参数移动到第一个参数,因此可以轻松地将复杂的命令作为剩余参数传递。

要使用它:

  • 将此保存到~/bin/watch
  • 在终端中执行chmod 700 ~/bin/watch以使其可执行。
  • 通过运行尝试watch 1 echo "hi there"

〜/斌/手表

#!/bin/bash

function show_help()
{
  echo ""
  echo "usage: watch [sleep duration in seconds] [command]"
  echo ""
  echo "e.g. To cat a file every second, run the following"
  echo ""
  echo "     watch 1 cat /tmp/it.txt" 
  exit;
}

function show_help_if_required()
{
  if [ "$1" == "help" ]
  then
      show_help
  fi
  if [ -z "$1" ]
    then
      show_help
  fi
}

function require_numeric_value()
{
  REG_EX='^[0-9]+$'
  if ! [[ $1 =~ $REG_EX ]] ; then
    show_help
  fi
}

show_help_if_required $1
require_numeric_value $1

DURATION=$1
shift

while :; do 
  clear
  echo "Updating every $DURATION seconds. Last updated $(date)"
  bash -c "$*"
  sleep $DURATION
done
于 2014-08-07T17:42:32.183 回答
1

使用Nix包管理器!

安装 Nix,然后执行,在完成安装说明(包括在你的 shell 中nix-env -iA nixpkgs.watch采购)后,它应该可以使用了。. "$HOME/.nix-profile/etc/profile.d/nix.sh"

于 2019-03-05T12:10:12.787 回答