slop 2.4.4 → 3.0.0.rc1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGES.md +0 -15
- data/README.md +46 -206
- data/lib/slop.rb +399 -888
- data/lib/slop/commands.rb +154 -0
- data/lib/slop/option.rb +149 -0
- data/slop.gemspec +1 -1
- data/test/commands_test.rb +58 -119
- data/test/option_test.rb +65 -159
- data/test/slop_test.rb +174 -497
- metadata +7 -5
data/test/option_test.rb
CHANGED
@@ -2,7 +2,7 @@ require 'helper'
|
|
2
2
|
|
3
3
|
class OptionTest < TestCase
|
4
4
|
def option(*args, &block)
|
5
|
-
Slop.new.
|
5
|
+
Slop.new.on(*args, &block)
|
6
6
|
end
|
7
7
|
|
8
8
|
def option_with_argument(*args, &block)
|
@@ -10,196 +10,102 @@ class OptionTest < TestCase
|
|
10
10
|
slop = Slop.new
|
11
11
|
option = slop.opt(*args)
|
12
12
|
slop.parse(options)
|
13
|
-
slop.find {|opt| opt.key == option.key }
|
13
|
+
slop.options.find {|opt| opt.key == option.key }
|
14
14
|
end
|
15
15
|
|
16
16
|
def option_value(*args, &block)
|
17
|
-
option_with_argument(*args, &block).
|
17
|
+
option_with_argument(*args, &block).value
|
18
18
|
end
|
19
19
|
|
20
|
-
test
|
21
|
-
assert option(:f, :foo, 'foo', true).expects_argument?
|
22
|
-
assert option(:f, :argument => true).expects_argument?
|
23
|
-
assert option(:f, :optional => false).expects_argument?
|
24
|
-
|
25
|
-
refute option(:f, :foo).expects_argument?
|
26
|
-
end
|
27
|
-
|
28
|
-
test 'expects an argument if long option is suffixed with =' do
|
29
|
-
assert option(:f, :foo=).expects_argument?
|
30
|
-
assert option('f', 'foo=').expects_argument?
|
20
|
+
test "expects_argument?" do
|
31
21
|
assert option(:f=).expects_argument?
|
22
|
+
assert option(:foo=).expects_argument?
|
23
|
+
assert option(:foo, :argument => true).expects_argument?
|
32
24
|
end
|
33
25
|
|
34
|
-
test
|
35
|
-
|
36
|
-
assert option(:f
|
37
|
-
|
38
|
-
refute option(:f, true).accepts_optional_argument?
|
26
|
+
test "accepts_optional_argument?" do
|
27
|
+
refute option(:f=).accepts_optional_argument?
|
28
|
+
assert option(:f=, :argument => :optional).accepts_optional_argument?
|
29
|
+
assert option(:f, :optional_argument => true).accepts_optional_argument?
|
39
30
|
end
|
40
31
|
|
41
|
-
test
|
42
|
-
|
43
|
-
option(:f
|
44
|
-
assert_equal
|
45
|
-
|
46
|
-
assert option(:callback => proc { item = "bar" }).call
|
47
|
-
assert_equal "bar", item
|
48
|
-
|
49
|
-
refute option(:f).call
|
50
|
-
end
|
51
|
-
|
52
|
-
test 'splits argument_value with :as => array' do
|
53
|
-
assert_equal %w/lee john bill/, option_value(
|
54
|
-
%w/--people lee,john,bill/, :people, true, :as => Array
|
55
|
-
)
|
56
|
-
|
57
|
-
assert_equal %w/lee john bill/, option_value(
|
58
|
-
%w/--people lee:john:bill/,
|
59
|
-
:people, true, :as => Array, :delimiter => ':'
|
60
|
-
)
|
61
|
-
|
62
|
-
assert_equal ['lee', 'john,bill'], option_value(
|
63
|
-
%w/--people lee,john,bill/,
|
64
|
-
:people, true, :as => Array, :limit => 2
|
65
|
-
)
|
66
|
-
|
67
|
-
assert_equal ['lee', 'john:bill'], option_value(
|
68
|
-
%w/--people lee:john:bill/,
|
69
|
-
:people, true, :as => Array, :limit => 2, :delimiter => ':'
|
70
|
-
)
|
32
|
+
test "key" do
|
33
|
+
assert_equal 'foo', option(:foo).key
|
34
|
+
assert_equal 'foo', option(:f, :foo).key
|
35
|
+
assert_equal 'f', option(:f).key
|
71
36
|
end
|
72
37
|
|
73
|
-
test
|
74
|
-
|
75
|
-
|
76
|
-
assert_equal
|
77
|
-
|
78
|
-
assert_equal "
|
79
|
-
|
80
|
-
assert_equal -1, option_value(%w/-i -1/, :i, true, :as => Integer)
|
81
|
-
assert_equal -1, option_value(%w/-i -1.1/, :i, true, :as => Integer)
|
82
|
-
assert_equal "-1.1", option_value(%w/-i -1.1/, :i, true, :as => Float).to_s
|
83
|
-
assert_equal "foo", option_value(%w/--foo1 foo/, :foo1, true)
|
84
|
-
|
85
|
-
assert_equal 0, option_value(%w//, :v, :verbose, :as => :count)
|
86
|
-
assert_equal 1, option_value(%w/--verbose/, :v, :verbose, :as => :count)
|
87
|
-
assert_equal 2, option_value(%w/--verbose -v/, :v, :verbose, :as => :count)
|
88
|
-
assert_equal 3, option_value(%w/-vvv/, :v, :verbose, :as => :count)
|
89
|
-
|
90
|
-
assert_equal 1, option_value(%w/-i 1/, :i, true, :as => proc { |x| x.to_i })
|
91
|
-
assert_equal "oof", option_value(%w/-i foo/, :i, true, :as => proc { |x| x.reverse })
|
38
|
+
test "call" do
|
39
|
+
foo = nil
|
40
|
+
option(:f, :callback => proc { foo = "bar" }).call
|
41
|
+
assert_equal "bar", foo
|
42
|
+
option(:f) { foo = "baz" }.call
|
43
|
+
assert_equal "baz", foo
|
44
|
+
option(:f) { |o| assert_equal 1, o }.call(1)
|
92
45
|
end
|
93
46
|
|
94
|
-
|
95
|
-
assert_equal nil, option_value(%w/-i/, :i, :as => :int)
|
96
|
-
assert_equal nil, option_value(%w/-i/, :i, :as => :str)
|
97
|
-
assert_equal nil, option_value(%w/-i/, :i, :as => :float)
|
98
|
-
assert_equal nil, option_value(%w/-i/, :i, :as => :array)
|
99
|
-
assert_equal nil, option_value(%w/-i/, :i, :as => :range)
|
47
|
+
# type casting
|
100
48
|
|
101
|
-
|
49
|
+
test "proc/custom type cast" do
|
50
|
+
assert_equal 1, option_value(%w'-f 1', :f=, :as => proc {|x| x.to_i })
|
51
|
+
assert_equal "oof", option_value(%w'-f foo', :f=, :as => proc {|x| x.reverse })
|
102
52
|
end
|
103
53
|
|
104
|
-
test
|
105
|
-
assert_equal
|
106
|
-
assert_equal (1..10), option_value(%w/-r 1-10/, :r, true, :as => Range)
|
107
|
-
assert_equal (1..10), option_value(%w/-r 1,10/, :r, true, :as => Range)
|
108
|
-
assert_equal (1...10), option_value(%w/-r 1...10/, :r, true, :as => Range)
|
109
|
-
assert_equal (-1..10), option_value(%w/-r -1..10/, :r, true, :as => Range)
|
110
|
-
assert_equal (1..-10), option_value(%w/-r 1..-10/, :r, true, :as => Range)
|
111
|
-
|
112
|
-
# default back to the string unless a regex is successful
|
113
|
-
# return value.to_i if the value is /\A\d+\z/
|
114
|
-
# maybe this should raise if Slop#strict?
|
115
|
-
assert_equal "1abc10", option_value(%w/-r 1abc10/, :r, true, :as => Range)
|
116
|
-
assert_equal (1..1), option_value(%w/-r 1/, :r, true, :as => Range)
|
117
|
-
assert_equal (2..2), option_value(%w/-r 2/, :r, true, :as => Range)
|
54
|
+
test "integer type cast" do
|
55
|
+
assert_equal 1, option_value(%w'-f 1', :f=, :as => Integer)
|
118
56
|
end
|
119
57
|
|
120
|
-
test
|
121
|
-
|
122
|
-
slop.opt :n, :name, 'Your name', true
|
123
|
-
slop.opt :age, 'Your age', true
|
124
|
-
slop.opt :V, 'Display the version'
|
125
|
-
|
126
|
-
assert_equal " -n, --name Your name", slop.options[:name].to_s
|
127
|
-
assert_equal " --age Your age", slop.options[:age].to_s
|
128
|
-
assert_equal " -V, Display the version", slop.options[:V].to_s
|
58
|
+
test "symbol type cast" do
|
59
|
+
assert_equal :foo, option_value(%w'-f foo', :f=, :as => Symbol)
|
129
60
|
end
|
130
61
|
|
131
|
-
test
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
assert_equal
|
62
|
+
test "range type cast" do
|
63
|
+
assert_equal (1..10), option_value(%w/-r 1..10/, :r=, :as => Range)
|
64
|
+
assert_equal (1..10), option_value(%w/-r 1-10/, :r=, :as => Range)
|
65
|
+
assert_equal (1..10), option_value(%w/-r 1,10/, :r=, :as => Range)
|
66
|
+
assert_equal (1...10), option_value(%w/-r 1...10/, :r=, :as => Range)
|
67
|
+
assert_equal (-1..10), option_value(%w/-r -1..10/, :r=, :as => Range)
|
68
|
+
assert_equal (1..-10), option_value(%w/-r 1..-10/, :r=, :as => Range)
|
136
69
|
end
|
137
70
|
|
138
|
-
test
|
139
|
-
assert_equal
|
140
|
-
assert_equal
|
71
|
+
test "array type cast" do
|
72
|
+
assert_equal %w/lee john bill/, option_value(%w/-p lee,john,bill/, :p=, :as => Array)
|
73
|
+
assert_equal %w/lee john bill/, option_value(%w/-p lee:john:bill/, :p=, :as => Array, :delimiter => ':')
|
74
|
+
assert_equal %w/lee john,bill/, option_value(%w/-p lee,john,bill/, :p=, :as => Array, :limit => 2)
|
75
|
+
assert_equal %w/lee john:bill/, option_value(%w/-p lee:john:bill/, :p=, :as => Array, :limit => 2, :delimiter => ':')
|
141
76
|
end
|
142
77
|
|
143
|
-
test
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
|
78
|
+
test "adding custom types" do
|
79
|
+
opts = Slop.new
|
80
|
+
opt = opts.on :f=, :as => :reverse
|
81
|
+
opt.types[:reverse] = proc { |v| v.reverse }
|
82
|
+
opts.parse %w'-f bar'
|
83
|
+
assert_equal 'rab', opt.value
|
148
84
|
end
|
149
85
|
|
150
|
-
|
151
|
-
slop = Slop.new
|
152
|
-
slop.on :f, :foo, :help => false
|
153
|
-
refute slop.help.include?('foo')
|
154
|
-
end
|
86
|
+
# end type casting tests
|
155
87
|
|
156
|
-
test
|
157
|
-
|
158
|
-
|
159
|
-
|
88
|
+
test "using a default value as fallback" do
|
89
|
+
opts = Slop.new
|
90
|
+
opt = opts.on :f, :argument => :optional, :default => 'foo'
|
91
|
+
opts.parse %w'-f'
|
92
|
+
assert_equal 'foo', opts[:f]
|
160
93
|
end
|
161
94
|
|
162
|
-
test
|
95
|
+
test "printing options" do
|
163
96
|
slop = Slop.new
|
164
|
-
slop.
|
165
|
-
|
166
|
-
|
167
|
-
assert slop.parse %w/--foo hello/
|
168
|
-
end
|
169
|
-
|
170
|
-
test 'non-casting of nil options' do
|
171
|
-
slop = Slop.new { on :f, :foo, true, :as => String }
|
172
|
-
slop.parse []
|
173
|
-
|
174
|
-
assert_equal nil, slop[:foo]
|
175
|
-
refute_equal "", slop[:foo]
|
176
|
-
end
|
177
|
-
|
178
|
-
test 'counting options' do
|
179
|
-
slop = Slop.new { on :v; on :x }
|
180
|
-
slop.parse %w/-v -v -v -x/
|
181
|
-
assert_equal 1, slop.options[:x].count
|
182
|
-
assert_equal 3, slop.options[:v].count
|
183
|
-
end
|
184
|
-
|
185
|
-
test 'omit block execution with :unless option' do
|
186
|
-
item = nil
|
187
|
-
opts = Slop.new do
|
188
|
-
on :foo
|
189
|
-
on :bar, true, :unless => 'foo' do; item = "foo"; end
|
190
|
-
end
|
191
|
-
opts.parse %w/--foo --bar 1/
|
97
|
+
slop.opt :n, :name=, 'Your name'
|
98
|
+
slop.opt :age=, 'Your age'
|
99
|
+
slop.opt :V, 'Display the version'
|
192
100
|
|
193
|
-
assert_equal "
|
194
|
-
|
101
|
+
assert_equal " -n, --name Your name", slop.fetch_option(:name).to_s
|
102
|
+
assert_equal " --age Your age", slop.fetch_option(:age).to_s
|
103
|
+
assert_equal " -V, Display the version", slop.fetch_option(:V).help
|
195
104
|
end
|
196
105
|
|
197
|
-
test
|
198
|
-
|
199
|
-
|
200
|
-
|
201
|
-
|
202
|
-
assert_raises(Slop::MissingOptionError, /foo is required/) { opts.parse %w[ --bar ] }
|
203
|
-
assert_raises(Slop::MissingOptionError, /foo is required/) { opts.parse %w[ foo ] }
|
106
|
+
test "overwriting the help text" do
|
107
|
+
slop = Slop.new
|
108
|
+
slop.on :foo, :help => ' -f, --foo SOMETHING FOOEY'
|
109
|
+
assert_equal ' -f, --foo SOMETHING FOOEY', slop.fetch_option(:foo).help
|
204
110
|
end
|
205
|
-
end
|
111
|
+
end
|
data/test/slop_test.rb
CHANGED
@@ -1,8 +1,11 @@
|
|
1
1
|
require 'helper'
|
2
2
|
|
3
3
|
class SlopTest < TestCase
|
4
|
-
|
5
|
-
|
4
|
+
|
5
|
+
def build_option(*args)
|
6
|
+
opt = Slop.new.send(:build_option, args)
|
7
|
+
config = opt.config.reject { |k, v| v == Slop::Option::DEFAULT_OPTIONS[k] }
|
8
|
+
[opt.short, opt.long, opt.description, config]
|
6
9
|
end
|
7
10
|
|
8
11
|
def temp_argv(items)
|
@@ -13,590 +16,264 @@ class SlopTest < TestCase
|
|
13
16
|
ARGV.replace old_argv
|
14
17
|
end
|
15
18
|
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
slop = Slop.new :strict, :multiple_switches => true
|
22
|
-
[ :@multiple_switches, :@strict ].each do |var|
|
23
|
-
assert slop.instance_variable_get var
|
24
|
-
end
|
25
|
-
end
|
26
|
-
|
27
|
-
test 'parse returns a Slop object' do
|
28
|
-
slop = Slop.parse([])
|
29
|
-
assert_kind_of Slop, slop
|
19
|
+
def temp_stderr
|
20
|
+
$stderr = StringIO.new
|
21
|
+
yield $stderr.string
|
22
|
+
ensure
|
23
|
+
$stderr = STDERR
|
30
24
|
end
|
31
25
|
|
32
|
-
test
|
33
|
-
|
34
|
-
|
35
|
-
|
26
|
+
test "build_option" do
|
27
|
+
assert_equal ['f', nil, nil, {}], build_option(:f)
|
28
|
+
assert_equal [nil, 'foo', nil, {}], build_option(:foo)
|
29
|
+
assert_equal ['f', nil, 'Some description', {}], build_option(:f, 'Some description')
|
30
|
+
assert_equal ['f', 'foo', nil, {}], build_option(:f, :foo)
|
36
31
|
|
37
|
-
|
38
|
-
|
32
|
+
# with arguments
|
33
|
+
assert_equal ['f', nil, nil, {:argument=>true}], build_option('f=')
|
34
|
+
assert_equal [nil, 'foo', nil, {:argument=>true}], build_option('foo=')
|
35
|
+
assert_equal [nil, 'foo', nil, {:optional_argument=>true}], build_option('foo=?')
|
39
36
|
end
|
40
37
|
|
41
|
-
test
|
38
|
+
test "fetch_option" do
|
42
39
|
slop = Slop.new
|
43
|
-
slop.
|
44
|
-
slop.
|
40
|
+
opt1 = slop.on :f, :foo
|
41
|
+
opt2 = slop.on :bar
|
45
42
|
|
46
|
-
|
43
|
+
assert_equal opt1, slop.fetch_option(:foo)
|
44
|
+
assert_equal opt1, slop.fetch_option(:f)
|
45
|
+
assert_equal opt2, slop.fetch_option(:bar)
|
46
|
+
assert_equal opt2, slop.fetch_option('--bar')
|
47
|
+
assert_nil slop.fetch_option(:baz)
|
47
48
|
end
|
48
49
|
|
49
|
-
test
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
end
|
50
|
+
test "default all options to take arguments" do
|
51
|
+
slop = Slop.new(:arguments => true)
|
52
|
+
opt1 = slop.on :foo
|
53
|
+
opt2 = slop.on :bar, :argument => false
|
54
54
|
|
55
|
-
|
56
|
-
|
57
|
-
temp_argv([]) do
|
58
|
-
Slop.new { on_empty { item1 = 'foo' } }.parse
|
59
|
-
end
|
60
|
-
|
61
|
-
assert_equal 'foo', item1
|
62
|
-
|
63
|
-
temp_argv([]) do
|
64
|
-
assert_equal [], Slop.new { on_empty {} }.parse
|
65
|
-
end
|
66
|
-
end
|
67
|
-
|
68
|
-
test 'callback when arguments contain no options' do
|
69
|
-
item = nil
|
70
|
-
Slop.new { on_optionless { item = 'foo' } }.parse %w/a b c/
|
71
|
-
assert_equal 'foo', item
|
55
|
+
assert opt1.expects_argument?
|
56
|
+
refute opt2.expects_argument?
|
72
57
|
end
|
73
58
|
|
74
|
-
test
|
75
|
-
slop = Slop.new :multiple_switches => true, :strict => true
|
76
|
-
%w/a b c/.each { |f| slop.on f }
|
77
|
-
slop.on :z, true
|
78
|
-
slop.parse %w/-abc/
|
79
|
-
|
80
|
-
%w/a b c/.each do |flag|
|
81
|
-
assert slop[flag]
|
82
|
-
assert slop.send(flag + '?')
|
83
|
-
end
|
84
|
-
|
85
|
-
assert_raises(Slop::InvalidOptionError, /d/) { slop.parse %w/-abcd/ }
|
86
|
-
assert_raises(Slop::MissingArgumentError, /z/) { slop.parse %w/-abcz/ }
|
87
|
-
|
88
|
-
slop = Slop.new(:multiple_switches)
|
89
|
-
slop.on :a
|
90
|
-
slop.on :f, true
|
91
|
-
args = %w[-abc -f foo bar]
|
92
|
-
slop.parse! args
|
93
|
-
|
94
|
-
assert_equal %w[ bar ], args
|
95
|
-
assert_equal 'foo', slop[:f]
|
96
|
-
assert slop[:a]
|
97
|
-
end
|
98
|
-
|
99
|
-
test 'passing a block' do
|
100
|
-
assert Slop.new {}
|
101
|
-
slop = nil
|
102
|
-
assert Slop.new {|s| slop = s }
|
103
|
-
assert_kind_of Slop, slop
|
104
|
-
end
|
105
|
-
|
106
|
-
test 'automatically adding the help option' do
|
59
|
+
test "extract_option" do
|
107
60
|
slop = Slop.new
|
108
|
-
|
109
|
-
|
110
|
-
slop = Slop.new :help => true
|
111
|
-
refute_empty slop.options
|
112
|
-
assert_equal 'Print this help message', slop.options[:help].description
|
113
|
-
end
|
114
|
-
|
115
|
-
test ':all_accept_arguments' do
|
116
|
-
opts = Slop.new(:all_accept_arguments) do
|
117
|
-
on :foo
|
118
|
-
on :bar, :optional => true
|
119
|
-
end
|
120
|
-
opts.parse %w[ --foo hello --bar ]
|
121
|
-
|
122
|
-
assert_equal 'hello', opts[:foo]
|
123
|
-
assert_nil opts[:bar]
|
124
|
-
assert_raises(Slop::MissingArgumentError) { opts.parse %w[ --foo --bar ] }
|
125
|
-
end
|
61
|
+
extract = proc { |flag| slop.send(:extract_option, flag) }
|
62
|
+
slop.on :opt=
|
126
63
|
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
end
|
64
|
+
assert_kind_of Array, extract['--foo']
|
65
|
+
assert_equal 'bar', extract['--foo=bar'][1]
|
66
|
+
assert_equal 'bar', extract['-f=bar'][1]
|
67
|
+
assert_nil extract['--foo'][0]
|
68
|
+
assert_kind_of Slop::Option, extract['--opt'][0]
|
69
|
+
assert_equal false, extract['--no-opt'][1]
|
134
70
|
end
|
135
71
|
|
136
|
-
test
|
137
|
-
|
138
|
-
slop = Slop.new { on(:name, true) { |name| items << name } }
|
139
|
-
slop.parse(%w/foo --name bar baz/) { |value| items << value }
|
140
|
-
assert_equal %w/foo bar baz/, items
|
141
|
-
end
|
142
|
-
|
143
|
-
test 'only parsing options' do
|
144
|
-
slop = Slop.new { on :n, true }
|
145
|
-
assert slop.parse %w/n/
|
146
|
-
end
|
147
|
-
|
148
|
-
test 'setting the banner' do
|
149
|
-
slop = Slop.new
|
150
|
-
slop.banner = "foo bar"
|
151
|
-
|
152
|
-
assert_equal "foo bar", slop.banner
|
153
|
-
assert slop.to_s =~ /^foo bar/
|
154
|
-
|
155
|
-
slop.banner = nil
|
156
|
-
assert_equal "", slop.to_s
|
157
|
-
|
158
|
-
slop = Slop.new "foo bar"
|
159
|
-
assert_equal "foo bar", slop.banner
|
160
|
-
|
161
|
-
slop = Slop.new :banner => "foo bar"
|
162
|
-
assert_equal "foo bar", slop.banner
|
163
|
-
end
|
164
|
-
|
165
|
-
test 'setting the summary' do
|
166
|
-
slop = Slop.new
|
167
|
-
slop.banner = "foo bar"
|
168
|
-
slop.summary = "does stuff"
|
169
|
-
|
170
|
-
assert_equal "foo bar\n\ndoes stuff", slop.to_s
|
171
|
-
end
|
172
|
-
|
173
|
-
test 'setting the description' do
|
72
|
+
test "non-options yielded to parse()" do
|
73
|
+
foo = nil
|
174
74
|
slop = Slop.new
|
175
|
-
slop.
|
176
|
-
|
177
|
-
slop.description = "This does stuff."
|
178
|
-
|
179
|
-
assert_equal "foo bar\n\ndoes stuff\n\n This does stuff.", slop.to_s
|
75
|
+
slop.parse ['foo'] do |x| foo = x end
|
76
|
+
assert_equal 'foo', foo
|
180
77
|
end
|
181
78
|
|
182
|
-
test
|
183
|
-
|
184
|
-
slop.banner = "foo bar"
|
185
|
-
slop.description = "This does stuff."
|
186
|
-
|
187
|
-
assert_equal "foo bar\n\n This does stuff.", slop.to_s
|
79
|
+
test "::parse returns a Slop object" do
|
80
|
+
assert_kind_of Slop, Slop.parse([])
|
188
81
|
end
|
189
82
|
|
190
|
-
test
|
83
|
+
test "parse" do
|
191
84
|
slop = Slop.new
|
192
|
-
assert_equal
|
193
|
-
slop.
|
194
|
-
assert_equal 4, slop.longest_flag
|
195
|
-
slop.opt(:username)
|
196
|
-
assert_equal 8, slop.longest_flag
|
197
|
-
end
|
198
|
-
|
199
|
-
test 'parse returning the list of arguments left after parsing' do
|
200
|
-
opts = Slop.new do
|
201
|
-
on :name, true
|
202
|
-
end
|
203
|
-
assert_equal %w/a/, opts.parse!(%w/--name lee a/)
|
204
|
-
assert_equal %w/--name lee a/, opts.parse(%w/--name lee a/)
|
205
|
-
assert_equal ['foo', :bar, 1], opts.parse(['foo', :bar, 1])
|
206
|
-
end
|
207
|
-
|
208
|
-
test '#parse does not remove parsed items' do
|
209
|
-
items = %w/--foo/
|
210
|
-
Slop.new { |opt| opt.on :foo }.parse(items)
|
211
|
-
assert_equal %w/--foo/, items
|
212
|
-
end
|
213
|
-
|
214
|
-
test '#parse! removes parsed items' do
|
215
|
-
items = %w/--foo/
|
216
|
-
Slop.new { |opt| opt.on :foo }.parse!(items)
|
217
|
-
assert_empty items
|
218
|
-
end
|
219
|
-
|
220
|
-
test '#parse! does not remove unparsed items with same value as a parsed item' do
|
221
|
-
items = %w/bar --foo bar/
|
222
|
-
Slop.new { |opt| opt.on :foo, 'foo', true }.parse!(items)
|
223
|
-
assert_equal %w/bar/, items
|
85
|
+
assert_equal ['foo'], slop.parse(%w'foo')
|
86
|
+
assert_equal ['foo'], slop.parse!(%w'foo')
|
224
87
|
end
|
225
88
|
|
226
|
-
test
|
227
|
-
|
228
|
-
|
229
|
-
|
89
|
+
test "parse!" do
|
90
|
+
slop = Slop.new { on :foo= }
|
91
|
+
assert_equal [], slop.parse!(%w'--foo bar')
|
92
|
+
slop = Slop.new { on :baz }
|
93
|
+
assert_equal ['etc'], slop.parse!(%w'--baz etc')
|
230
94
|
end
|
231
95
|
|
232
|
-
test
|
233
|
-
|
234
|
-
|
235
|
-
clean_options('-s', '--short', 'short option')
|
236
|
-
)
|
237
|
-
|
238
|
-
assert_equal(
|
239
|
-
[nil, 'long', 'long option only', true, {}],
|
240
|
-
clean_options('--long', 'long option only', true)
|
241
|
-
)
|
242
|
-
|
243
|
-
assert_equal(
|
244
|
-
['S', 'symbol', 'symbolize', false, {}],
|
245
|
-
clean_options(:S, :symbol, 'symbolize')
|
246
|
-
)
|
247
|
-
|
248
|
-
assert_equal(
|
249
|
-
['a', nil, 'alphabetical only', true, {}],
|
250
|
-
clean_options('a', 'alphabetical only', true)
|
251
|
-
)
|
252
|
-
|
253
|
-
assert_equal( # for description-less options
|
254
|
-
[nil, 'optiononly', nil, false, {}],
|
255
|
-
clean_options('--optiononly')
|
256
|
-
)
|
257
|
-
|
258
|
-
assert_equal(
|
259
|
-
['f', 'foo', 'some description', false, {:optional => false, :help => 'BAR'}],
|
260
|
-
clean_options(:f, 'foo BAR', 'some description')
|
261
|
-
)
|
262
|
-
|
263
|
-
assert_equal(
|
264
|
-
[nil, 'bar', nil, false, {:optional => true, :help => '[STUFF]'}],
|
265
|
-
clean_options('bar [STUFF]')
|
266
|
-
)
|
267
|
-
|
268
|
-
assert_equal([nil, 'foo', nil, false, {:as => Array}], clean_options(:foo, Array, false))
|
269
|
-
assert_equal([nil, 'foo', nil, false, {:as => Array}], clean_options(Array, :foo, false))
|
270
|
-
|
271
|
-
assert_equal(['c', nil, nil, true, {}], clean_options(:c, true))
|
272
|
-
assert_equal(['c', nil, nil, false, {}], clean_options(:c, false))
|
96
|
+
test "new() accepts a hash of configuration options" do
|
97
|
+
slop = Slop.new(:foo => :bar)
|
98
|
+
assert_equal :bar, slop.config[:foo]
|
273
99
|
end
|
274
100
|
|
275
|
-
test
|
276
|
-
|
277
|
-
|
278
|
-
|
279
|
-
slop.command(:foo) { }
|
280
|
-
slop.command(:bar) { }
|
281
|
-
slop.parse %w/--name lee --foo/
|
282
|
-
|
283
|
-
assert_equal 'lee', slop[:name]
|
284
|
-
assert_equal 'lee', slop[:n]
|
285
|
-
|
286
|
-
assert_equal true, slop[:foo]
|
287
|
-
assert_kind_of Slop, slop[:bar]
|
288
|
-
|
289
|
-
assert_nil slop[:baz]
|
290
|
-
end
|
291
|
-
|
292
|
-
test 'arguments ending ? test for option existance' do
|
293
|
-
slop = Slop.new
|
294
|
-
slop.opt :v, :verbose
|
295
|
-
slop.opt :d, :debug
|
296
|
-
slop.parse %w/--verbose/
|
297
|
-
|
298
|
-
assert slop[:verbose]
|
299
|
-
assert slop.verbose?
|
300
|
-
|
301
|
-
refute slop[:debug]
|
302
|
-
refute slop.debug?
|
303
|
-
end
|
304
|
-
|
305
|
-
test 'options are present' do
|
306
|
-
opts = Slop.new do
|
307
|
-
on :f, 'foo-bar'
|
308
|
-
on :b, 'bar-baz'
|
309
|
-
on :h, :optional => true
|
101
|
+
test "defaulting to ARGV" do
|
102
|
+
temp_argv(%w/--name lee/) do
|
103
|
+
opts = Slop.parse { on :name= }
|
104
|
+
assert_equal 'lee', opts[:name]
|
310
105
|
end
|
311
|
-
opts.parse %w/--foo-bar -h/
|
312
|
-
|
313
|
-
assert opts.present?('foo-bar')
|
314
|
-
refute opts.present?('bar-baz')
|
315
|
-
refute opts.present?('foo-bar', 'bar-baz')
|
316
|
-
assert opts.present?(:h)
|
317
106
|
end
|
318
107
|
|
319
|
-
test
|
320
|
-
slop = Slop.new
|
321
|
-
slop.
|
322
|
-
|
323
|
-
|
324
|
-
assert_raises(Slop::MissingArgumentError, /name/) { slop.parse %w/--name/ }
|
325
|
-
assert slop.parse %w/--name 'foo'/
|
326
|
-
end
|
327
|
-
|
328
|
-
test 'returning a hash of options' do
|
329
|
-
slop = Slop.new
|
330
|
-
slop.opt :name, true
|
331
|
-
slop.opt :version
|
332
|
-
slop.opt :V, :verbose, :default => false
|
333
|
-
slop.parse %w/--name lee --version/
|
334
|
-
|
335
|
-
assert_equal({'name' => 'lee', 'version' => true, 'verbose' => false}, slop.to_hash(false))
|
336
|
-
assert_equal({:name => 'lee', :version => true, :verbose => false}, slop.to_hash(true))
|
108
|
+
test "automatically adding the help option" do
|
109
|
+
slop = Slop.new :help => true
|
110
|
+
refute_empty slop.options
|
111
|
+
assert_equal 'Display this help message.', slop.options.first.description
|
337
112
|
end
|
338
113
|
|
339
|
-
test
|
340
|
-
slop = Slop.new
|
341
|
-
slop.
|
342
|
-
slop.opt :f, :foo
|
114
|
+
test ":arguments and :optional_arguments config options" do
|
115
|
+
slop = Slop.new(:arguments => true) { on :foo }
|
116
|
+
assert slop.fetch_option(:foo).expects_argument?
|
343
117
|
|
344
|
-
|
345
|
-
slop.
|
118
|
+
slop = Slop.new(:optional_arguments => true) { on :foo }
|
119
|
+
assert slop.fetch_option(:foo).accepts_optional_argument?
|
346
120
|
end
|
347
121
|
|
348
|
-
test
|
349
|
-
|
350
|
-
|
351
|
-
|
352
|
-
|
353
|
-
assert_kind_of Slop::Option, slop.options[:foo]
|
354
|
-
assert_equal "bar", slop[:foo]
|
355
|
-
assert_equal "bar", slop['foo']
|
356
|
-
assert_kind_of Slop::Option, slop.options[0]
|
357
|
-
assert_nil slop.options['0']
|
122
|
+
test "yielding non-options when a block is passed to parse()" do
|
123
|
+
items = []
|
124
|
+
opts = Slop.new { on :name= }
|
125
|
+
opts.parse(%w/--name lee a b c/) { |v| items << v }
|
126
|
+
assert_equal ['a', 'b', 'c'], items
|
358
127
|
end
|
359
128
|
|
360
|
-
test
|
361
|
-
|
362
|
-
|
363
|
-
|
364
|
-
|
129
|
+
test "on empty callback" do
|
130
|
+
opts = Slop.new
|
131
|
+
foo = nil
|
132
|
+
opts.add_callback(:empty) { foo = "bar" }
|
133
|
+
opts.parse []
|
134
|
+
assert_equal "bar", foo
|
365
135
|
end
|
366
136
|
|
367
|
-
test
|
368
|
-
name = nil
|
137
|
+
test "on no_options callback" do
|
369
138
|
opts = Slop.new
|
370
|
-
|
371
|
-
opts.
|
372
|
-
|
139
|
+
foo = nil
|
140
|
+
opts.add_callback(:no_options) { foo = "bar" }
|
141
|
+
opts.parse %w( --foo --bar etc hello )
|
142
|
+
assert_equal "bar", foo
|
373
143
|
end
|
374
144
|
|
375
|
-
test
|
376
|
-
|
377
|
-
|
378
|
-
|
379
|
-
assert_raises(Slop::InvalidOptionError, /--foo/) { strict.parse %w/--foo/ }
|
380
|
-
assert totallynotstrict.parse %w/--foo/
|
145
|
+
test "to_hash()" do
|
146
|
+
opts = Slop.new { on :foo=; on :bar }
|
147
|
+
opts.parse(%w'--foo hello --bar')
|
148
|
+
assert_equal({ :foo => 'hello', :bar => nil }, opts.to_hash)
|
381
149
|
end
|
382
150
|
|
383
|
-
test
|
384
|
-
|
385
|
-
|
386
|
-
|
387
|
-
assert_raises(Slop::InvalidOptionError, /--foo/) { strict.parse %w/--foo --name nelson/ }
|
388
|
-
assert_equal 'nelson', strict[:name]
|
151
|
+
test "missing() returning all missing option keys" do
|
152
|
+
opts = Slop.new { on :foo; on :bar }
|
153
|
+
opts.parse %w'--foo'
|
154
|
+
assert_equal ['bar'], opts.missing
|
389
155
|
end
|
390
156
|
|
391
|
-
test
|
392
|
-
|
393
|
-
|
394
|
-
|
395
|
-
|
396
|
-
|
397
|
-
|
398
|
-
assert_equal 'bar', slop[:shortpass]
|
157
|
+
test "autocreating options" do
|
158
|
+
opts = Slop.new :autocreate => true
|
159
|
+
opts.parse %w[ --foo bar --baz ]
|
160
|
+
assert opts.fetch_option(:foo).expects_argument?
|
161
|
+
assert opts.fetch_option(:foo).autocreated?
|
162
|
+
assert_equal 'bar', opts.fetch_option(:foo).value
|
163
|
+
refute opts.fetch_option(:baz).expects_argument?
|
399
164
|
end
|
400
165
|
|
401
|
-
test
|
402
|
-
|
403
|
-
|
404
|
-
slop.opt :v, :verbose, :default => true
|
405
|
-
slop.parse %w/--no-debug --no-verbose --no-nothing/
|
406
|
-
|
407
|
-
refute slop.verbose?
|
408
|
-
refute slop.debug?
|
409
|
-
refute slop[:verbose]
|
410
|
-
refute slop[:debug]
|
166
|
+
test "raising an InvalidArgumentError when the argument doesn't match" do
|
167
|
+
opts = Slop.new { on :foo=, :match => /^[a-z]+$/ }
|
168
|
+
assert_raises(Slop::InvalidArgumentError) { opts.parse %w' --foo b4r '}
|
411
169
|
end
|
412
170
|
|
413
|
-
test
|
414
|
-
|
415
|
-
|
416
|
-
slop.parse %w/--name=lee/
|
417
|
-
|
418
|
-
assert_equal 'lee', slop[:name]
|
419
|
-
assert slop.name?
|
171
|
+
test "raising a MissingArgumentError when the option expects an argument" do
|
172
|
+
opts = Slop.new { on :foo= }
|
173
|
+
assert_raises(Slop::MissingArgumentError) { opts.parse %w' --foo '}
|
420
174
|
end
|
421
175
|
|
422
|
-
test
|
423
|
-
|
424
|
-
assert_raises(Slop::
|
176
|
+
test "raising a MissingOptionError when a required option is missing" do
|
177
|
+
opts = Slop.new { on :foo, :required => true }
|
178
|
+
assert_raises(Slop::MissingOptionError) { opts.parse %w'' }
|
425
179
|
end
|
426
180
|
|
427
|
-
test
|
428
|
-
|
429
|
-
|
430
|
-
|
181
|
+
test "raising InvalidOptionError when strict mode is enabled and an unknown option appears" do
|
182
|
+
opts = Slop.new :strict => true
|
183
|
+
assert_raises(Slop::InvalidOptionError) { opts.parse %w'--foo' }
|
184
|
+
assert_raises(Slop::InvalidOptionError) { opts.parse %w'-fabc' }
|
431
185
|
end
|
432
186
|
|
433
|
-
test
|
434
|
-
|
435
|
-
|
436
|
-
|
437
|
-
|
438
|
-
|
439
|
-
slop.parse %w( --foo )
|
440
|
-
assert_equal true, slop.foo?
|
187
|
+
test "multiple_switches is enabled by default" do
|
188
|
+
opts = Slop.new { on :f; on :b }
|
189
|
+
opts.parse %w[ -fb ]
|
190
|
+
assert opts.present?(:f)
|
191
|
+
assert opts.present?(:b)
|
441
192
|
end
|
442
193
|
|
443
|
-
test
|
444
|
-
|
445
|
-
|
446
|
-
|
447
|
-
begin
|
448
|
-
slop.parse %w/--help/
|
449
|
-
rescue SystemExit
|
450
|
-
end
|
451
|
-
assert io.string.include? 'something fooey'
|
194
|
+
test "multiple_switches disabled" do
|
195
|
+
opts = Slop.new(:multiple_switches => false) { on :f= }
|
196
|
+
opts.parse %w[ -fabc123 ]
|
197
|
+
assert_equal 'abc123', opts[:f]
|
452
198
|
end
|
453
199
|
|
454
|
-
test
|
455
|
-
|
456
|
-
|
457
|
-
assert_raises(SystemExit) { opts.parse %w/--help/ }
|
200
|
+
test "setting/getting the banner" do
|
201
|
+
opts = Slop.new :banner => 'foo'
|
202
|
+
assert_equal 'foo', opts.banner
|
458
203
|
|
459
|
-
opts = Slop.new
|
460
|
-
|
461
|
-
|
204
|
+
opts = Slop.new
|
205
|
+
opts.banner 'foo'
|
206
|
+
assert_equal 'foo', opts.banner
|
462
207
|
|
463
|
-
|
464
|
-
opts =
|
465
|
-
|
466
|
-
opts.parse %w/--NAME lee/
|
467
|
-
assert_equal 'lee', opts[:name]
|
208
|
+
opts = Slop.new
|
209
|
+
opts.banner = 'foo'
|
210
|
+
assert_equal 'foo', opts.banner
|
468
211
|
end
|
469
212
|
|
470
|
-
test
|
471
|
-
opts = Slop.new
|
472
|
-
|
473
|
-
|
474
|
-
opts
|
475
|
-
|
476
|
-
assert opts.hello?
|
477
|
-
assert opts.foo?
|
478
|
-
assert_equal 'bar', opts[:foo]
|
479
|
-
assert opts.a?
|
480
|
-
assert_equal 'ipsum', opts[:lorem]
|
213
|
+
test "get/[] fetching an options argument value" do
|
214
|
+
opts = Slop.new { on :foo=; on :bar; on :baz }
|
215
|
+
opts.parse %w' --foo hello --bar '
|
216
|
+
assert_equal 'hello', opts[:foo]
|
217
|
+
assert_nil opts[:bar]
|
218
|
+
assert_nil opts[:baz]
|
481
219
|
end
|
482
220
|
|
483
|
-
test
|
484
|
-
opts = Slop.new
|
485
|
-
|
486
|
-
|
487
|
-
opts.
|
488
|
-
|
489
|
-
assert_equal %w/foo bar etc/, opts[:a]
|
221
|
+
test "checking for an options presence" do
|
222
|
+
opts = Slop.new { on :foo; on :bar }
|
223
|
+
opts.parse %w' --foo '
|
224
|
+
assert opts.present?(:foo)
|
225
|
+
refute opts.present?(:bar)
|
490
226
|
end
|
491
227
|
|
492
|
-
test
|
493
|
-
opts = Slop.new
|
494
|
-
opts.parse %w
|
228
|
+
test "ignoring case" do
|
229
|
+
opts = Slop.new { on :foo }
|
230
|
+
opts.parse %w' --FOO bar '
|
231
|
+
assert_nil opts[:foo]
|
495
232
|
|
233
|
+
opts = Slop.new(:ignore_case => true) { on :foo= }
|
234
|
+
opts.parse %w' --FOO bar '
|
496
235
|
assert_equal 'bar', opts[:foo]
|
497
236
|
end
|
498
237
|
|
499
|
-
test
|
500
|
-
opts = Slop.new do
|
501
|
-
on 'f', 'foo BAR'
|
502
|
-
on 'bar [HELLO]'
|
503
|
-
end
|
504
|
-
|
505
|
-
assert opts.options[:foo].expects_argument?
|
506
|
-
assert opts.options[:bar].accepts_optional_argument?
|
507
|
-
|
508
|
-
assert_equal ' -f, --foo BAR ', opts.options[:foo].to_s
|
509
|
-
assert_equal ' --bar [HELLO] ', opts.options[:bar].to_s
|
510
|
-
end
|
511
|
-
|
512
|
-
test 'not parsing options if after --' do
|
513
|
-
args = %w[ foo bar -- --foo bar ]
|
514
|
-
opts = Slop.parse!(args) do
|
515
|
-
on :foo, true
|
516
|
-
end
|
517
|
-
|
518
|
-
assert_equal %w[ foo bar --foo bar ], args
|
519
|
-
end
|
520
|
-
|
521
|
-
test 'inline classes' do
|
522
|
-
opts = Slop.new do
|
523
|
-
on :foo, Array, true
|
524
|
-
on Symbol, :bar, true
|
525
|
-
end
|
526
|
-
opts.parse %w/--foo one,two --bar hello/
|
527
|
-
|
528
|
-
assert_equal %w[one two], opts[:foo]
|
529
|
-
assert_equal :hello, opts[:bar]
|
530
|
-
end
|
531
|
-
|
532
|
-
test 'wrap and indent' do
|
533
|
-
slop = Slop.new
|
534
|
-
|
535
|
-
assert_equal(
|
536
|
-
"Lorem ipsum dolor sit amet, consectetur\n" +
|
537
|
-
"adipisicing elit, sed do eiusmod tempor\n" +
|
538
|
-
"incididunt ut labore et dolore magna\n" +
|
539
|
-
"aliqua.",
|
540
|
-
slop.send(:wrap_and_indent, "Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.", 40, 0))
|
541
|
-
|
542
|
-
assert_equal(
|
543
|
-
" Lorem ipsum dolor sit amet,\n" +
|
544
|
-
" consectetur adipisicing elit, sed\n" +
|
545
|
-
" do eiusmod tempor incididunt ut\n" +
|
546
|
-
" labore et dolore magna aliqua.",
|
547
|
-
slop.send(:wrap_and_indent, "Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.", 36, 4))
|
548
|
-
end
|
549
|
-
|
550
|
-
test 'to_struct' do
|
551
|
-
assert_nil Slop.new.to_struct
|
552
|
-
|
553
|
-
slop = Slop.new { on :a, true }
|
554
|
-
slop.parse %w[ -a foo -b ]
|
555
|
-
struct = slop.to_struct
|
556
|
-
|
557
|
-
assert_equal 'foo', struct.a
|
558
|
-
assert_kind_of Struct, struct
|
559
|
-
assert_raises(NoMethodError) { struct.b }
|
560
|
-
|
561
|
-
pstruct = slop.to_struct('Foo')
|
562
|
-
assert_kind_of Struct::Foo, pstruct
|
563
|
-
end
|
564
|
-
|
565
|
-
test 'returning missing options' do
|
566
|
-
slop = Slop.new { on :a; on :b, :bar; on :c; }
|
567
|
-
slop.parse %w[ -a ]
|
568
|
-
|
569
|
-
assert_equal %w[ bar c ], slop.missing
|
570
|
-
end
|
571
|
-
|
572
|
-
test 'parsing an optspec and building options' do
|
238
|
+
test "parsing an optspec and building options" do
|
573
239
|
optspec = <<-SPEC
|
574
240
|
ruby foo.rb [options]
|
575
241
|
--
|
576
242
|
v,verbose enable verbose mode
|
577
243
|
q,quiet enable quiet mode
|
578
|
-
debug enable debug mode
|
579
|
-
H enable hax mode (srsly)
|
580
244
|
n,name= set your name
|
581
|
-
|
245
|
+
p,pass=? set your password
|
582
246
|
SPEC
|
583
247
|
opts = Slop.optspec(optspec.gsub(/^\s+/, ''))
|
584
248
|
opts.parse %w[ --verbose --name Lee ]
|
585
249
|
|
586
250
|
assert_equal 'Lee', opts[:name]
|
587
|
-
assert opts.verbose
|
588
|
-
assert_equal 'enable quiet mode', opts.
|
251
|
+
assert opts.present?(:verbose)
|
252
|
+
assert_equal 'enable quiet mode', opts.fetch_option(:quiet).description
|
253
|
+
assert opts.fetch_option(:pass).accepts_optional_argument?
|
589
254
|
end
|
590
255
|
|
591
|
-
test "negative integers
|
256
|
+
test "ensure negative integers are not processed as options" do
|
592
257
|
items = %w(-1)
|
593
258
|
Slop.parse!(items)
|
594
259
|
assert_equal %w(-1), items
|
595
260
|
end
|
596
261
|
|
597
|
-
test "
|
598
|
-
opts = Slop.new
|
599
|
-
|
600
|
-
|
262
|
+
test "separators" do
|
263
|
+
opts = Slop.new do
|
264
|
+
on :foo
|
265
|
+
separator "hello"
|
266
|
+
on :bar
|
267
|
+
end
|
268
|
+
assert_equal " --foo \nhello\n --bar ", opts.help
|
269
|
+
end
|
270
|
+
|
271
|
+
test "printing help with :help => true" do
|
272
|
+
temp_stderr do |string|
|
273
|
+
opts = Slop.new(:help => true)
|
274
|
+
opts.parse %w( --help )
|
275
|
+
assert_equal " -h, --help Display this help message.\n", string
|
276
|
+
end
|
601
277
|
end
|
602
|
-
|
278
|
+
|
279
|
+
end
|