optimist_xl 3.1.1 → 3.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: d15a0ddf0d2205266ff1df22f86c3e96c9bcccfe449394840194269ff35de564
4
- data.tar.gz: b84c5a820184de6941b54054d7ab3786be5c4b75b5e934d99021e21838cb1355
3
+ metadata.gz: 4f71228547d0536054a7e674aa46cedde06fc46ea310e46076f4beb19585f9f5
4
+ data.tar.gz: 948058a857b01c3939866fbb5b484131f5d104083c4ca4800c7072ce8eba8de7
5
5
  SHA512:
6
- metadata.gz: fbe733a8b0f74918aef616ed3a2d1d5a6f9ff7cc414de871f8bdfb33aba1186899f4d25c8e66c08bfbfe3dc2dcc87514e7d2b2e3f1859d1b96a4bddc773c2c77
7
- data.tar.gz: 8de3c39ad1356af6b5e599127b0afefd78e4ccec11f5ec06b801eac94ad631a5e6fa1c266f64e94c2a0b8c11a137a6978409767c2d657266eb0643a51b688541
6
+ metadata.gz: f8f594f3eb28c433b9b34b81ae452060d0cd2f5cb1302b6167da58358e1c2cbf3749792918ce1f96da6c02112fb9f4f30ee85c00eb38a7cfd46372387dd37446
7
+ data.tar.gz: 6fcabc7018c7660aa0fdc3c79d1d020a0a352b76fe22655c9d02bed4eb8556ec40503e6e349ba2bd968504e3cedf13ca54d4c9f8598b59f06c25121579f1b328
@@ -1,13 +1,14 @@
1
1
  language: ruby
2
- sudo: false
2
+ cache: bundler
3
3
  rvm:
4
- - "2.2"
5
- - "2.3.4"
6
- - "2.5.1"
7
- - "2.6.3"
8
- - "2.7.0"
4
+ - 2.2
5
+ - 2.3
6
+ - 2.4
7
+ - 2.5
8
+ - 2.6
9
+ - 2.7
9
10
  - jruby-head
10
11
  matrix:
11
12
  allow_failures:
12
- - rvm: jruby-head
13
- fast_finish: true
13
+ # - rvm: jruby-head
14
+ # fast_finish: true
@@ -1,4 +1,9 @@
1
- == [3.1.1] / 2020-01-20
1
+ # [3.2.0] / 2020-03-02
2
+
3
+ * Added alternate-named long options using `:alt`
4
+ * Added alternate-named short-options by allowing `:short` to take an Array.
5
+ * Refactored some short/long handling code into ShortNames and LongNames classes.
6
+ # [3.1.1] / 2020-01-20
2
7
 
3
8
  * The gem has been forked from optimist to optimist_xl
4
9
  * Added "native" subcommands support
@@ -7,11 +12,11 @@
7
12
  * ability to globally prevent short-options by default
8
13
  * permitted and permitted_response keywords now available
9
14
 
10
- == [3.0.0] / 2018-08-24
15
+ # [3.0.0] / 2018-08-24
11
16
 
12
17
  * The gem has been officially renamed to optimist
13
18
 
14
- == [2.1.3] / 2018-07-05
19
+ # [2.1.3] / 2018-07-05
15
20
 
16
21
  * Refactor each option type into subclasses of Option. Define a registry for the registration of each option. This makes the code more modular and facilitates extension by allowing additional Option subclasses. (thanks @clxy)
17
22
  * Fixed implementation of ignore_invalid_options. (thanks @metcalf)
@@ -20,18 +25,18 @@
20
25
  * fixed default (thanks @nanobowers)
21
26
  * Change from ruby license to MIT license in the code.
22
27
 
23
- == [2.1.2] / 2015-03-10
28
+ # [2.1.2] / 2015-03-10
24
29
  * loosen mime-types requirements (for better ruby 1.8.7 support)
25
30
  * use io/console gem instead of curses (for better jruby support)
26
31
  * fix parsing bug when chronic gem is not available
27
32
  * allow default array to be empty if a type is specified
28
33
  * better specified license and better spec coverage
29
34
 
30
- == [2.1.1] / 2015-01-03
35
+ # [2.1.1] / 2015-01-03
31
36
  * Remove curses as a hard dependency. It is optional. This can leverage the gem if it is present.
32
37
  * Fix ruby -w warnings
33
38
 
34
- == 2.1.0 / 2015-01-02
39
+ # 2.1.0 / 2015-01-02
35
40
  * Integer parser now supports underscore separator.
36
41
  * Add Parser#usage and Parser#synopsis commands for creating a standard banner
37
42
  message. Using Parser#banner directly will override both of those.
@@ -46,7 +51,7 @@
46
51
  * Fix handling of newlines inside descriptions
47
52
  * Documentation and other fixes.
48
53
 
49
- == 2.0 / 2012-08-11
54
+ # 2.0 / 2012-08-11
50
55
  * Change flag logic: --no-X will always be false, and --X will always be true,
51
56
  regardless of default.
52
57
  * For flags that default to true, display --no-X instead of --X in the help
@@ -55,55 +60,55 @@
55
60
  * Update Rakefile to 1.9
56
61
  * Minor documentation fixes
57
62
 
