我有一个成功运行的以下 Shell 命令:
sed -e "1,/^$(date -d -24hour +'%Y-%m-%d %H')/d" logfile | grep -A20 -B10 'Exception' | mail -s "Sample report" xyz@yourdomain
但是,我必须通过 SSH 连接到特定机器才能运行它。为了避免这种情况,我按照以下方式修改它导致失败:
ssh myserver 'sed -e "1,/^$(date -d -24hour +'%Y-%m-%d %H')/d" logfile | grep -A20 -B10 'Exception' | mail -s "Sample report" xyz@yourdomain '
这个命令有什么问题?我该如何解决这个问题?
最佳答案
将您的代码嵌入到引用的 heredoc 中以避免需要对其进行修改(这本质上是一个容易出错的过程):
ssh myserver 'bash -s' <<'EOF'
sed -e "1,/^$(date -d -24hour +'%Y-%m-%d %H')/d" logfile \
| grep -A20 -B10 'Exception' \
| mail -s "Sample report" xyz@yourdomain
EOF
在此处的特定情况下,您的原始修改失败的明显原因是内部单引号终止了整个代码周围的单引号。
具体来说:
+'%Y-%m-%d %H'
...该表达式中的第一个 '
终止了命令之前的空缺,因此该空格在语法上不 protected 。
您可以改为执行以下操作,因为您的 shell 是 bash:
ssh myserver $'sed -e "1,/^$(date -d -24hour +\'%Y-%m-%d %H\')/d" logfile | grep -A20 -B10 Exception | mail -s "Sample report" xyz@yourdomain'
$''
是一个扩展,其中反斜杠可以转义单引号(也可用于其他文字——\n
换行,\t
用于选项卡等),典型 POSIX sh 语法不可用的功能。
相比之下,在 POSIX sh 中,可以切换引号类型以嵌入文字单引号:'foo'"'"'bar'
以定义同时包含 foo< 的字符串
和 bar
被单引号括起来,并且在它们之间由单个文字单引号分隔——完全有效的语法,但对于不熟悉该习语的读者来说不一定容易处理)。
关于linux - 使用 SSH 的嵌套 grep,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35164688/