Search code examples
rubygetopt-long

GetoptLong is not raising error when GetoptLong::REQUIRED_ARGUMENT is not mentioned


First of all in my tests the errors are only triggered when calling .each, not in the constructor so this:

require "getoptlong"

GetoptLong.new(
  [ "--argument", "-a", GetoptLong::REQUIRED_ARGUMENT ]
)

# ~$ ruby script.rb --argument

Doesn't show any error.

This shows the error:

require "getoptlong"

GetoptLong.new(
  [ "--argument", "-a", GetoptLong::REQUIRED_ARGUMENT ]
).each

# ~$ ruby script.rb --argument

Error:

test_getoptlong.rb: option `--argument' requires an argument
/Users/me/.rbenv/versions/3.1.1/lib/ruby/3.1.0/getoptlong.rb:398:in `set_error': option `--argument' requires an argument (GetoptLong::MissingArgument)

If I don't pass the argument --argument at all, I don't see any error:

require "getoptlong"

GetoptLong.new(
  [ "--argument", "-a", GetoptLong::REQUIRED_ARGUMENT ]
).each

# ~$ ruby script.rb

No error.

As this is a GetoptLong::REQUIRED_ARGUMENT, I expected to see an error if the user didn't add it to the script call.

How can I raise an error if any GetoptLong::REQUIRED_ARGUMENT is missing?


Solution

  • In spite of the Documentation, which shows the following example:

    If the option is last, an exception is raised:

    $ ruby types.rb
    # Raises GetoptLong::MissingArgument
    

    It appears that you would need to validate this manually using ARGV.

    The GetoptLong::REQUIRED_ARGUMENT constant simply specifies that the option requires an argument, not that the option itself is required.

    You could do this using something as simple as:

    require 'getoptlong'
    
    options =GetoptLong.new(
      [ "--argument", "-a", GetoptLong::REQUIRED_ARGUMENT ]
    )
    unless ARGV.any? {|opt| opt == '--argument' || opt == '-a'}
     raise GetoptLong::MissingArgument, '--argument is required' 
    end
    

    There is a better example Here which shows subsequent validation is necessary and provides alternate means of handling.