58
- == 1.16.2 / 2010-04-06
63
+ # 1.16.2 / 2010-04-06
59
64
  * Bugfix in Optimist::options. Thanks to Brian C. Thomas for pointing it out.
60
65
 
61
- == 1.16.1 / 2010-04-05
66
+ # 1.16.1 / 2010-04-05
62
67
  * Bugfix in Optimist::die method introduced in last release.
63
68
 
64
- == 1.16 / 2010-04-01
69
+ # 1.16 / 2010-04-01
65
70
  * Add Optimist::with_standard_exception_handling method for easing the use of Parser directly.
66
71
  * Handle scientific notation in float arguments, thanks to Will Fitzgerald.
67
72
  * Drop hoe dependency.
68
73
 
69
- == 1.15 / 2009-09-30
74
+ # 1.15 / 2009-09-30
70
75
  * Don't raise an exception when out of short arguments (thanks to Rafael
71
76
  Sevilla for pointing out how dumb this behavior was).
72
77
 
73
- == 1.14 / 2009-06-19
78
+ # 1.14 / 2009-06-19
74
79
  * Make :multi arguments default to [], not nil, when not set on the commandline.
75
80
  * Minor commenting and error message improvements
76
81
 
77
- == 1.13 / 2009-03-16
82
+ # 1.13 / 2009-03-16
78
83
  * Fix parsing of "--longarg=<value with spaces>".
79
84
 
80
- == 1.12 / 2009-01-30
85
+ # 1.12 / 2009-01-30
81
86
  * Fix some unit test failures in the last release. Should be more careful.
82
87
  * Make default short options only be assigned *after* all user-specified
83
88
  short options. Now there's a little less juggling to do when you just
84
89
  want to specify a few short options.
85
90
 
86
- == 1.11 / 2009-01-29
91
+ # 1.11 / 2009-01-29
87
92
  * Set <opt>_given keys in the results hash for options that were specified
88
93
  on the commandline.
89
94
 
90
- == 1.10.2 / 2008-10-23
95
+ # 1.10.2 / 2008-10-23
91
96
  * No longer try `stty size` for screen size detection. Just use curses, and
92
97
  screen users will have to deal with the screen clearing.
93
98
 
94
- == 1.10.1 / 2008-10-22
99
+ # 1.10.1 / 2008-10-22
95
100
  * Options hash now responds to method calls as well as standard hash lookup.
96
101
  * Default values for multi-occurrence parameters now autoboxed.
97
102
  * The relationship between multi-value, multi-occurrence, and default values
98
103
  improved and explained.
99
104
  * Documentation improvements.
100
105
 
101
- == 1.10 / 2008-10-21
106
+ # 1.10 / 2008-10-21
102
107
  * Added :io type for parameters that point to IO streams (filenames, URIs, etc).
103
108
  * For screen size detection, first try `stty size` before loading Curses.
104
109
  * Improved documentation.
105
110
 
106
- == 1.9 / 2008-08-20
111
+ # 1.9 / 2008-08-20
107
112
  * Added 'stop_on_unknown' command to stop parsing on any unknown argument.
108
113
  This is useful for handling sub-commands when you don't know the entire
109
114
  set of commands up front. (E.g. if the initial arguments can change it.)
@@ -112,51 +117,51 @@
112
117
  * Added :ints, :strings, :doubles, and :floats option types, which can take
113
118
  multiple arguments.
114
119
 
115
- == 1.8.2 / 2008-06-25
120
+ # 1.8.2 / 2008-06-25
116
121
  * Bugfix for #conflicts and #depends error messages
117
122
 
118
- == 1.8.1 / 2008-06-24
123
+ # 1.8.1 / 2008-06-24
119
124
  * Bugfix for short option autocreation
120
125
  * More aggressive documentation
121
126
 
122
- == 1.8 / 2008-06-16
127
+ # 1.8 / 2008-06-16
123
128
  * Sub-command support via Parser#stop_on
124
129
 
125
- == 1.7.2 / 2008-01-16
130
+ # 1.7.2 / 2008-01-16
126
131
  * Ruby 1.9-ify. Apparently this means replacing :'s with ;'s.
127
132
 
128
- == 1.7.1 / 2008-01-07
133
+ # 1.7.1 / 2008-01-07
129
134
  * Documentation improvements
130
135
 
131
- == 1.7 / 2007-06-17
136
+ # 1.7 / 2007-06-17
132
137
  * Fix incorrect error message for multiple missing required arguments
133
138
  (thanks to Neill Zero)
134
139
 
135
- == 1.6 / 2007-04-01
140
+ # 1.6 / 2007-04-01
136
141
  * Don't attempt curses screen-width magic unless running on a terminal.
137
142
 
138
- == 1.5 / 2007-03-31
143
+ # 1.5 / 2007-03-31
139
144
  * --help and --version do the right thing even if the rest of the
140
145
  command line is incorrect.
141
146
  * Added #conflicts and #depends to model dependencies and exclusivity
142
147
  between arguments.
143
148
  * Minor bugfixes.
144
149
 
145
- == 1.4 / 2007-03-26
150
+ # 1.4 / 2007-03-26
146
151
  * Disable short options with :short => :none.
