Ruby中执行Linux shell命令的六种方法详解
在Ruby中,执行shell命令是一件不奇怪的事情,Ruby提供了大概6种方法供开发者进行实现。这些方法都很简单,本文将具体介绍一下如何在Ruby脚本中进行调用终端命令。
exec
exec会将指定的命令替换掉当前进程中的操作,指定命令结束后,进程结束。
exec'echo"helloworld"' print'abc'
执行上述的命令,结果如下,我们可以看到没有abc的输出,可以看出来,在执行echo"helloworld"命令后进程就结束了。不会继续执行后面的print'abc'。
rubytestCommand.rb helloworld
使用exec一个头疼的事情就是没有办法知道shell命令执行成功还是失败。
system
system和exec相似,但是system执行的命令不会是在当前进程,而是在一个新创建的进程。system会返回布尔值来表明命令执行结果是成功还是失败。
$irb >system'echo"hello$HOSTNAME"' helloandroidyue =>true >puts$? pid11845exit0 =>nil >system'false' =>false >puts$? pid11858exit1 =>nil >>
system会将进程的退出的状态码赋值给$?,如果程序正常退出,$?的值为0,否则为非0。通过检测退出的状态码我们可以在ruby脚本中抛出异常或者进行重试操作。
注:在Unix-like系统中进程的退出状态码以0和非0表示,0代表成功,非0代表失败。
system可以告诉我们命令执行是成功还是失败,但是有些时候我们需要得到执行命令的输出,并在脚本中使用。显然system无法直接满足,需要我们使用反引号来实现。
反引号(`)
使用反引号是shell中常用的获取命令输出内容的方法,在ruby中也是可以,而且一点都需要做改变。使用反引号执行命令也会将命令在另一个进程中执行。
1.9.3p448:013>today=`date` =>"SatNov1519:28:55CST2014\n" 1.9.3p448:014>$? =>#<Process::Status:pid11925exit0> 1.9.3p448:015>$?.to_i =>0 1.9.3p448:016>
上面的方法如此简单,我们可以直接对返回的字符串结果进行操作。
注意,$?已经不再是上述的那样单纯的退出状态码了,它实际上是一个Process::Status对象。我们从中不仅可以知道进程的退出状态码也可以知道进程的ID。使用$?.to_i会得到退出的状态码,使用$?.to_s会得到包含了进程id,退出状态码等信息的字符串。
使用反引号的一个结果就是我们只能得到标准的输出(stdout)而不能得到标准的错误信息(stderr),比如下面的例子,我们执行一个输出错误字符串的perl脚本。
$irb >>warning=`perl-e"warn'dustinthewind'"` dustinthewindat-eline1. =>"" >>putswarning
=>nil