Java 为什么默认解析器(使用commons cli)在无法识别选项时不引发异常?
当指定为程序参数的选项无效(在预定义选项列表中不可用)时,我希望打印一条用法帮助消息 我键入参数“Test”字符串。我在想,无效选项会导致解析器抛出ParseException,但事实并非如此。我怎样才能做到这一点?这个图书馆有可能吗?现在它只是一个无效的参数 更新Java 为什么默认解析器(使用commons cli)在无法识别选项时不引发异常?,java,apache-commons-cli,Java,Apache Commons Cli,当指定为程序参数的选项无效(在预定义选项列表中不可用)时,我希望打印一条用法帮助消息 我键入参数“Test”字符串。我在想,无效选项会导致解析器抛出ParseException,但事实并非如此。我怎样才能做到这一点?这个图书馆有可能吗?现在它只是一个无效的参数 更新 实际上,当选项的前缀为“-”时,它会引发异常。所以“-Test”会引发异常,但“Test”不会。无论如何,我的问题仍然有效,如何强制解析器对无效参数抛出异常是的,您可以,您必须创建自定义异常,如: public class Pars
实际上,当选项的前缀为“-”时,它会引发异常。所以“-Test”会引发异常,但“Test”不会。无论如何,我的问题仍然有效,如何强制解析器对无效参数抛出异常是的,您可以,您必须创建自定义异常,如:
public class ParseException extends Exception{
ParseException(String msg){
super(msg);
}
}
并转换成代码:
CommandLineParser parser = new BasicParser();
try {
CommandLine line = parser.parse(getOptions(), args);
}
catch( Exception exp ) {
throw new ParseException("Invalid Arguments");
}
return true;
而以上方法应该抛出
throws ParseException
因此,如果传递无效参数,则其调用者将获得ParseException是的,您可以创建自定义异常,如:
public class ParseException extends Exception{
ParseException(String msg){
super(msg);
}
}
并转换成代码:
CommandLineParser parser = new BasicParser();
try {
CommandLine line = parser.parse(getOptions(), args);
}
catch( Exception exp ) {
throw new ParseException("Invalid Arguments");
}
return true;
而以上方法应该抛出
throws ParseException
因此,它的调用者if pass invalid参数将获得ParseException命令行有两种类型的条目,而不是程序名、选项(用
-
或-
指定)和我将调用的参数(可能有更好的名称,但我不知道它是什么!),它们没有前缀。例如,对于ls
:
ls-lafoo
选项是
-l
和-a
,参数是foo
(要列出的目录)。使用commons cli解析命令行时,它只关心选项,而忽略其他所有内容。这就是为什么如果添加测试(不是选项),它不会失败,但是如果添加-Test
,它会失败 命令行有两种类型的条目,除了程序名,选项(用-
或-
指定)和我将调用的参数(可能有更好的名称,但我不知道它是什么!),它们没有前缀。例如,对于ls
:
ls-lafoo
选项是-l
和-a
,参数是foo
(要列出的目录)。使用commons cli解析命令行时,它只关心选项,而忽略其他所有内容。这就是为什么如果添加测试(不是选项),它不会失败,但是如果添加-Test
,它会失败 虽然提供的答案很好,我也接受,但我决定扩展默认解析器功能,以防止键入无效选项,即使没有“-”或“--”符号。我制作了自己的自定义解析器:
public class StrictParser extends Parser {
@Override
protected String[] flatten(Options opts, String[] arguments, boolean stopAtNonOption) {
return arguments;
}
@Override
public CommandLine parse(Options options, String[] arguments, boolean stopAtNonOption) throws ParseException {
CommandLine cmd = null;
List<String> tokenList = Arrays.asList(flatten(getOptions(), arguments, stopAtNonOption));
ListIterator<String> iterator = tokenList.listIterator();
boolean eatTheRest = false;
setOptions(options);
cmd = super.parse(options, arguments, stopAtNonOption);
while (iterator.hasNext()) {
String token = (String) iterator.next();
if (!token.startsWith("--") && !token.startsWith("-")) {
if (stopAtNonOption) {
throw new UnrecognizedOptionException("Unrecognized option: " + token +". Every option must start with '--' or '-'", token);
}
} else {
eatTheRest = true;
}
if (eatTheRest) {
iterator.next();
}
}
return cmd;
}
}
到
(忽略这三个嵌套的ifs;))
每个选项也只接受一个参数,但正如我所提到的,它是实现对默认解析器的其他修改的唯一起点虽然提供的答案很好,我也接受它,但我决定扩展默认解析器功能,以防止在没有“-”或“---”符号的情况下键入无效选项。我制作了自己的自定义解析器:
public class StrictParser extends Parser {
@Override
protected String[] flatten(Options opts, String[] arguments, boolean stopAtNonOption) {
return arguments;
}
@Override
public CommandLine parse(Options options, String[] arguments, boolean stopAtNonOption) throws ParseException {
CommandLine cmd = null;
List<String> tokenList = Arrays.asList(flatten(getOptions(), arguments, stopAtNonOption));
ListIterator<String> iterator = tokenList.listIterator();
boolean eatTheRest = false;
setOptions(options);
cmd = super.parse(options, arguments, stopAtNonOption);
while (iterator.hasNext()) {
String token = (String) iterator.next();
if (!token.startsWith("--") && !token.startsWith("-")) {
if (stopAtNonOption) {
throw new UnrecognizedOptionException("Unrecognized option: " + token +". Every option must start with '--' or '-'", token);
}
} else {
eatTheRest = true;
}
if (eatTheRest) {
iterator.next();
}
}
return cmd;
}
}
到
(忽略这三个嵌套的ifs;))
每个选项也只接受一个参数,但正如我所提到的,它是实现对默认解析器的其他修改的唯一起点您的解决方案更像是定义新的异常。但在我的例子中,ParseException不是从parse方法抛出的,当args包含无效选项时。@ArturSkrzydło请仔细阅读答案,答案的第二部分包含修改后的代码,第三部分显示方法调用的更改。您创建了新异常,并在从parse方法抛出ParseException时抛出它。在这种情况下,它没有任何意义,因为我在定义无效参数时从未到达catch语句。@ArturSkrzydł现在看到答案,如果parse get exception它将抛出ParseException再次查看我的问题-'我在想,无效选项会导致解析器抛出ParseException,这意味着当我键入无效的选项名时,不会抛出ParseException。所以你的解决方案毫无意义。另外,重新引用异常的意义是什么。我可以尝试使用catch语句,并在方法声明的“throws”中定义它。您的解决方案更像是定义新的异常。但在我的例子中,ParseException不是从parse方法抛出的,当args包含无效选项时。@ArturSkrzydło请仔细阅读答案,答案的第二部分包含修改后的代码,第三部分显示方法调用的更改。您创建了新异常,并在从parse方法抛出ParseException时抛出它。在这种情况下,它没有任何意义,因为我在定义无效参数时从未到达catch语句。@ArturSkrzydł现在看到答案,如果parse get exception它将抛出ParseException再次查看我的问题-'我在想,无效选项会导致解析器抛出ParseException,这意味着当我键入无效的选项名时,不会抛出ParseException。所以你的解决方案毫无意义。另外,重新引用异常的意义是什么。我可以只使用ommit try catch语句,并在方法声明中的“throws”中定义它。好吧,我理解这一点,但我认为在commons cli库中,我可以验证所有命令行,但据我所知:(这就是为什么您经常可以知道什么时候使用commons cli—因为一切都是一个--
选项:)好的,我理解这一点,但我认为在commons cli库中,我可以验证所有命令行,但据我所知,这还不够:(这就是为什么您经常可以知道某些东西何时使用commons cli的原因,因为一切都是--
选项:)