使用xargs将bash中的URL连接起来

Max*_*wer 1 bash xargs

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

<stuff> | xargs -L1 -I {} echo "${url}&page=queryresults&j="{}
Run Code Online (Sandbox Code Playgroud)

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

<stuff> | xargs -L1 -I {} echo "${url}&page=queryresults&j=" {}
Run Code Online (Sandbox Code Playgroud)

同样,如果我删除该&page=queryresults位,它的工作原理.我不知道为什么.

我在这里错过了什么?

它适用于此:

blajob_123abcd_1234567890x
Run Code Online (Sandbox Code Playgroud)

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

Cha*_*ffy 5

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

while IFS= read -r line; do
  printf '%s&page=queryresults&j=%s\n' "$url" "$line"
done
Run Code Online (Sandbox Code Playgroud)

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

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

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

xargs -d $'\n' printf "${url//%/%%}"'&page=queryresults&j=%s\n'
Run Code Online (Sandbox Code Playgroud)

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

tr '\n' '\0' | xargs -0 printf "${url//%/%%}"'&page=queryresults&j=%s\n'
Run Code Online (Sandbox Code Playgroud)

注意:

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