如何通过 SFTP 列出文件且仅列出文件?

如何通过 SFTP 列出文件且仅列出文件?

我实际上可以列出文件名,但很多不需要的东西也来自那里。

> echo "ls *.txt" | sftp user@host:/dir
Connected to 1.1.1.1.
Changing to: /dir
sftp> ls *.txt
1.txt
2.txt
3.txt

是否有一种经过验证/可靠的方法来列出文件并且仅列出文件?如果可能的话,我想避免使用head类似的过滤器。

答案1

使用-q选项告诉sftpquiet,从而抑制大部分你不关心的输出:

echo "ls *.txt" | sftp -q [email protected]:/path

您仍然会看到您正在回显的交互式提示行,例如sftp> ls *.txt,但可以使用 过滤掉这些行grep -v

echo "ls *.txt" | sftp -q [email protected]:/path | grep -v '^sftp>'

顺便说一句,最好的做法是使用批处理文件,并将其与参数一起传递给-bsftp不是echo将管道传入其中。

如果你们都真的想要做的是得到一个列表文件,这实际上可能比sshwith更好sftp(毕竟,s埃库尔F伊莱t转移 p程序):

ssh [email protected] ls -1 /path

答案2

通过挂载远程目录树SSHFS。 SSHFS 是一种使用 SFTP 协议访问远程文件的远程文件系统。如果服务器允许SFTP访问,则可以使用SSHFS(从服务器的角度来看,这是一样的)。在客户端,需要获得授权才能使用保险丝,这是大多数现代 unice 的情况。

一旦安装了文件系统,您就可以使用所有常用命令,而不必关心文件实际上是远程的。

mkdir host-dir
sshfs user@host:/dir host-dir
echo host-dir/*.txt
fusermount -u host-dir

答案3

sftp -q user@host:/dir <<<"ls *.txt" | grep -v '^sftp>`

但只有当 sftp 不询问密码时,这才有效。因为 grep -v 会影响 sftp 询问密码。

但我认为如果使用 tail,很多时候会很简单。

sftp -q user@host:/dir <<<"ls *.txt" | tail -n+2 

答案4

你们假设目录中只有文件。但是,如果有子目录,它们也会进入导出列表。所以你也必须以某种方式过滤子目录..可以使用 ls -l 并过滤掉以 d 开头的行:

 sftp -q user@host:/dir <<<"ls -l *.txt" | grep -v -E "^sftp|^d"

但这仍然会留下符号链接,所以也许:

sftp -q user@host:/dir <<<"ls -l *.txt" | grep -v "^sftp"| grep -- ^- 

在哪里

  • grep -v -E "^sftp|^d" 过滤 sftp cmd 或 ^d - 目录、^l 符号链接的打印输出.. 还有什么?
  • grep -- ^- 这仅显示文件

然而,来自 ls -l 的冗余信息..所以它也必须被切断..使用 cut 或 awk 作为直接方法:

sftp -q user@host:/dir <<<"ls -l *.txt" | grep -v "^sftp"| grep -- ^- | tr -s ' '|cut -d' ' -f9
sftp -q user@host:/dir <<<"ls -l *.txt" | grep -v "^sftp"| grep -- ^- | awk -F' ' '{print $9}'
sftp -q user@host:/dir <<<"ls -l *.txt" | grep -v "^sftp"| grep -- ^- | cut -c57-
  • tr -s ' ' 挤压重复的空白..用于 turther 字段排序
  • cut -d' ' -f9仅保留字段#9(通常为文件名,但请检查您的系统)
  • awk -F' ' '{print $9}'也只输出第9个字段。
  • cut -c57-只是删除字符 1-56 并将文件名保留在我的系统上。当文件名带有空格时,这种脆弱的剪切是我发现的唯一选项...

所以,得到简单的列表真是太奇怪了仅限 sftp 文件您可以使用它进行进一步处理..

更新:对于文件名包含空格的情况,我找不到比cut -c57-从 ls -l 中提取文件名更好的方法了。但它不可靠,因为不同的系统在 ls 输出中可能有不同的名称字段位置,甚至当文件所有者名称很长时,同一系统也会移动数据!我发现,可以通过使用 来避免这种情况ls -n,它将名称替换为数字 id,但这种方法仍然不是“好”。

我想尝试使用 awk,从 $0 中提取文件名,从 $9 的第一个位置开始直到 $0 行的末尾。任何人都知道如何在 awk 中获取字段的位置,比如说 $9,在 $0 行中?

我还没有找到任何可靠的方法来做到这一点。index($0,$9)如果文件名与用户名或前列中的某个数字匹配,将产生错误的结果。计算length$1,$2..$8 的总计也是错误的,因为字段分隔符在序列中重复。

我还注意到,使用ls -n *, 将在目录名之后打印/,这样很容易过滤。然而,使用带有 a 的任何 glob 掩码ls,如果未找到任何内容,则会向 stderr 报告一条消息(Can't ls: "/curdir/*" not found),这很烦人。

那么,有人知道如何获取 sftp 上的常规文件列表,从而允许处理带有空格和其他特殊字符的文件名吗?

相关内容