Class: RVC::OptionParser

Inherits:
Trollop::Parser
  • Object
show all
Defined in:
lib/rvc/option_parser.rb

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(cmd, &b) ⇒ OptionParser

Returns a new instance of OptionParser.



28
29
30
31
32
33
34
35
36
37
# File 'lib/rvc/option_parser.rb', line 28

def initialize cmd, &b
  @cmd = cmd
  @summary = nil
  @args = []
  @has_options = false
  @seen_not_required = false
  @seen_multi = false
  @applicable = Set.new
  super &b
end

Instance Attribute Details

#applicableObject (readonly)

Returns the value of attribute applicable.



26
27
28
# File 'lib/rvc/option_parser.rb', line 26

def applicable
  @applicable
end

Instance Method Details

#arg(name, description, spec = {}) ⇒ Object



58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
# File 'lib/rvc/option_parser.rb', line 58

def arg name, description, spec={}
  spec = {
    :description => description,
    :required => true,
    :default => nil,
    :multi => false,
  }.merge spec
  spec[:default] = [] if spec[:multi] and spec[:default].nil?
  fail "Multi argument must be the last one" if @seen_multi
  fail "Can't have required argument after optional ones" if spec[:required] and @seen_not_required
  fail "lookup and lookup_parent are mutually exclusive" if spec[:lookup] and spec[:lookup_parent]
  [:lookup, :lookup_parent].each do |sym|
    if spec[sym].is_a? Enumerable
      spec[sym].each { |x| @applicable << x }
    elsif spec[sym]
      @applicable << spec[sym]
    end
  end
  @args << [name,spec]
  text "  #{name}: " + [description, spec[:lookup], spec[:lookup_parent]].compact.join(' ')
end

#educateObject



122
123
124
125
126
127
128
129
130
131
132
# File 'lib/rvc/option_parser.rb', line 122

def educate
  arg_texts = @args.map do |name,spec|
    text = name
    text = "[#{text}]" if not spec[:required]
    text = "#{text}..." if spec[:multi]
    text
  end
  arg_texts.unshift "[opts]" if has_options?
  puts "usage: #{@cmd} #{arg_texts*' '}"
  super
end

#has_options?Boolean

Returns:

  • (Boolean)


54
55
56
# File 'lib/rvc/option_parser.rb', line 54

def has_options?
  @has_options
end

#opt(name, *a) ⇒ Object



48
49
50
51
52
# File 'lib/rvc/option_parser.rb', line 48

def opt name, *a
  super
  @applicable << @specs[name][:lookup] if @specs[name][:lookup]
  @has_options = true unless name == :help
end

#parse(argv) ⇒ Object



80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
# File 'lib/rvc/option_parser.rb', line 80

def parse argv
  opts = super argv

  @specs.each do |name,spec|
    next unless klass = spec[:lookup] and path = opts[name]
    opts[name] = lookup_single! path, klass
  end

  argv = leftovers
  args = []
  @args.each do |name,spec|
    if spec[:multi]
      err "missing argument '#{name}'" if spec[:required] and argv.empty?
      a = (argv.empty? ? spec[:default] : argv.dup)
      a = a.map { |x| postprocess_arg x, spec }.inject(:+)
      err "no matches for '#{name}'" if spec[:required] and a.empty?
      args << a
      argv.clear
    else
      x = argv.shift
      err "missing argument '#{name}'" if spec[:required] and x.nil?
      x = spec[:default] if x.nil?
      a = x.nil? ? [] : postprocess_arg(x, spec)
      err "more than one match for #{name}" if a.size > 1
      err "no match for '#{name}'" if spec[:required] and a.empty?
      args << a.first
    end
  end
  err "too many arguments" unless argv.empty?
  return args, opts
end

#postprocess_arg(x, spec) ⇒ Object



112
113
114
115
116
117
118
119
120
# File 'lib/rvc/option_parser.rb', line 112

def postprocess_arg x, spec
  if spec[:lookup]
    lookup! x, spec[:lookup]
  elsif spec[:lookup_parent]
    lookup!(File.dirname(x), spec[:lookup_parent]).map { |y| [y, File.basename(x)] }
  else
    [x]
  end
end

#summary(str) ⇒ Object



39
40
41
42
# File 'lib/rvc/option_parser.rb', line 39

def summary str
  @summary = str
  text str
end

#summary?Boolean

Returns:

  • (Boolean)


44
45
46
# File 'lib/rvc/option_parser.rb', line 44

def summary?
  @summary
end