为什么在 Java 中使用管道执行系统命令会在没有空格的情况下失败?
Why executing system command with pipeline in Java fail without whitespaces?
在 shell 命令行中,两个命令都是合法的并且 运行 没有问题:
# without whitespaces
parted /dev/sdd print free -m|grep free
和
# with whitespaces
parted /dev/sdd print free -m | grep free
但是,一旦我从 Java 它的前一个版本(没有空格的那个)运行,即:
Runtime.getRuntime().exec("parted /dev/sdd print free -m|grep free")
失败:
2019-09-10 18:33:34.012 WARN 2528 --- [ main] Utils : Error running parted /dev/sdd print free -m|grep free: parted: invalid option -- '|'
parted: invalid option -- 'g'
parted: invalid option -- 'r'
parted: invalid option -- 'e'
parted: invalid option -- 'p'
Usage: parted [-hlmsv] [-a<align>] [DEVICE [COMMAND [PARAMETERS]]...]
然而,与后一个命令版本(带空格的那个)相同的 java 行 运行 完全没问题。
显然,当 Java 中的 运行 时,'|'
符号无法被识别。问题是为什么?
Java exec
函数使用的规则不是 shell.
使用的规则
exec
splits into tokens based on whitespace.
因此foo|bar
是一个单一的标记。
相比之下,Shell 解析会将其视为 3 个独立的元素,foo
、|
和 bar
。 bash 的手册页为您详细说明了 bash 处理过程。
在 shell 命令行中,两个命令都是合法的并且 运行 没有问题:
# without whitespaces
parted /dev/sdd print free -m|grep free
和
# with whitespaces
parted /dev/sdd print free -m | grep free
但是,一旦我从 Java 它的前一个版本(没有空格的那个)运行,即:
Runtime.getRuntime().exec("parted /dev/sdd print free -m|grep free")
失败:
2019-09-10 18:33:34.012 WARN 2528 --- [ main] Utils : Error running parted /dev/sdd print free -m|grep free: parted: invalid option -- '|'
parted: invalid option -- 'g'
parted: invalid option -- 'r'
parted: invalid option -- 'e'
parted: invalid option -- 'p'
Usage: parted [-hlmsv] [-a<align>] [DEVICE [COMMAND [PARAMETERS]]...]
然而,与后一个命令版本(带空格的那个)相同的 java 行 运行 完全没问题。
显然,当 Java 中的 运行 时,'|'
符号无法被识别。问题是为什么?
Java exec
函数使用的规则不是 shell.
exec
splits into tokens based on whitespace.
因此foo|bar
是一个单一的标记。
相比之下,Shell 解析会将其视为 3 个独立的元素,foo
、|
和 bar
。 bash 的手册页为您详细说明了 bash 处理过程。