使用ruby的OptionParser来解析子命令

我希望能够使用ruby的OptionParser来解析表单的子命令

COMMAND [GLOBAL FLAGS] [SUB-COMMAND [SUB-COMMAND FLAGS]] 

喜欢:

 git branch -a gem list foo 

我知道我可以切换到一个不同的选项解析器库(如Trollop),但我有兴趣从OptionParser中学习如何做到这一点,因为我想更好地学习库。

有小费吗?

弄清楚了。 我需要使用OptionParser#order! 。 它将解析从ARGV开始的所有选项,直到找到非选项(不是选项参数),从ARGV删除它处理的所有内容,然后它将退出。

所以我只需要做一些事情:

 global = OptionParser.new do |opts| # ... end subcommands = { 'foo' => OptionParser.new do |opts| # ... end, # ... 'baz' => OptionParser.new do |opts| # ... end } global.order! subcommands[ARGV.shift].order! 

看起来OptionParser语法已经改变了一些。 我必须使用以下内容,以便arguments数组具有opts对象未解析的所有选项。

 begin opts.order!(arguments) rescue OptionParser::InvalidOption => io # Prepend the invalid option onto the arguments array arguments = io.recover(arguments) rescue => e raise "Argument parsing failed: #{e.to_s()}" end 

还有其他你可以看到的gem,如main 。

GLI是要走的路, https://github.com/davetron5000/gli 。 教程摘录:

 #!/usr/bin/env ruby require 'gli' require 'hacer' include GLI::App program_desc 'A simple todo list' flag [:t,:tasklist], :default_value => File.join(ENV['HOME'],'.todolist') pre do |global_options,command,options,args| $todo_list = Hacer::Todolist.new(global_options[:tasklist]) end command :add do |c| c.action do |global_options,options,args| $todo_list.create(args) end end command :list do |c| c.action do $todo_list.list.each do |todo| printf("%5d - %s\n",todo.todo_id,todo.text) end end end command :done do |c| c.action do |global_options,options,args| id = args.shift.to_i $todo_list.list.each do |todo| $todo_list.complete(todo) if todo.todo_id == id end end end exit run(ARGV) 

您可以在http://davetron5000.github.io/gli/找到该教程。