147
152
  * Minor bugfixes and error message improvements.
148
153
 
149
- == 1.3 / 2007-01-31
154
+ # 1.3 / 2007-01-31
150
155
  * Wrap at (screen width - 1) instead of screen width.
151
156
  * User can override --help and --version.
152
157
  * Bugfix in handling of -v and -h.
153
158
  * More tests to confirm the above.
154
159
 
155
- == 1.2 / 2007-01-31
160
+ # 1.2 / 2007-01-31
156
161
  * Minor documentation tweaks.
157
162
  * Removed hoe dependency.
158
163
 
159
- == 1.1 / 2007-01-30
164
+ # 1.1 / 2007-01-30
160
165
  * Optimist::options now passes any arguments as block arguments. Since
161
166
  instance variables are not properly captured by the block, this
162
167
  makes it slightly less noisy to pass them in as local variables.
@@ -169,7 +174,7 @@
169
174
  in the help text.
170
175
  * Slightly more indicative formatting for parameterized arguments.
171
176
 
172
- == 1.0 / 2007-01-29
177
+ # 1.0 / 2007-01-29
173
178
  * Initial release.
174
179
 
175
180
  [2.1.3]: https://github.com/ManageIQ/optimist/compare/v2.1.2...v2.1.3
data/LICENSE ADDED
@@ -0,0 +1,25 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2008-2014 William Morgan (http://masanjin.net/).
4
+
5
+ Copyright (c) 2014 Red Hat, Inc.
6
+
7
+ Copyright (c) 2019 Ben Bowers
8
+
9
+ Permission is hereby granted, free of charge, to any person obtaining a copy
10
+ of this software and associated documentation files (the "Software"), to deal
11
+ in the Software without restriction, including without limitation the rights
12
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
13
+ copies of the Software, and to permit persons to whom the Software is
14
+ furnished to do so, subject to the following conditions:
15
+
16
+ The above copyright notice and this permission notice shall be included in all
17
+ copies or substantial portions of the Software.
18
+
19
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
22
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
25
+ SOFTWARE.
data/README.md CHANGED
@@ -17,15 +17,19 @@ One line of code per option is all you need to write. For that, you get a nice
17
17
  automatically-generated help page, robust option parsing, and sensible defaults
18
18
  for everything you don't specify.
19
19
 
20
+ This code is a feature-fork of Optimist: https://github.com/ManageIQ/optimist
21
+
22
+ See the **Extended Features** section below for the differences/enhancements
23
+
20
24
  ## Features
21
25
 
22
- - Dirt-simple usage.
26
+ - Simple usage.
23
27
  - Sensible defaults. No tweaking necessary, much tweaking possible.
24
28
  - Support for long options, short options, subcommands, and automatic type validation and
25
29
  conversion.
26
30
  - Automatic help message generation, wrapped to current screen width.
27
31
 
28
- ## Extended features
32
+ ## Extended Features
29
33
 
30
34
  ### Parser Settings
31
35
  - Automatic suggestions whens incorrect options are given
@@ -37,16 +41,30 @@ for everything you don't specify.
37
41
 
38
42
  ### Option Settings
39
43
 
44
+ #### Permitted
45
+
40
46
  Permitted options allow specifying valid choices for an option using lists, ranges or regexp's
41
47
  - `permitted:` to specify a allow lists, ranges or regexp filtering of options.
42
48
  - `permitted_response:` can be added to provide more explicit output when incorrect choices are given.
43
49
  - see [example](examples/permitted.rb)
44
50
  - concept and code via @akhoury6
45
51
 
52
+ #### Alternate named options
53
+
54
+ Short options can now take be provided as an Array of list of alternate short-option characters.
55
+ - `opt :cat, 'desc', short: ['c', 't']`
56
+ - Previously `short:` only accepted a single character.
57
+
58
+ Long options can be given alternate names using `alt:`
59
+ - `opt :length, 'desc', alt: ['size']`
60
+ - Note that `long: 'othername'` still exists to _override_ the named option and can be used in addition to the alt names.
61
+
62
+ See [example](examples/alt_names.rb)
63
+
46
64
  ### Subcommands
47
- "Native" subcommand support
48
- - see [example](examples/subcommands.rb)
49
- - ideas borrowed from https://github.com/jwliechty/trollop-subcommands
65
+ "Native" subcommand support - similar to sub-commands in Git.
66
+ - See [example](examples/subcommands.rb)
67
+ - Ideas borrowed from https://github.com/jwliechty/trollop-subcommands
50
68
 
51
69
  ## Requirements
52
70
 
@@ -0,0 +1,15 @@
1
+ #!/usr/bin/env ruby
2
+ require_relative '../lib/optimist_xl'
3
+
4
+ opts = OptimistXL::options do
5
+ # 'short:' can now take more than one short-option character
6
+ # you can specify 'short:' as a string/symbol or an array of strings/symbols
7
+ # 'alt:' adds additional long-opt choices (over the original name or the long: name)
8
+ # you can specify 'alt:' as a string/symbol or an array of strings/symbols.
9
+ #
10
+ opt :concat, 'concatenate flag', short: ['-C', 'A'], alt: ['cat', '--append']
11
+ opt :array_len, 'set Array length', long: 'size', alt: 'length', type: Integer
12
+ end
13
+
14
+ p opts
15
+
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env ruby
2
2
  require_relative '../lib/optimist_xl'
3
3
 
4
- opts = OptimistXL::options do
4
+ OptimistXL::options do
5
5
  synopsis "Overall synopsis of this program"
6
6
  version "cool-script v0.3 (code-name: apple-cake)"
7
7
  opt :juice, "use juice"
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env ruby
2
2
  require_relative '../lib/optimist_xl'
3
3
 
4
- opts = OptimistXL::options do
4
+ OptimistXL::options do
5
5
  synopsis "Overall synopsis of this program"
6
6
  version "cool-script v0.3.1 (code-name: apple-cake)"
7
7
  banner "My Banner"
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env ruby
2
2
  require_relative '../lib/optimist_xl'
3
3
 
4
- opts = OptimistXL::options do
4
+ OptimistXL::options do
5
5
  version "cool-script v0.3.2 (code-name: apple-cake)"
6
6
  banner self.version ## print out the version in the banner
7
7
  banner "drinks"
File without changes
File without changes
File without changes
File without changes
@@ -9,7 +9,7 @@ require 'date'
9
9
  module OptimistXL
10
10
  # note: this is duplicated in gemspec
11
11
  # please change over there too
12
- VERSION = "3.1.1"
12
+ VERSION = "3.2.0"
13
13
 
14
14
  ## Thrown by Parser in the event of a commandline error. Not needed if
15
15
  ## you're using the OptimistXL::options entry.
@@ -76,8 +76,6 @@ class Parser
76
76
  return @registry[lookup].new
77
77
  end
78
78
 
79
- INVALID_SHORT_ARG_REGEX = /[\d-]/ #:nodoc:
80
-
81
79
  ## The values from the commandline that were not interpreted by #parse.
82
80
  attr_reader :leftovers
83
81
 
@@ -174,11 +172,18 @@ class Parser
174
172
  o = Option.create(name, desc, opts)
175
173
 
176
174
  raise ArgumentError, "you already have an argument named '#{name}'" if @specs.member? o.name
177
- raise ArgumentError, "long option name #{o.long.inspect} is already taken; please specify a (different) :long" if @long[o.long]
178
- raise ArgumentError, "short option name #{o.short.inspect} is already taken; please specify a (different) :short" if @short[o.short]
179
- raise ArgumentError, "permitted values for option #{o.long.inspect} must be either nil, Range, Regexp or an Array;" unless o.permitted_type_valid?
180
- @long[o.long] = o.name
181
- @short[o.short] = o.name if o.short?
175
+ o.long.names.each do |lng|
176
+ raise ArgumentError, "long option name #{lng.inspect} is already taken; please specify a (different) :long/:alt" if @long[lng]
177
+ @long[lng] = o.name
178
+ end
179
+
180
+ raise ArgumentError, "permitted values for option #{o.long.long.inspect} must be either nil, Range, Regexp or an Array;" unless o.permitted_type_valid?
181
+
182
+ o.short.chars.each do |short|
183
+ raise ArgumentError, "short option name #{short.inspect} is already taken; please specify a (different) :short" if @short[short]
184
+ @short[short] = o.name
185
+ end
186
+
182
187
  @specs[o.name] = o
183
188
  @order << [:opt, o.name]
184
189
  end
@@ -429,7 +434,7 @@ class Parser
429
434
  end
430
435
  end
431
436
 
432
- required.each do |sym, val|
437
+ required.each do |sym, _val|
433
438
  raise CommandlineError, "option --#{@specs[sym].long} must be specified" unless given_args.include? sym
434
439
  end
435
440
 
@@ -586,7 +591,7 @@ class Parser
586
591
  exit(error_code || -1)
587
592
  end
588
593
 
589
- private
594
+ private
590
595
 
591
596
  ## yield successive arg, parameter pairs
592
597
  def each_arg(args)
@@ -679,11 +684,11 @@ private
679
684
  def resolve_default_short_options!
680
685
  @order.each do |type, name|
681
686
  opts = @specs[name]
682
- next if type != :opt || opts.short
687
+ next if type != :opt || opts.doesnt_need_autogen_short
683
688
 
684
- c = opts.long.split(//).find { |d| d !~ INVALID_SHORT_ARG_REGEX && !@short.member?(d) }
689
+ c = opts.long.long.split(//).find { |d| d !~ OptimistXL::ShortNames::INVALID_ARG_REGEX && !@short.member?(d) }
685
690
  if c # found a character to use
686
- opts.short = c
691
+ opts.short.add c
687
692
  @short[c] = name
688
693
  end
689
694
  end
@@ -757,14 +762,84 @@ class SubcommandParser < Parser
757
762
 
758
763
  end
759
764
 
765
+ class LongNames
766
+ def initialize
767
+ @truename = nil
768
+ @long = nil
769
+ @alts = []
770
+ end
771
+
772
+ def make_valid(lopt)
773
+ return nil if lopt.nil?
774
+ case lopt.to_s
775
+ when /^--([^-].*)$/ then $1
776
+ when /^[^-]/ then lopt.to_s
777
+ else raise ArgumentError, "invalid long option name #{lopt.inspect}"
778
+ end
779
+ end
780
+
781
+ def set(name, lopt, alts)
782
+ @truename = name
783
+ lopt = lopt ? lopt.to_s : name.to_s.gsub("_", "-")
784
+ @long = make_valid(lopt)
785
+ alts = [alts] unless alts.is_a?(Array) # box the value
786
+ @alts = alts.map { |alt| make_valid(alt) }.compact
787
+ end
788
+
789
+ # long specified with :long has precedence over the true-name
790
+ def long ; @long || @truename ; end
791
+
792
+ # all valid names, including alts
793
+ def names
794
+ [long] + @alts
795
+ end
796
+
797
+ end
798
+
799
+ class ShortNames
800
+
801
+ INVALID_ARG_REGEX = /[\d-]/ #:nodoc:
802
+
803
+ def initialize
804
+ @chars = []
805
+ @auto = true
806
+ end
807
+
808
+ attr_reader :chars, :auto
809
+
810
+ def add(values)
811
+ values = [values] unless values.is_a?(Array) # box the value
812
+ values.compact.each do |val|
813
+ if val == :none
814
+ @auto = false
815
+ raise "Cannot set short to :none if short-chars have been defined '#{@chars}'" unless chars.empty?
816
+ next
817
+ end
818
+ strval = val.to_s
819
+ sopt = case strval
820
+ when /^-(.)$/ then $1
821
+ when /^.$/ then strval
822
+ else raise ArgumentError, "invalid short option name '#{val.inspect}'"
823
+ end
824
+
825
+ if sopt =~ INVALID_ARG_REGEX
826
+ raise ArgumentError, "short option name '#{sopt}' can't be a number or a dash"
827
+ end
828
+ @chars << sopt
829
+ end
830
+ end
831
+
832
+ end
833
+
760
834
  class Option
761
835
 
762
- attr_accessor :name, :short, :long, :default, :permitted, :permitted_response
836
+ attr_reader :short
837
+ attr_accessor :name, :long, :default, :permitted, :permitted_response
763
838
  attr_writer :multi_given
764
839
 
765
840
  def initialize
766
- @long = nil
767
- @short = nil
841
+ @long = LongNames.new
842
+ @short = ShortNames.new # can be an Array of one-char strings, a one-char String, nil or :none
768
843
  @name = nil
769
844
  @multi_given = false
770
845
  @hidden = false
@@ -797,7 +872,7 @@ class Option
797
872
 
798
873
  def array_default? ; self.default.kind_of?(Array) ; end
799
874
 
800
- def short? ; short && short != :none ; end
875
+ def doesnt_need_autogen_short ; !short.auto || !short.chars.empty? ; end
801
876
 
802
877
  def callback ; opts(:callback) ; end
803
878
  def desc ; opts(:desc) ; end
@@ -812,7 +887,10 @@ class Option
812
887
  def type_format ; "" ; end
813
888
 
814
889
  def educate
815
- (short? ? "-#{short}, " : "") + "--#{long}" + type_format + (flag? && default ? ", --no-#{long}" : "")
890
+ optionlist = []
891
+ optionlist.concat(short.chars.map { |o| "-#{o}" })
892
+ optionlist.concat(long.names.map { |o| "--#{o}" })
893
+ optionlist.compact.join(', ') + type_format + (flag? && default ? ", --no-#{long}" : "")
816
894
  end
817
895
 
818
896
  ## Format the educate-line description including the default and permitted value(s)
@@ -865,7 +943,7 @@ class Option
865
943
  when Array
866
944
  return "one of: " + permitted.to_a.map(&:to_s).join(', ')
867
945
  when Range
868
- return "value in range of: #{permitted.to_s}"
946
+ return "value in range of: #{permitted}"
869
947
  when Regexp
870
948
  return "value matching: #{permitted.inspect}"
871
949
  end
@@ -916,7 +994,7 @@ class Option
916
994
  # to +OptimistXL::opt+. This is trickier in OptimistXL, than other cmdline
917
995
  # parsers (e.g. Slop) because we allow the +default:+ to be able to
918
996
  # set the option's type.
919
- def self.create(name, desc="", opts={}, settings={})
997
+ def self.create(name, _desc="", opts={}, _settings={})
920
998
 
921
999
  opttype = OptimistXL::Parser.registry_getopttype(opts[:type])
922
1000
  opttype_from_default = get_klass_from_default(opts, opttype)
@@ -926,10 +1004,10 @@ class Option
926
1004
  opt_inst = (opttype || opttype_from_default || OptimistXL::BooleanOption.new)
927
1005
 
928
1006
  ## fill in :long
929
- opt_inst.long = handle_long_opt(opts[:long], name)
1007
+ opt_inst.long.set(name, opts[:long], opts[:alt])
930
1008
 
931
1009
  ## fill in :short
932
- opt_inst.short = handle_short_opt(opts[:short])
1010
+ opt_inst.short.add opts[:short]
933
1011
 
934
1012
  ## fill in :multi
935
1013
  multi_given = opts[:multi] || false
@@ -951,7 +1029,6 @@ class Option
951
1029
  opt_inst
952
1030
  end
953
1031
 
954
- private
955
1032
 
956
1033
  def self.get_type_from_disdef(optdef, opttype, disambiguated_default)
957
1034
  if disambiguated_default.is_a? Array
@@ -983,28 +1060,8 @@ class Option
983
1060
  return OptimistXL::Parser.registry_getopttype(type_from_default)
984
1061
  end
985
1062
 
986
- def self.handle_long_opt(lopt, name)
987
- lopt = lopt ? lopt.to_s : name.to_s.gsub("_", "-")
988
- lopt = case lopt
989
- when /^--([^-].*)$/ then $1
990
- when /^[^-]/ then lopt
991
- else raise ArgumentError, "invalid long option name #{lopt.inspect}"
992
- end
993
- end
994
-
995
- def self.handle_short_opt(sopt)
996
- sopt = sopt.to_s if sopt && sopt != :none
997
- sopt = case sopt
998
- when /^-(.)$/ then $1
999
- when nil, :none, /^.$/ then sopt
1000
- else raise ArgumentError, "invalid short option name '#{sopt.inspect}'"
1001
- end
1002
-
1003
- if sopt
1004
- raise ArgumentError, "a short option name can't be a number or a dash" if sopt =~ ::OptimistXL::Parser::INVALID_SHORT_ARG_REGEX
1005
- end
1006
- return sopt
1007
- end
1063
+ private_class_method :get_type_from_disdef
1064
+ private_class_method :get_klass_from_default
1008
1065
 
1009
1066
  end
1010
1067
 
@@ -9,9 +9,9 @@ Gem::Specification.new do |spec|
9
9
  spec.version = OptimistXL::VERSION
10
10
  spec.authors = ["William Morgan", "Keenan Brock", "Jason Frey", "Ben Bowers"]
11
11
  spec.email = "nanobowers@gmail.com"
12
- spec.summary = "OptimistXL is a commandline option parser for Ruby that just gets out of your way."
13
- spec.description = "OptimistXL is a commandline option parser for Ruby that just
14
- gets out of your way. One line of code per option is all you need to write.
12
+ spec.summary = "OptimistXL is feature fork of the Optimist commandline option parser."
13
+ spec.description = "OptimistXL is feature filled but lightweight commandline option parser.
14
+ One line of code per option is all you typically need to write.
15
15
  For that, you get a nice automatically-generated help page, robust option
16
16
  parsing, command subcompletion, and sensible defaults for everything you don't
17
17
  specify. This gem is an enhanced-feature fork of the Optimist gem."
@@ -29,6 +29,8 @@ specify. This gem is an enhanced-feature fork of the Optimist gem."
29
29
 
30
30
  spec.require_paths = ["lib"]
31
31
 
32
+ spec.required_ruby_version = '>= 2.2'
33
+
32
34
  spec.add_development_dependency "minitest", "~> 5.4.3"
33
35
  spec.add_development_dependency "rake", "~> 10.0"
34
36
  spec.add_development_dependency "chronic"
@@ -0,0 +1,146 @@
1
+ require 'test_helper'
2
+
3
+ module OptimistXL
4
+
5
+ class AlternateNamesTest < ::MiniTest::Test
6
+
7
+ def setup
8
+ @p = Parser.new
9
+ end
10
+
11
+ def get_help_string
12
+ err = assert_raises(OptimistXL::HelpNeeded) do
13
+ @p.parse(%w(--help))
14
+ end
15
+ sio = StringIO.new "w"
16
+ err.parser.educate sio
17
+ sio.string
18
+ end
19
+
20
+ def test_altshort
21
+ @p.opt :catarg, "desc", :short => ["c", "-C"]
22
+ opts = @p.parse %w(-c)
23
+ assert_equal true, opts[:catarg]
24
+ opts = @p.parse %w(-C)
25
+ assert_equal true, opts[:catarg]
26
+ assert_raises(CommandlineError) { @p.parse %w(-c -C) }
27
+ assert_raises(CommandlineError) { @p.parse %w(-cC) }
28
+ end
29
+
30
+ def test_altshort_with_multi
31
+ @p.opt :flag, "desc", :short => ["-c", "C", :x], :multi => true
32
+ @p.opt :num, "desc", :short => ["-n", "N"], :multi => true, type: Integer
33
+ @p.parse %w(-c)
34
+ @p.parse %w(-C -c -x)
35
+ @p.parse %w(-c -C)
36
+ @p.parse %w(-c -C -c -C)
37
+ opts = @p.parse %w(-ccCx)
38
+ assert_equal true, opts[:flag]
39
+ @p.parse %w(-c)
40
+ @p.parse %w(-N 1 -n 3)
41
+ @p.parse %w(-n 2 -N 4)
42
+ opts = @p.parse %w(-n 4 -N 3 -n 2 -N 1)
43
+ assert_equal [4, 3, 2, 1], opts[:num]
44
+ end
45
+
46
+ def test_altlong
47
+ @p.opt "goodarg0", "desc", :alt => "zero"
48
+ @p.opt "goodarg1", "desc", :long => "newone", :alt => "one"
49
+ @p.opt "goodarg2", "desc", :alt => "--two"
50
+ @p.opt "goodarg3", "desc", :alt => ["three", "--four", :five]
51
+
52
+ [%w[--goodarg0], %w[--zero]].each do |a|
53
+ opts = @p.parse(a)
54
+ assert opts.goodarg0
55
+ end
56
+
57
+ [%w[--newone], %w[-n], %w[--one]].each do |a|
58
+ opts = @p.parse(a)
59
+ assert opts.goodarg1
60
+ end
61
+
62
+ [%w[--two]].each do |a|
63
+ opts = @p.parse(a)
64
+ assert opts.goodarg2
65
+ end
66
+
67
+ [%w[--three], %w[--four], %w[--five]].each do |a|
68
+ opts = @p.parse(a)
69
+ assert opts.goodarg3
70
+ end
71
+
72
+ [%w[--goodarg1], %w[--missing], %w[-a]].each do |a|
73
+ assert_raises(OptimistXL::CommandlineError) { @p.parse(a) }
74
+ end
75
+
76
+ ["", '--', '-bad', '---threedash'].each do |altitem|
77
+ assert_raises(ArgumentError) { @p.opt "badarg", "desc", :alt => altitem }
78
+ end
79
+ end
80
+
81
+ def test_altshort_help
82
+ @p.opt :cat, 'cat', short: ['c','C','a','T']
83
+ outstring = get_help_string
84
+ # expect mutliple short-opts to be in the help
85
+ assert_match(/-c, -C, -a, -T, --cat/, outstring)
86
+ end
87
+
88
+
89
+ def test_altlong_help
90
+ @p.opt :cat, 'a cat', alt: :feline
91
+ @p.opt :dog, 'a dog', alt: ['Pooch', :canine]
92
+ @p.opt :fruit, 'a fruit', long: :fig, alt: ['peach', :pear, "--apple"], short: :none
93
+
94
+ outstring = get_help_string
95
+
96
+ assert_match(/^\s*-c, --cat, --feline/, outstring)
97
+ assert_match(/^\s*-d, --dog, --Pooch, --canine/, outstring)
98
+
99
+ # expect long-opt to shadow the actual name
100
+ assert_match(/^\s*--fig, --peach, --pear, --apple/, outstring)
101
+
102
+ end
103
+
104
+ def test_alt_duplicates
105
+ # alt duplicates named option
106
+ assert_raises(ArgumentError) {
107
+ @p.opt :cat, 'desc', :alt => :cat
108
+ }
109
+ # alt duplicates :long
110
+ assert_raises(ArgumentError) {
111
+ @p.opt :cat, 'desc', :long => :feline, :alt => [:feline]
112
+ }
113
+ # alt duplicates itself
114
+ assert_raises(ArgumentError) {
115
+ @p.opt :abc, 'desc', :alt => [:aaa, :aaa]
116
+ }
117
+ end
118
+
119
+ def test_altlong_collisions
120
+ @p.opt :fat, 'desc'
121
+ @p.opt :raton, 'desc', :long => :rat
122
+ @p.opt :bat, 'desc', :alt => [:baton, :twirl]
123
+
124
+ # :alt collision with named option
125
+ assert_raises(ArgumentError) {
126
+ @p.opt :cat, 'desc', :alt => :fat
127
+ }
128
+
129
+ # :alt collision with :long option
130
+ assert_raises(ArgumentError) {
131
+ @p.opt :cat, 'desc', :alt => :rat
132
+ }
133
+
134
+ # :named option collision with existing :alt option
135
+ assert_raises(ArgumentError) {
136
+ @p.opt :baton, 'desc'
137
+ }
138
+
139
+ # :long option collision with existing :alt option
140
+ assert_raises(ArgumentError) {
141
+ @p.opt :whirl, 'desc', :long => 'twirl'
142
+ }
143
+
144
+ end
145
+ end
146
+ end
@@ -273,10 +273,7 @@ class ParserTest < ::MiniTest::Test
273
273
  end
274
274
 
275
275
  def test_flag_with_no_defaults_and_no_args_act_as_switches_array
276
- opts = nil
277
-
278
276
  @p.opt :argd, "desc", :type => :strings, :default => ["default_string"]
279
-
280
277
  opts = @p.parse(%w(--argd))
281
278
  assert_equal ["default_string"], opts[:argd]
282
279
  end
@@ -571,7 +568,11 @@ Options:
571
568
  assert_raises(ArgumentError) { @p.opt :arg, "desc", :short => "-1" }
572
569
  @p.opt :a1b, "desc"
573
570
  @p.opt :a2b, "desc"
574
- assert @p.specs[:a2b].short.to_i == 0
571
+ @p.parse []
572
+ # testing private interface to ensure default
573
+ # short options did not become numeric
574
+ assert_equal @p.specs[:a1b].short.chars.first, 'a'
575
+ assert_equal @p.specs[:a2b].short.chars.first, 'b'
575
576
  end
576
577
 
577
578
  def test_short_options_can_be_weird
@@ -748,7 +749,7 @@ Options:
748
749
 
749
750
  def test_auto_generated_long_names_convert_underscores_to_hyphens
750
751
  @p.opt :hello_there
751
- assert_equal "hello-there", @p.specs[:hello_there].long
752
+ assert_equal "hello-there", @p.specs[:hello_there].long.long
752
753
  end
753
754
 
754
755
  def test_arguments_passed_through_block
@@ -1305,7 +1306,7 @@ Options:
1305
1306
 
1306
1307
  def test_supports_callback_inline
1307
1308
  assert_raises(RuntimeError, "good") do
1308
- @p.opt :cb1 do |vals|
1309
+ @p.opt :cb1 do |_vals|
1309
1310
  raise "good"
1310
1311
  end
1311
1312
  @p.parse(%w(--cb1))
@@ -1314,7 +1315,7 @@ Options:
1314
1315
 
1315
1316
  def test_supports_callback_param
1316
1317
  assert_raises(RuntimeError, "good") do
1317
- @p.opt :cb1, "with callback", :callback => lambda { |vals| raise "good" }
1318
+ @p.opt :cb1, "with callback", :callback => lambda { |_vals| raise "good" }
1318
1319
  @p.parse(%w(--cb1))
1319
1320
  end
1320
1321
  end
@@ -13,15 +13,15 @@ class PermittedTest < ::MiniTest::Test
13
13
  end
14
14
 
15
15
  def test_permitted_invalid_value
16
- err_regexp = /permitted values for option "bad" must be either nil, Range, Regexp or an Array/
17
- assert_raises(ArgumentError) {
16
+ err_regexp = /permitted values for option "(bad|mad|sad)" must be either nil, Range, Regexp or an Array/
17
+ assert_raises(ArgumentError, err_regexp) {
18
18
  @p.opt 'bad', 'desc', :permitted => 1
19
19
  }
20
- assert_raises(ArgumentError) {
21
- @p.opt 'bad', 'desc', :permitted => "A"
20
+ assert_raises(ArgumentError, err_regexp) {
21
+ @p.opt 'mad', 'desc', :permitted => "A"
22
22
  }
23
23
  assert_raises_errmatch(ArgumentError, err_regexp) {
24
- @p.opt 'bad', 'desc', :permitted => :abcd
24
+ @p.opt 'sad', 'desc', :permitted => :abcd
25
25
  }
26
26
  end
27
27
 
@@ -17,6 +17,6 @@ end
17
17
 
18
18
  require 'minitest/autorun'
19
19
 
20
- Dir[File.expand_path('../support/**/*.rb', __FILE__)].each { |f| require f }
20
+ Dir[File.expand_path('../support/**/*.rb', __FILE__)].sort.each { |f| require f }
21
21
 
22
22
  require 'optimist_xl'
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: optimist_xl
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.1.1
4
+ version: 3.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - William Morgan
@@ -11,7 +11,7 @@ authors:
11
11
  autorequire:
12
12
  bindir: bin
13
13
  cert_chain: []
14
- date: 2020-01-20 00:00:00.000000000 Z
14
+ date: 2020-03-07 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: minitest
@@ -56,8 +56,8 @@ dependencies:
56
56
  - !ruby/object:Gem::Version
57
57
  version: '0'
58
58
  description: |-
59
- OptimistXL is a commandline option parser for Ruby that just
60
- gets out of your way. One line of code per option is all you need to write.
59
+ OptimistXL is feature filled but lightweight commandline option parser.
60
+ One line of code per option is all you typically need to write.
61
61
  For that, you get a nice automatically-generated help page, robust option
62
62
  parsing, command subcompletion, and sensible defaults for everything you don't
63
63
  specify. This gem is an enhanced-feature fork of the Optimist gem.
@@ -70,10 +70,12 @@ files:
70
70
  - ".travis.yml"
71
71
  - FAQ.txt
72
72
  - Gemfile
73
- - History.txt
73
+ - History.md
74
+ - LICENSE
74
75
  - README.md
75
76
  - Rakefile
76
77
  - examples/a_basic_example.rb
78
+ - examples/alt_names.rb
77
79
  - examples/banners1.rb
78
80
  - examples/banners2.rb
79
81
  - examples/banners3.rb
@@ -85,6 +87,7 @@ files:
85
87
  - lib/optimist_xl.rb
86
88
  - lib/optimist_xl/chronic.rb
87
89
  - optimist_xl.gemspec
90
+ - test/optimist_xl/alt_names_test.rb
88
91
  - test/optimist_xl/command_line_error_test.rb
89
92
  - test/optimist_xl/help_needed_test.rb
90
93
  - test/optimist_xl/parser_educate_test.rb
@@ -112,7 +115,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
112
115
  requirements:
113
116
  - - ">="
114
117
  - !ruby/object:Gem::Version
115
- version: '0'
118
+ version: '2.2'
116
119
  required_rubygems_version: !ruby/object:Gem::Requirement
117
120
  requirements:
118
121
  - - ">="
@@ -123,9 +126,9 @@ rubyforge_project:
123
126
  rubygems_version: 2.7.4
124
127
  signing_key:
125
128
  specification_version: 4
126
- summary: OptimistXL is a commandline option parser for Ruby that just gets out of
127
- your way.
129
+ summary: OptimistXL is feature fork of the Optimist commandline option parser.
128
130
  test_files:
131
+ - test/optimist_xl/alt_names_test.rb
129
132
  - test/optimist_xl/command_line_error_test.rb
130
133
  - test/optimist_xl/help_needed_test.rb
131
134
  - test/optimist_xl/parser_educate_test.rb