将文件内容作为字符串传递给另一个命令的参数

Pass contents of file as a string to an argument for another command

我有一个这样的 json 文件:

{"my_string": "apple", "my_int": 456}

还有一个 Bash 程序可以正常工作,如下所示:

my_program --message='{"my_string": "apple", "my_int": 456}'

但是当我的 JSON 是一个文件时,我似乎无法将它正确地获取到 运行:

my_program --message=$(cat test_message.json) 

我一直在搜索类似的问题,并尝试了很多方法,例如 tr、awk 以及 echo 和 cat 的各种组合,但都无济于事。

这是我收到的错误,让我相信这是我在 Bash 中做错的事情:

ERROR: (gcloud.beta.pubsub.schemas.validate-message) unrecognized arguments:
  "apple",
  "my_int":
  456}
  To search the help text of gcloud commands, run:
  gcloud help -- SEARCH_TERMS

如果你看到它看起来像是把 JSON 打断了,只取第一个 space 之前的字符。有任何想法吗?我觉得这是非常基本的,但我似乎无法弄清楚。提前谢谢你。

直接解决方法是在命令替换周围添加引号:

my_program --message="$(cat test_message.json)"

另见 When to wrap quotes around a shell variable?

但是,如果您可以控制 my_program,更好的解决方法是让它读取标准输入。

my_program --stdin <test_message.json

如果 cat 只是一个更复杂的东西的占位符,结合管道:

jq .fnord test_message.json |
my_program --stdin

(对于这种常见的基本情况,不要求显式选项可能更好。)

如果不是很明显,管道是生产者和消费者之间的直接通信线路,而命令替换需要 shell 在传递之前读取所有输出并将其缓冲到内存中.这是低效、不优雅和缓慢的,并且 error-prone 对于任何不平凡的输出量。