【问题标题】:How to remove multiples files in bash using ssh heredoc?如何使用 ssh heredoc 删除 bash 中的多个文件?
【发布时间】:2020-10-10 00:03:56
【问题描述】:

我知道其他用户已经问过同样的问题,但答案对我不起作用。

我正在尝试通过 ssh heredoc 连接使用 bash 中的数组删除多个文件,但它不起作用不要删除任何文件夹,但是如果我使用 ssh 命令运行相同的命令,它可以工作。

如何修复我的 heredoc ssh 命令?

#!/usr/bin/bash -x

DIRA="/home/developer/Documents/a"
DIRB="/home/developer/Documents/b"
DIRC="/home/developer/Documents/c"

declare -a array=($DIRA $DIRB $DIRC)

ssh -T developer@192.168.0.13 <<- EOSSH
    rm -rf "${array[@]}"
EOSSH

【问题讨论】:

  • $(declare -f) 是干什么用的?它列出了当前环境中定义的所有函数并将执行输出,从而在远程机器上声明你在本地机器上拥有的所有函数,但你似乎不需要任何这些?
  • 我使用它来通过 ssh 连接使用我的 bash 脚本函数
  • 是的,我不需要,我只是写这个例子的时候忘记删除了
  • 问题是${array[@]} 被本地shell 扩展(因为它处理here-doc),但是在远程shell 解析它之前不会应用双引号。将ssh -T developer@192.168.0.13替换为cat,这样你就可以看到发送到远程端的内容,应该更清楚问题是什么。
  • 我的意思是尝试使用不起作用的版本 cat,它会告诉你为什么它不起作用。

标签: linux bash ssh


【解决方案1】:

考虑这个最小的例子:

arr=(a b c)

cat <<EOF
    printf '<%s>\n' "${arr[@]}"
EOF

输出将是

printf '<%s>\n' "a b c"

会打印出来

<a b c>

如果你去掉引号,

printf '<%s>\n' ${arr[@]}

它扩展到

printf '<%s>\n' a b c

你得到

<a>
<b>
<c>

这就是为什么它似乎“解决”了您的问题,但它遭受了不带引号的扩展所具有的所有问题(分词、参数扩展)。

正如 Gordon 在他的 comment 中指出的那样,这种行为是因为 ${arr[@]} 立即被 shell 扩展,但 printf 命令中的引号仅适用于该扩展的结果,导致 printf看到一个论点。

要解决此问题,您可以将声明拉入 here-doc 并引用它,因此 shell 不会扩展任何内容:

cat <<'EOF'
    arr=(a b c)
    printf '<%s>\n' "${arr[@]}"
EOF

导致

arr=(a b c)
printf '<%s>\n' "${arr[@]}"

这会得到你

<a>
<b>
<c>

应用于问题中的具体案例:

ssh -T developer@192.168.0.13 <<- 'EOSSH'
    DIRA="/home/developer/Documents/a"
    DIRB="/home/developer/Documents/b"
    DIRC="/home/developer/Documents/c"

    array=("$DIRA" "$DIRB" "$DIRC")

    rm -rf "${array[@]}"
EOSSH

此时你可以直接去

ssh -T developer@192.168.0.13 <<- 'EOSSH'
    rm -rf "/home/developer/Documents/a" \
        "/home/developer/Documents/b" \
        "/home/developer/Documents/c"
EOSSH

【讨论】:

  • 我需要 DIRA、DIRB 和 DIRC 是全局变量,因此必须在 ssh heredoc 之外定义。
【解决方案2】:

我删除了引号,它可以工作。

#!/usr/bin/bash -x

DIRA="/home/developer/Documents/a"
DIRB="/home/developer/Documents/b"
DIRC="/home/developer/Documents/c"

declare -a array=($DIRA $DIRB $DIRC)

ssh -T developer@192.168.0.13 <<- EOSSH
    rm -rf ${array[@]}
EOSSH

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2013-03-11
    • 2022-11-17
    • 2023-03-23
    • 2019-08-05
    • 2012-05-17
    • 2021-05-01
    • 2011-02-26
    • 1970-01-01
    相关资源
    最近更新 更多