das*_*s-g 6 ruby command-line-interface
在Ruby脚本中,有多种方法可以调用系统命令/命令行
`command arg1 arg2`%x(command arg1 arg2)(可用的其他分隔符)Kernel#system 方法: system('command arg1 arg2')Kernel#exec 方法: exec('command arg1 arg2')如果我希望Ruby脚本在被调用的命令失败时(异常)失败(使用非零退出代码),我可以检查$?前两个变量的特殊变量中的退出代码:
`command arg1 arg2`
fail unless $? == 0
Run Code Online (Sandbox Code Playgroud)
要么
%x,command arg1 arg2,
fail unless $? == 0
Run Code Online (Sandbox Code Playgroud)
如果我对命令的标准输出转到Ruby脚本的标准输出(我是),我可以使用变量3并检查其返回值:
unless system('command arg1 arg2')
fail
end
Run Code Online (Sandbox Code Playgroud)
如果我不关心拯救异常的能力,也不关心无法解决的异常的堆栈跟踪打印行为,我当然可以使用exit(1)或者在前两个变体exit($?)中代替fail.
如果进一步执行命令是Ruby脚本应该做的最后一件事,即使命令成功(退出代码0),我也可以使用第四个变体:
exec('command arg1 arg2')
Run Code Online (Sandbox Code Playgroud)
这将使用通过调用命令创建的新进程替换Ruby进程,但Ruby脚本的调用者的效果将是相同的:如果被调用的命令导致非零退出,他会看到非零退出代码码.
我非常喜欢第四个变体的简洁性,但是如果执行命令不是最后一件事,如果成功,我很遗憾不会使用它.相比之下,其他变体的条件fail或exit调用看起来非常不洁净,并且在我的一个用例中,往往违反单一抽象级别和单一责任原则.
我当然可以轻松地为前三种方法中的任何一种编写一个包装函数,使它们的用法看起来简洁,但由于这看起来像是一个基本的操作方法,我想知道Ruby是否已经内置了类似的内容 ......是一个我可以使用的实用程序函数,而不是我自己的包装器,或者一种机制,当命令失败时,它会改变一个或多个命令调用方法的行为,导致错误或非零退出,类似于sh和bash的选择set -e.
据我所知,没有内置的方法可以做到这一点,但你几乎可以通过一点元编程魔法来获得你想要的行为
def set_exit enable
if enable
define_method :system do |*args|
Kernel.system *args
exit $?.exitstatus unless $?.success?
end
else
define_method :system, Kernel.instance_method(:system)
end
end
set_exit true
# ...
# any failed system calls here will cause your script to exit
# ...
set_exit false
# now system is back to normal
Run Code Online (Sandbox Code Playgroud)
这通过重新定义systemfor 来工作Object,同时Kernel.system在需要内置行为时显式使用。
| 归档时间: |
|
| 查看次数: |
979 次 |
| 最近记录: |