用 xargs 连接 bash 中的 URL

Concatenate URL in bash with xargs

我正在尝试从每行一个条目的输出构建 URL。我试过这个:

<stuff> | xargs -L1 -I {} echo "${url}&page=queryresults&j="{}

但是,对于一些长行(它们没有 space 但可以有破折号和下划线),我得到 '{}' 我希望 <stuff> 生成的字符串.如果我在最后的双引号和 {} 之间添加一个 space 它可以工作,但我有一个额外的 space 我不想要:

<stuff> | xargs -L1 -I {} echo "${url}&page=queryresults&j=" {}

同样,如果我删除 &page=queryresults 位,它会起作用。我不知道为什么。

我在这里错过了什么?

适用于此:

blajob_123abcd_1234567890x

但不是这个:SomeTask_some_long_project_name_with_cumulative_metrics_YYYYMMDD_2018_08_15T00_12345a67b8-scheduled-run-bla-bla-bla-yadda

这里根本不需要 xargs,没有它你会过得更好。以下保证在所有符合 POSIX 的 shell 上正常工作:

while IFS= read -r line; do
  printf '%s&page=queryresults&j=%s\n' "$url" "$line"
done

为什么不坚持 xargs -I {} echo "$url&...&j={}"

  • xargs -I 的规范包括以下文本:构造参数不能大于 255 字节。如果您的 URL 很长,这可能会导致截断——这似乎与描述的细节相符。
  • xargs -I 仅包含在 POSIX 的 XSI 扩展中;不声称实现这些扩展的平台不需要提供它,或者如果它们提供,也不需要以任何特定方式运行。
  • 如果您使用 xargs printf "$url..."(将 URL 替换为格式字符串而不是通过占位符),如果您的 URL 包含 % 符号,您将遇到错误.
  • 如果您使用 echo,如果您的 URL 包含文字反斜杠(请参阅 the POSIX specification for echo 的应用程序使用部分),您将有未指定的行为。

也就是说,如果您真的想要使用xargs,请考虑(在 GNU 系统上):

xargs -d $'\n' printf "${url//%/%%}"'&page=queryresults&j=%s\n'

...或者,在带有 BSD 工具的平台上:

tr '\n' '[=12=]' | xargs -0 printf "${url//%/%%}"'&page=queryresults&j=%s\n'

注:

  • 因为我们没有使用 -I,所以 255 个字符的限制根本不适用。 (类似地,xargs 能够将尽可能多的参数传递给 /usr/bin/printf 的每个实例,以适应其命令行,而不是每次调用仅限于一个参数)。
  • 在 URL 中,我们将任何 % 文字替换为 %%。如果 URL 已经正确编码,它不应包含任何反斜杠(它们应该已经被 %5C 替换)。
  • GNU 扩展 -d 用于指定只有换行符应被视为要作为参数的单词之间的分隔符;这也可以防止 xargs 本身解析和使用文字引号。在 BSD 平台上,将换行符转换为 NUL 并使用 -0 作为替代。