support nil to indicate no short param name

develop
myk002 2021-09-25 21:15:53 -07:00 committed by Myk
parent fc556c9e5d
commit ecdfca89d1
2 changed files with 23 additions and 7 deletions

@ -75,12 +75,13 @@ end
-- as positional parameters and returned in the nonoptions list. -- as positional parameters and returned in the nonoptions list.
-- --
-- optionActions is a vector with elements in the following format: -- optionActions is a vector with elements in the following format:
-- {shortOptionName, longOptionAlias, hasArg=boolean, handler=fn} -- {shortOptionName, longOptionAlias, hasArg=boolean, handler=fn}
-- shortOptionName and handler are required. If the option takes an argument, -- shortOptionName and handler are required. If the option takes an argument,
-- it will be passed to the handler function. -- it will be passed to the handler function.
-- longOptionAlias is optional. -- longOptionAlias is optional.
-- hasArg defaults to false. -- hasArg defaults to false.
-- to have an option that has only a long form, pass '' as the shortOptionName. -- To have an option that has only a long form, pass nil or '' as the
-- shortOptionName.
-- --
-- example usage: -- example usage:
-- --
@ -101,16 +102,21 @@ function processArgsGetopt(args, optionActions)
local handlers = {} local handlers = {}
for _,optionAction in ipairs(optionActions) do for _,optionAction in ipairs(optionActions) do
local sh_opt,long_opt = optionAction[1], optionAction[2] local sh_opt,long_opt = optionAction[1], optionAction[2]
-- sh_opt can be zero-length if long_opt is specified if sh_opt and (type(sh_opt) ~= 'string' or #sh_opt > 1) then
if not sh_opt or type(sh_opt) ~= 'string' or
(#sh_opt ~= 1 and not (#sh_opt == 0 and long_opt)) then
error('option letter not found') error('option letter not found')
end end
if long_opt and (type(long_opt) ~= 'string' or #long_opt == 0) then if long_opt and (type(long_opt) ~= 'string' or #long_opt == 0) then
error('long option name must be a string with length >0') error('long option name must be a string with length >0')
end end
if not sh_opt then
sh_opt = ''
end
if not long_opt and #sh_opt == 0 then
error('at least one of sh_opt and long_opt must be specified')
end
if not optionAction.handler then if not optionAction.handler then
error(string.format('handler missing for option "%s"', sh_opt)) error(string.format('handler missing for option "%s"',
#sh_opt > 0 and sh_opt or long_opt))
end end
if #sh_opt > 0 then if #sh_opt > 0 then
sh_opts = sh_opts .. sh_opt sh_opts = sh_opts .. sh_opt

@ -58,7 +58,7 @@ function test.processArgsGetopt_happy_path()
end end
function test.processArgsGetopt_action_errors() function test.processArgsGetopt_action_errors()
expect.error_match('option letter not found', expect.error_match('at least one of sh_opt and long_opt',
function() function()
argparse.processArgsGetopt({}, {{handler=function() end}}) argparse.processArgsGetopt({}, {{handler=function() end}})
end) end)
@ -72,6 +72,9 @@ function test.processArgsGetopt_action_errors()
expect.error_match('long option name', expect.error_match('long option name',
function() argparse.processArgsGetopt({}, {{'', ''}}) end) function() argparse.processArgsGetopt({}, {{'', ''}}) end)
expect.error_match('long option name',
function() argparse.processArgsGetopt({}, {{nil, ''}}) end)
expect.error_match('long option name', expect.error_match('long option name',
function() argparse.processArgsGetopt({}, {{'a', ''}}) end) function() argparse.processArgsGetopt({}, {{'a', ''}}) end)
@ -120,6 +123,13 @@ function test.processArgsGetopt_long_opt_without_short_opt()
{{'', 'long', handler=function() var = true end}}) {{'', 'long', handler=function() var = true end}})
expect.true_(var) expect.true_(var)
expect.table_eq({}, nonoptions) expect.table_eq({}, nonoptions)
var = false
nonoptions = argparse.processArgsGetopt(
{'--long'},
{{nil, 'long', handler=function() var = true end}})
expect.true_(var)
expect.table_eq({}, nonoptions)
end end
function test.stringList() function test.stringList()