我正在尝试通过 ssh 连接到服务器,然后找到今天的文件,然后在这些文件中执行 grep 操作。但我收到一个错误,find: missing argument to `-exec'
.
我在这里缺少什么?
ssh server.name find /dir1/subdir/filelist* -maxdepth 1 type f -mtime 0 -exec grep 'pattern' {} \;
答案1
您的代码存在问题:
本地 shell 可以扩展
/dir1/subdir/filelist*
到一个或多个匹配路径。这些路径可能存在于远程端,也可能不存在。本地
ssh
根据它获取的多个参数构建 shell 代码(在远程端运行)。论据是:find
/dir1/subdir/filelist*
(如果没有本地匹配)-maxdepth
1
-type
(我假设你type
是一个错字)f
-mtime
0
-exec
grep
pattern
(因为本地 shell 用完了引号){}
;
(因为本地shell用掉了反斜杠)
构建的shell命令是:
find /dir1/subdir/filelist* -maxdepth 1 -type f -mtime 0 -exec grep pattern {} ;
这不是一个有效的
find
命令,因为(远程)shell 将解释;
为命令终止符,因此;
永远不会到达find
.另请注意,pattern
在远程 shell 的上下文中, 未加引号。
我认为这正是您想要在远程端的 shell 中运行的命令:
find /dir1/subdir/filelist* -maxdepth 1 -type f -mtime 0 -exec grep 'pattern' {} \;
看如何通过 ssh 执行复杂的命令行以及我的回答。我不会在这里重复所有内容。最重要的事情:
为了控制远程 shell 将获得的内容
$command_line_built_by_ssh
,您需要理解、预测和策划之前发生的解析和解释。您需要制作本地命令,所以后本地 shell 并消化它,它就变成了您想要在远程端执行的ssh
确切内容。$command_line…
ssh
一个基本的解决方案是将精确的(远程)命令作为单个参数传递给本地。在您的情况下,本地命令可能是:
ssh server.name 'find /dir1/subdir/filelist* -maxdepth 1 -type f -mtime 0 -exec grep '\''pattern'\'' {} \;'
在我对相关问题的回答中,我讨论了更多的想法。
答案2
您没有使用此 ssh 命令运行多个命令,而只是运行一个更复杂的 find 命令。
这里有两个主要问题。
- 根据您编写命令的方式,glob 模式将在客户端上进行评估。
- 出现错误消息的原因是
;
未到达find
命令。基本上,ssh
连接参数并将它们传递到sh -c
服务器上。你需要类似的东西\\\;
。
除非您在服务器上需要 stdin,否则最简单的解决方案是将 stdin 上的命令发送到 shell。这消除了对引号的需要。
ssh server.name /bin/sh <<'EOF'
find /dir1/subdir/filelist* -maxdepth 1 -type f -mtime 0 -exec grep 'pattern' {} \;
EOF