From 9c4e8a29b701afaa74fd6c8d05241f0be3793517 Mon Sep 17 00:00:00 2001 From: serg-v Date: Mon, 9 Jan 2023 08:58:27 +0300 Subject: [PATCH 01/11] picocli fish completion --- src/main/java/picocli/AutoComplete.java | 29 +++++++++++++++++++++ src/test/java/picocli/AutoCompleteTest.java | 16 ++++++++++++ 2 files changed, 45 insertions(+) diff --git a/src/main/java/picocli/AutoComplete.java b/src/main/java/picocli/AutoComplete.java index a43f8ba5c..72d34d86e 100644 --- a/src/main/java/picocli/AutoComplete.java +++ b/src/main/java/picocli/AutoComplete.java @@ -305,6 +305,17 @@ private static class CommandDescriptor { this.commandName = commandName; this.commandLine = commandLine; } + + @Override + public String toString() { + return "CommandDescriptor{" + + "functionName='" + functionName + '\'' + + ", parentFunctionName='" + parentFunctionName + '\'' + + ", parentWithoutTopLevelCommand='" + parentWithoutTopLevelCommand + '\'' + + ", commandName='" + commandName + '\'' + + ", commandLine=" + commandLine + + '}'; + } } private static final String SCRIPT_HEADER = "" + @@ -534,6 +545,24 @@ public static String bash(String scriptName, CommandLine commandLine) { return result.toString(); } + + public static String fish(String scriptName, CommandLine commandLine) { + if (scriptName == null) { throw new NullPointerException("scriptName"); } + if (commandLine == null) { throw new NullPointerException("commandLine"); } + List hierarchy = createHierarchy(scriptName, commandLine); + //print hierarchy + for (CommandDescriptor descriptor : hierarchy) { + System.out.println(descriptor.functionName + " " + descriptor.commandName); + } + + StringBuilder result = new StringBuilder(); + result.append("Hello from fish!").append("\n"); + for (CommandDescriptor commandDescriptor : hierarchy) { + result.append(commandDescriptor.toString()).append("\n"); + } + return result.toString(); + } + private static List createHierarchy(String scriptName, CommandLine commandLine) { List result = new ArrayList(); result.add(new CommandDescriptor("_picocli_" + scriptName, "", "", scriptName, commandLine)); diff --git a/src/test/java/picocli/AutoCompleteTest.java b/src/test/java/picocli/AutoCompleteTest.java index 49b37b78b..d62e16dc3 100644 --- a/src/test/java/picocli/AutoCompleteTest.java +++ b/src/test/java/picocli/AutoCompleteTest.java @@ -2117,4 +2117,20 @@ public void testIssue1388_AliasesCommand() throws FileNotFoundException { existingScript.delete(); } } + + @Test + public void testFish() { + String expected = String.format("hello from fish%n"); + + assertEquals( + expected, + AutoComplete.fish("myapp", new CommandLine(new Issue1352CommandWithResourceBundle())) + ); + + assertEquals( + expected, + AutoComplete.fish("myapp", new CommandLine(new Issue1352ParentCommand())) + ); + + } } From 1af827496b74d28ab63e7d5c8d77001f4c7fab7e Mon Sep 17 00:00:00 2001 From: serg-v Date: Sun, 15 Jan 2023 17:50:22 +0300 Subject: [PATCH 02/11] picocli fish completion --- src/main/java/picocli/AutoComplete.java | 110 +++++++++++++++++--- src/test/java/picocli/AutoCompleteTest.java | 16 --- 2 files changed, 93 insertions(+), 33 deletions(-) diff --git a/src/main/java/picocli/AutoComplete.java b/src/main/java/picocli/AutoComplete.java index 72d34d86e..46d8588ed 100644 --- a/src/main/java/picocli/AutoComplete.java +++ b/src/main/java/picocli/AutoComplete.java @@ -305,17 +305,6 @@ private static class CommandDescriptor { this.commandName = commandName; this.commandLine = commandLine; } - - @Override - public String toString() { - return "CommandDescriptor{" + - "functionName='" + functionName + '\'' + - ", parentFunctionName='" + parentFunctionName + '\'' + - ", parentWithoutTopLevelCommand='" + parentWithoutTopLevelCommand + '\'' + - ", commandName='" + commandName + '\'' + - ", commandLine=" + commandLine + - '}'; - } } private static final String SCRIPT_HEADER = "" + @@ -551,18 +540,105 @@ public static String fish(String scriptName, CommandLine commandLine) { if (commandLine == null) { throw new NullPointerException("commandLine"); } List hierarchy = createHierarchy(scriptName, commandLine); //print hierarchy + StringBuilder result = new StringBuilder(); + //result.append("complete --command ").append(scriptName).append(" --no-files").append("\n"); + + String parentFunction = ""; + List currentLevel = new ArrayList(); + List currentLevelCommands = new ArrayList(); + + CommandDescriptor rootDescriptor = null; for (CommandDescriptor descriptor : hierarchy) { - System.out.println(descriptor.functionName + " " + descriptor.commandName); - } + if (descriptor.parentFunctionName.equals("")) { + rootDescriptor = descriptor; + continue; + } + if (!descriptor.parentFunctionName.equals(parentFunction)) { + if (!currentLevelCommands.isEmpty()) { + processLevel(scriptName, result, currentLevel, currentLevelCommands, parentFunction, rootDescriptor); + rootDescriptor = null; - StringBuilder result = new StringBuilder(); - result.append("Hello from fish!").append("\n"); - for (CommandDescriptor commandDescriptor : hierarchy) { - result.append(commandDescriptor.toString()).append("\n"); + currentLevel.clear(); + currentLevelCommands.clear(); + } + parentFunction = descriptor.parentFunctionName; + } + + currentLevel.add(descriptor); + currentLevelCommands.add(descriptor.commandName); } + if (!currentLevelCommands.isEmpty()) { + processLevel(scriptName, result, currentLevel, currentLevelCommands, parentFunction, rootDescriptor); + } + + return result.toString(); } + private static void processLevel(String scriptName, StringBuilder result, List currentLevel, + List currentLevelCommands, String levelName, + CommandDescriptor rootDescriptor) { + result.append("\n# ").append(levelName).append(" completion \n"); + result.append("set -l ").append(levelName).append(" ").append(String.join(" ", currentLevelCommands)).append( + "\n"); + if (rootDescriptor != null) { + for (OptionSpec optionSpec : rootDescriptor.commandLine.getCommandSpec().options()) { + result.append("complete -c ").append(scriptName); + result.append(" -n \"not __fish_seen_subcommand_from $").append(levelName).append("\""); + result.append(" -l ").append(optionSpec.longestName().replace("--", "")); + String optionDescription = sanitizeDescription(optionSpec.description().length > 0 ? optionSpec.description()[0] : ""); + result.append(" -d '").append(optionDescription).append("'\n"); + + if (!optionSpec.shortestName().equals(optionSpec.longestName())) { + result.append("complete -c ").append(scriptName); + result.append(" -n \"not __fish_seen_subcommand_from $").append(levelName).append("\""); + result.append(" -s ").append(optionSpec.shortestName().replace("-", "")); + result.append(" -d '").append(optionDescription).append("'\n"); + } + } + } + for (CommandDescriptor commandDescriptor : currentLevel) { + String[] descriptions = commandDescriptor.commandLine.getCommandSpec().usageMessage().description(); + String description = descriptions.length > 0 ? descriptions[0] : ""; + result.append("complete -c ").append(scriptName); + result.append(" -f"); // do not show files + result.append(" -n \"not __fish_seen_subcommand_from $").append(levelName).append("\""); + if (!commandDescriptor.parentWithoutTopLevelCommand.equals("")) { + result.append(" -n '__fish_seen_subcommand_from ").append( + commandDescriptor.parentWithoutTopLevelCommand).append("'"); + } + result.append(" -a ").append(commandDescriptor.commandName).append(" -d '").append(description).append("'\n"); + + for (OptionSpec optionSpec : commandDescriptor.commandLine.getCommandSpec().options()) { + result.append("complete -c ").append(scriptName); + result.append(" -n \"__fish_seen_subcommand_from ").append(commandDescriptor.commandName).append("\""); + if (!commandDescriptor.parentWithoutTopLevelCommand.equals("")) { + result.append(" -n '__fish_seen_subcommand_from ").append( + commandDescriptor.parentWithoutTopLevelCommand).append("'"); + } + result.append(" -l ").append(optionSpec.longestName().replace("--", "")); + String optionDescription = sanitizeDescription(optionSpec.description().length > 0 ? optionSpec.description()[0] : ""); + result.append(" -d '").append(optionDescription).append("'\n"); + + if (!optionSpec.shortestName().equals(optionSpec.longestName())) { + result.append("complete -c ").append(scriptName); + result.append(" -n \"__fish_seen_subcommand_from ").append(commandDescriptor.commandName).append("\""); + if (!commandDescriptor.parentWithoutTopLevelCommand.equals("")) { + result.append(" -n '__fish_seen_subcommand_from ").append( + commandDescriptor.parentWithoutTopLevelCommand).append("'"); + } + result.append(" -s ").append(optionSpec.shortestName().replace("-", "")); + result.append(" -d '").append(optionDescription).append("'\n"); + } + } + } + + } + + private static String sanitizeDescription(String description) { + return description.replace("'", "\\'"); + } + private static List createHierarchy(String scriptName, CommandLine commandLine) { List result = new ArrayList(); result.add(new CommandDescriptor("_picocli_" + scriptName, "", "", scriptName, commandLine)); diff --git a/src/test/java/picocli/AutoCompleteTest.java b/src/test/java/picocli/AutoCompleteTest.java index d62e16dc3..49b37b78b 100644 --- a/src/test/java/picocli/AutoCompleteTest.java +++ b/src/test/java/picocli/AutoCompleteTest.java @@ -2117,20 +2117,4 @@ public void testIssue1388_AliasesCommand() throws FileNotFoundException { existingScript.delete(); } } - - @Test - public void testFish() { - String expected = String.format("hello from fish%n"); - - assertEquals( - expected, - AutoComplete.fish("myapp", new CommandLine(new Issue1352CommandWithResourceBundle())) - ); - - assertEquals( - expected, - AutoComplete.fish("myapp", new CommandLine(new Issue1352ParentCommand())) - ); - - } } From a144222a8e0ae4778c57a1b27b5bc1ef4f687d20 Mon Sep 17 00:00:00 2001 From: serg-v Date: Sun, 22 Jan 2023 13:12:15 +0300 Subject: [PATCH 03/11] picocli fish completion tests --- .gitignore | 2 + src/main/java/picocli/AutoComplete.java | 44 ++++++++---- src/test/dejagnu.fishtests/README.adoc | 4 ++ .../completion/basicExample.exp | 24 +++++++ .../completion/picocompletion-demo.exp | 14 ++++ src/test/dejagnu.fishtests/lib/completion.exp | 4 ++ src/test/dejagnu.fishtests/lib/library.exp | 11 +++ src/test/dejagnu.tests/runCompletion | 0 src/test/java/picocli/AutoCompleteTest.java | 36 ++++++++-- src/test/resources/basic.fish | 7 ++ .../picocompletion-demo_completion.fish | 68 +++++++++++++++++++ 11 files changed, 192 insertions(+), 22 deletions(-) create mode 100644 src/test/dejagnu.fishtests/README.adoc create mode 100644 src/test/dejagnu.fishtests/completion/basicExample.exp create mode 100644 src/test/dejagnu.fishtests/completion/picocompletion-demo.exp create mode 100644 src/test/dejagnu.fishtests/lib/completion.exp create mode 100644 src/test/dejagnu.fishtests/lib/library.exp mode change 100644 => 100755 src/test/dejagnu.tests/runCompletion create mode 100644 src/test/resources/basic.fish create mode 100644 src/test/resources/picocompletion-demo_completion.fish diff --git a/.gitignore b/.gitignore index 4e50d82d1..c914d015e 100644 --- a/.gitignore +++ b/.gitignore @@ -21,5 +21,7 @@ picocli.iml /src/test/dejagnu.tests/testrun.log /src/test/dejagnu.tests/testrun.sum /src/test/dejagnu.tests/tmp/ +/src/test/dejagnu.fishtests/log/completion.sum +/src/test/dejagnu.fishtests/log/completion.log /picocli-legacy-tests/gradle/wrapper/dists/**/*.lck /picocli-legacy-tests/gradle/wrapper/dists/**/*.ok diff --git a/src/main/java/picocli/AutoComplete.java b/src/main/java/picocli/AutoComplete.java index 46d8588ed..6860fd761 100644 --- a/src/main/java/picocli/AutoComplete.java +++ b/src/main/java/picocli/AutoComplete.java @@ -539,9 +539,7 @@ public static String fish(String scriptName, CommandLine commandLine) { if (scriptName == null) { throw new NullPointerException("scriptName"); } if (commandLine == null) { throw new NullPointerException("commandLine"); } List hierarchy = createHierarchy(scriptName, commandLine); - //print hierarchy StringBuilder result = new StringBuilder(); - //result.append("complete --command ").append(scriptName).append(" --no-files").append("\n"); String parentFunction = ""; List currentLevel = new ArrayList(); @@ -554,22 +552,18 @@ public static String fish(String scriptName, CommandLine commandLine) { continue; } if (!descriptor.parentFunctionName.equals(parentFunction)) { - if (!currentLevelCommands.isEmpty()) { - processLevel(scriptName, result, currentLevel, currentLevelCommands, parentFunction, rootDescriptor); - rootDescriptor = null; + processLevel(scriptName, result, currentLevel, currentLevelCommands, parentFunction, rootDescriptor); + rootDescriptor = null; - currentLevel.clear(); - currentLevelCommands.clear(); - } + currentLevel.clear(); + currentLevelCommands.clear(); parentFunction = descriptor.parentFunctionName; } currentLevel.add(descriptor); currentLevelCommands.add(descriptor.commandName); } - if (!currentLevelCommands.isEmpty()) { - processLevel(scriptName, result, currentLevel, currentLevelCommands, parentFunction, rootDescriptor); - } + processLevel(scriptName, result, currentLevel, currentLevelCommands, parentFunction, rootDescriptor); return result.toString(); @@ -578,17 +572,31 @@ public static String fish(String scriptName, CommandLine commandLine) { private static void processLevel(String scriptName, StringBuilder result, List currentLevel, List currentLevelCommands, String levelName, CommandDescriptor rootDescriptor) { - result.append("\n# ").append(levelName).append(" completion \n"); - result.append("set -l ").append(levelName).append(" ").append(String.join(" ", currentLevelCommands)).append( - "\n"); + if (levelName.equals("")) { + levelName = "root"; + } + + // fish doesn't like dashes in variable names + levelName = levelName.replaceAll("-", "_"); + + result.append("\n# ").append(levelName).append(" completion\n"); + result.append("set -l ").append(levelName); + if (!currentLevelCommands.isEmpty()) { + result.append(" ").append(String.join(" ", currentLevelCommands)); + } + result.append("\n"); if (rootDescriptor != null) { for (OptionSpec optionSpec : rootDescriptor.commandLine.getCommandSpec().options()) { result.append("complete -c ").append(scriptName); result.append(" -n \"not __fish_seen_subcommand_from $").append(levelName).append("\""); result.append(" -l ").append(optionSpec.longestName().replace("--", "")); + + if (optionSpec.completionCandidates() != null) { + result.append(" -f -a '").append(String.join(" ", extract(optionSpec.completionCandidates()))).append("' "); + } + String optionDescription = sanitizeDescription(optionSpec.description().length > 0 ? optionSpec.description()[0] : ""); result.append(" -d '").append(optionDescription).append("'\n"); - if (!optionSpec.shortestName().equals(optionSpec.longestName())) { result.append("complete -c ").append(scriptName); result.append(" -n \"not __fish_seen_subcommand_from $").append(levelName).append("\""); @@ -617,9 +625,15 @@ private static void processLevel(String scriptName, StringBuilder result, List 0 ? optionSpec.description()[0] : ""); result.append(" -d '").append(optionDescription).append("'\n"); + if (!optionSpec.shortestName().equals(optionSpec.longestName())) { result.append("complete -c ").append(scriptName); result.append(" -n \"__fish_seen_subcommand_from ").append(commandDescriptor.commandName).append("\""); diff --git a/src/test/dejagnu.fishtests/README.adoc b/src/test/dejagnu.fishtests/README.adoc new file mode 100644 index 000000000..28caddea8 --- /dev/null +++ b/src/test/dejagnu.fishtests/README.adoc @@ -0,0 +1,4 @@ +Run +``` +runtest --outdir log --tool completion +``` \ No newline at end of file diff --git a/src/test/dejagnu.fishtests/completion/basicExample.exp b/src/test/dejagnu.fishtests/completion/basicExample.exp new file mode 100644 index 000000000..eee1b41dd --- /dev/null +++ b/src/test/dejagnu.fishtests/completion/basicExample.exp @@ -0,0 +1,24 @@ +set timeout 1 + +# Setup completion and fake command +send "source ../resources/basic.fish\r" +expect -re "(.+>)" + +send "function basicExample; echo 'do'; end\r" +expect -re "(.+>)" + +set cmd "basicExample -" +set test "Tab should show options for '$cmd'" +set candidates "-t -u --timeout --timeUnit --timeUnit=" +run_completion_test $cmd $test $candidates + +set cmd "basicExample --" +set test "Tab should show options for '$cmd'" +set candidates "--timeout --timeUnit --timeUnit=" +run_completion_test $cmd $test $candidates + +set cmd "basicExample --timeUnit=" +set test "Tab should show time unit enum values for '$cmd'" +#set candidates "1 2 3" +set candidates "\u2026timeUnit=DAYS \u2026timeUnit=MICROSECONDS \u2026timeUnit=MINUTES \u2026timeUnit=SECONDS\r\n\u2026timeUnit=HOURS \u2026timeUnit=MILLISECONDS \u2026timeUnit=NANOSECONDS " +run_completion_test $cmd $test $candidates diff --git a/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp b/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp new file mode 100644 index 000000000..288d998c9 --- /dev/null +++ b/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp @@ -0,0 +1,14 @@ +exp_internal 1 +set timeout 1 + +# Setup completion and fake command +send "source ../resources/picocompletion-demo_completion.fish\r" +expect -re "(.+>)" + +send "function picocompletion-demo; echo 'do'; end\r" +expect -re "(.+>)" + +set cmd "picocompletion-demo " +set test "Tab should show sub1 and sub2 for '${cmd}'" +set candidates "sub1.*sub1-alias.*sub2.*sub2-alias.*" +run_completion_test $cmd $test $candidates diff --git a/src/test/dejagnu.fishtests/lib/completion.exp b/src/test/dejagnu.fishtests/lib/completion.exp new file mode 100644 index 000000000..c5df2c1ad --- /dev/null +++ b/src/test/dejagnu.fishtests/lib/completion.exp @@ -0,0 +1,4 @@ +exp_spawn fish --no-config +expect -re "(.+>)" + +source $::srcdir/lib/library.exp diff --git a/src/test/dejagnu.fishtests/lib/library.exp b/src/test/dejagnu.fishtests/lib/library.exp new file mode 100644 index 000000000..670de975f --- /dev/null +++ b/src/test/dejagnu.fishtests/lib/library.exp @@ -0,0 +1,11 @@ +proc run_completion_test {cmd test candidates} { + send "${cmd}\t" + expect { + -re "(\n${candidates}\u001b)" { pass $test } + timeout { fail $test } + } + puts "###Output" + puts "$expect_out(1,string)" + send "\x03" + expect ">" +} diff --git a/src/test/dejagnu.tests/runCompletion b/src/test/dejagnu.tests/runCompletion old mode 100644 new mode 100755 diff --git a/src/test/java/picocli/AutoCompleteTest.java b/src/test/java/picocli/AutoCompleteTest.java index 49b37b78b..26bf1e191 100644 --- a/src/test/java/picocli/AutoCompleteTest.java +++ b/src/test/java/picocli/AutoCompleteTest.java @@ -102,6 +102,14 @@ public void basic() throws Exception { assertEquals(expected, script); } + @Test + public void basicFish() throws Exception { + String script = AutoComplete.fish("basicExample", new CommandLine(new BasicExample())); + System.out.println(script); + String expected = loadTextFromClasspath("/basic.fish"); + assertEquals(expected, script); + } + public static class TopLevel { @Option(names = {"-V", "--version"}, help = true) boolean versionRequested; @Option(names = {"-h", "--help"}, help = true) boolean helpRequested; @@ -184,19 +192,33 @@ public static class Sub2Child3 { // } @Test public void nestedSubcommands() throws Exception { - CommandLine hierarchy = new CommandLine(new TopLevel()) - .addSubcommand("sub1", new Sub1()) - .addSubcommand("sub2", new CommandLine(new Sub2()) - .addSubcommand("subsub1", new Sub2Child1()) - .addSubcommand("subsub2", new Sub2Child2()) - .addSubcommand("subsub3", new Sub2Child3()) - ); + CommandLine hierarchy = getNestedSubcommandsCommandLine(); String script = AutoComplete.bash("picocompletion-demo", hierarchy); String expected = format(loadTextFromClasspath("/picocompletion-demo_completion.bash"), CommandLine.VERSION, concat("\" \"", TimeUnit.values())); assertEquals(expected, script); } + @Test + public void nestedSubcommandsFish() throws Exception { + CommandLine hierarchy = getNestedSubcommandsCommandLine(); + String script = AutoComplete.fish("picocompletion-demo", hierarchy); + System.out.println(script); + String expected = loadTextFromClasspath("/picocompletion-demo_completion.fish"); + assertEquals(expected, script); + } + + private static CommandLine getNestedSubcommandsCommandLine() { + CommandLine hierarchy = new CommandLine(new TopLevel()) + .addSubcommand("sub1", new Sub1()) + .addSubcommand("sub2", new CommandLine(new Sub2()) + .addSubcommand("subsub1", new Sub2Child1()) + .addSubcommand("subsub2", new Sub2Child2()) + .addSubcommand("subsub3", new Sub2Child3()) + ); + return hierarchy; + } + @Test public void helpCommand() { CommandLine hierarchy = new CommandLine(new AutoCompleteTest.TopLevel()) diff --git a/src/test/resources/basic.fish b/src/test/resources/basic.fish new file mode 100644 index 000000000..062e70134 --- /dev/null +++ b/src/test/resources/basic.fish @@ -0,0 +1,7 @@ + +# root completion +set -l root +complete -c basicExample -n "not __fish_seen_subcommand_from $root" -l timeUnit -f -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c basicExample -n "not __fish_seen_subcommand_from $root" -s u -d '' +complete -c basicExample -n "not __fish_seen_subcommand_from $root" -l timeout -d '' +complete -c basicExample -n "not __fish_seen_subcommand_from $root" -s t -d '' diff --git a/src/test/resources/picocompletion-demo_completion.fish b/src/test/resources/picocompletion-demo_completion.fish new file mode 100644 index 000000000..bb6282acd --- /dev/null +++ b/src/test/resources/picocompletion-demo_completion.fish @@ -0,0 +1,68 @@ + +# root completion +set -l root +complete -c picocompletion-demo -n "not __fish_seen_subcommand_from $root" -l version -d '' +complete -c picocompletion-demo -n "not __fish_seen_subcommand_from $root" -s V -d '' +complete -c picocompletion-demo -n "not __fish_seen_subcommand_from $root" -l help -d '' +complete -c picocompletion-demo -n "not __fish_seen_subcommand_from $root" -s h -d '' + +# _picocli_picocompletion_demo completion +set -l _picocli_picocompletion_demo sub1 sub1-alias sub2 sub2-alias +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" -a sub1 -d 'First level subcommand 1' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1" -l num -d 'a number' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1" -l str -d 'a String' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1" -l candidates -a 'aaa bbb ccc' -d 'with candidates' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" -a sub1-alias -d 'First level subcommand 1' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1-alias" -l num -d 'a number' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1-alias" -l str -d 'a String' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1-alias" -l candidates -a 'aaa bbb ccc' -d 'with candidates' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" -a sub2 -d 'First level subcommand 2' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2" -l num2 -d 'another number' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2" -l directory -d 'a directory' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2" -s d -d 'a directory' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" -a sub2-alias -d 'First level subcommand 2' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2-alias" -l num2 -d 'another number' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2-alias" -l directory -d 'a directory' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2-alias" -s d -d 'a directory' + +# _picocli_picocompletion_demo_sub2 completion +set -l _picocli_picocompletion_demo_sub2 subsub1 sub2child1-alias subsub2 sub2child2-alias subsub3 sub2child3-alias +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a subsub1 -d 'Second level sub-subcommand 1' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub1" -n '__fish_seen_subcommand_from sub2' -l host -d 'a host' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub1" -n '__fish_seen_subcommand_from sub2' -s h -d 'a host' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a sub2child1-alias -d 'Second level sub-subcommand 1' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child1-alias" -n '__fish_seen_subcommand_from sub2' -l host -d 'a host' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child1-alias" -n '__fish_seen_subcommand_from sub2' -s h -d 'a host' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a subsub2 -d 'Second level sub-subcommand 2' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2' -l timeUnit -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2' -s u -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2' -l timeout -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2' -s t -d '' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a sub2child2-alias -d 'Second level sub-subcommand 2' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2' -l timeUnit -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2' -s u -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2' -l timeout -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2' -s t -d '' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a subsub3 -d 'Second level sub-subcommand 3' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a sub2child3-alias -d 'Second level sub-subcommand 3' + +# _picocli_picocompletion_demo_sub2alias completion +set -l _picocli_picocompletion_demo_sub2alias subsub1 sub2child1-alias subsub2 sub2child2-alias subsub3 sub2child3-alias +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a subsub1 -d 'Second level sub-subcommand 1' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub1" -n '__fish_seen_subcommand_from sub2-alias' -l host -d 'a host' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub1" -n '__fish_seen_subcommand_from sub2-alias' -s h -d 'a host' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a sub2child1-alias -d 'Second level sub-subcommand 1' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child1-alias" -n '__fish_seen_subcommand_from sub2-alias' -l host -d 'a host' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child1-alias" -n '__fish_seen_subcommand_from sub2-alias' -s h -d 'a host' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a subsub2 -d 'Second level sub-subcommand 2' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2-alias' -l timeUnit -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2-alias' -s u -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2-alias' -l timeout -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2-alias' -s t -d '' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a sub2child2-alias -d 'Second level sub-subcommand 2' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2-alias' -l timeUnit -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2-alias' -s u -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2-alias' -l timeout -d '' +complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2-alias' -s t -d '' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a subsub3 -d 'Second level sub-subcommand 3' +complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a sub2child3-alias -d 'Second level sub-subcommand 3' From d6c2c8dccabe2d54c916d35cbc6c8d489062bde7 Mon Sep 17 00:00:00 2001 From: serg-v Date: Fri, 24 Feb 2023 16:38:28 +0300 Subject: [PATCH 04/11] picocli fish completion: java5 compatability --- src/main/java/picocli/AutoComplete.java | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/src/main/java/picocli/AutoComplete.java b/src/main/java/picocli/AutoComplete.java index 6860fd761..136735198 100644 --- a/src/main/java/picocli/AutoComplete.java +++ b/src/main/java/picocli/AutoComplete.java @@ -582,7 +582,7 @@ private static void processLevel(String scriptName, StringBuilder result, List 0 ? optionSpec.description()[0] : ""); @@ -627,7 +627,7 @@ private static void processLevel(String scriptName, StringBuilder result, List 0 ? optionSpec.description()[0] : ""); @@ -646,13 +646,23 @@ private static void processLevel(String scriptName, StringBuilder result, List list) { + StringBuilder result = new StringBuilder(); + for (int i = 0; i < list.size(); i++) { + if (i > 0) { + result.append(delimeter); + } + result.append(list.get(i)); + } + return result.toString(); + } + private static List createHierarchy(String scriptName, CommandLine commandLine) { List result = new ArrayList(); result.add(new CommandDescriptor("_picocli_" + scriptName, "", "", scriptName, commandLine)); From 1b90553c717997fc8f74789a2a92112be1d1c7e8 Mon Sep 17 00:00:00 2001 From: serg-v Date: Sat, 25 Feb 2023 12:32:36 +0300 Subject: [PATCH 05/11] picocli fish completion: refactoring --- src/main/java/picocli/AutoComplete.java | 85 ++++++++-------- .../completion/picocompletion-demo.exp | 11 +++ src/test/resources/basic.fish | 6 +- .../picocompletion-demo_completion.fish | 96 ++++++++----------- 4 files changed, 92 insertions(+), 106 deletions(-) diff --git a/src/main/java/picocli/AutoComplete.java b/src/main/java/picocli/AutoComplete.java index e605d5f4f..93d6dc44d 100644 --- a/src/main/java/picocli/AutoComplete.java +++ b/src/main/java/picocli/AutoComplete.java @@ -586,69 +586,62 @@ private static void processLevel(String scriptName, StringBuilder result, List 0 ? optionSpec.description()[0] : ""); - result.append(" -d '").append(optionDescription).append("'\n"); - if (!optionSpec.shortestName().equals(optionSpec.longestName())) { - result.append("complete -c ").append(scriptName); - result.append(" -n \"not __fish_seen_subcommand_from $").append(levelName).append("\""); - result.append(" -s ").append(optionSpec.shortestName().replace("-", "")); - result.append(" -d '").append(optionDescription).append("'\n"); - } + completeFishOption(scriptName, optionSpec, condition, result); } } for (CommandDescriptor commandDescriptor : currentLevel) { - String[] descriptions = commandDescriptor.commandLine.getCommandSpec().usageMessage().description(); - String description = descriptions.length > 0 ? descriptions[0] : ""; + result.append("complete -c ").append(scriptName); - result.append(" -f"); // do not show files - result.append(" -n \"not __fish_seen_subcommand_from $").append(levelName).append("\""); + result.append(" --no-files"); // do not show files + result.append(" --condition \"not __fish_seen_subcommand_from $").append(levelName).append("\""); if (!commandDescriptor.parentWithoutTopLevelCommand.equals("")) { - result.append(" -n '__fish_seen_subcommand_from ").append( + result.append(" --condition '__fish_seen_subcommand_from ").append( commandDescriptor.parentWithoutTopLevelCommand).append("'"); } - result.append(" -a ").append(commandDescriptor.commandName).append(" -d '").append(description).append("'\n"); + result.append(" --arguments ").append(commandDescriptor.commandName); + + String[] descriptions = commandDescriptor.commandLine.getCommandSpec().usageMessage().description(); + String description = descriptions.length > 0 ? descriptions[0] : ""; + result.append(" -d '").append(sanitizeFishDescription(description)).append("'\n"); + + String condition = getFishCondition(commandDescriptor); for (OptionSpec optionSpec : commandDescriptor.commandLine.getCommandSpec().options()) { - result.append("complete -c ").append(scriptName); - result.append(" -n \"__fish_seen_subcommand_from ").append(commandDescriptor.commandName).append("\""); - if (!commandDescriptor.parentWithoutTopLevelCommand.equals("")) { - result.append(" -n '__fish_seen_subcommand_from ").append( - commandDescriptor.parentWithoutTopLevelCommand).append("'"); - } - result.append(" -l ").append(optionSpec.longestName().replace("--", "")); + completeFishOption(scriptName, optionSpec, condition, result); + } + } + } - if (optionSpec.completionCandidates() != null) { - result.append(" -a '").append(join(" ", extract(optionSpec.completionCandidates()))).append("' "); - } + private static String getFishCondition(CommandDescriptor commandDescriptor) { + StringBuilder condition = new StringBuilder(); + condition.append(" --condition \"__fish_seen_subcommand_from ").append(commandDescriptor.commandName).append("\""); + if (!commandDescriptor.parentWithoutTopLevelCommand.equals("")) { + condition.append(" --condition '__fish_seen_subcommand_from ").append( + commandDescriptor.parentWithoutTopLevelCommand).append("'"); + } + return condition.toString(); + } - String optionDescription = sanitizeDescription(optionSpec.description().length > 0 ? optionSpec.description()[0] : ""); - result.append(" -d '").append(optionDescription).append("'\n"); + private static void completeFishOption(String scriptName, OptionSpec optionSpec, String conditions, StringBuilder result) { + result.append("complete -c ").append(scriptName); + result.append(conditions); + result.append(" --long-option ").append(optionSpec.longestName().replace("--", "")); + if (!optionSpec.shortestName().equals(optionSpec.longestName())) { + result.append(" --short-option ").append(optionSpec.shortestName().replace("-", "")); + } - if (!optionSpec.shortestName().equals(optionSpec.longestName())) { - result.append("complete -c ").append(scriptName); - result.append(" -n \"__fish_seen_subcommand_from ").append(commandDescriptor.commandName).append("\""); - if (!commandDescriptor.parentWithoutTopLevelCommand.equals("")) { - result.append(" -n '__fish_seen_subcommand_from ").append( - commandDescriptor.parentWithoutTopLevelCommand).append("'"); - } - result.append(" -s ").append(optionSpec.shortestName().replace("-", "")); - result.append(" -d '").append(optionDescription).append("'\n"); - } - } + if (optionSpec.completionCandidates() != null) { + result.append(" --no-files --arguments '").append(join(" ", extract(optionSpec.completionCandidates()))).append("' "); } + + String optionDescription = sanitizeFishDescription(optionSpec.description().length > 0 ? optionSpec.description()[0] : ""); + result.append(" -d '").append(optionDescription).append("'\n"); } - private static String sanitizeDescription(String description) { + private static String sanitizeFishDescription(String description) { return description.replace("'", "\\'"); } diff --git a/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp b/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp index 288d998c9..a0287213f 100644 --- a/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp +++ b/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp @@ -10,5 +10,16 @@ expect -re "(.+>)" set cmd "picocompletion-demo " set test "Tab should show sub1 and sub2 for '${cmd}'" +# for some reason, bash completion doesn't show sub1-alias and sub2-alias set candidates "sub1.*sub1-alias.*sub2.*sub2-alias.*" run_completion_test $cmd $test $candidates + +# now we show files in this test +# set cmd "picocompletion-demo sub1 " +# set test "Tab should not show completions for '${cmd}'" + +# there is completion from root level +# set cmd "picocompletion-demo sub1 -" +# set test "Tab should show sub1 options for '${cmd}'" +# set candidates "-h --candidates --candidates= (with candidates) --num (a number) --version" +# run_completion_test $cmd $test $candidates diff --git a/src/test/resources/basic.fish b/src/test/resources/basic.fish index 062e70134..d2e18458e 100644 --- a/src/test/resources/basic.fish +++ b/src/test/resources/basic.fish @@ -1,7 +1,5 @@ # root completion set -l root -complete -c basicExample -n "not __fish_seen_subcommand_from $root" -l timeUnit -f -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' -complete -c basicExample -n "not __fish_seen_subcommand_from $root" -s u -d '' -complete -c basicExample -n "not __fish_seen_subcommand_from $root" -l timeout -d '' -complete -c basicExample -n "not __fish_seen_subcommand_from $root" -s t -d '' +complete -c basicExample --condition "not __fish_seen_subcommand_from $root" --long-option timeUnit --short-option u --no-files --arguments 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c basicExample --condition "not __fish_seen_subcommand_from $root" --long-option timeout --short-option t -d '' diff --git a/src/test/resources/picocompletion-demo_completion.fish b/src/test/resources/picocompletion-demo_completion.fish index bb6282acd..8b3163cb8 100644 --- a/src/test/resources/picocompletion-demo_completion.fish +++ b/src/test/resources/picocompletion-demo_completion.fish @@ -1,68 +1,52 @@ # root completion set -l root -complete -c picocompletion-demo -n "not __fish_seen_subcommand_from $root" -l version -d '' -complete -c picocompletion-demo -n "not __fish_seen_subcommand_from $root" -s V -d '' -complete -c picocompletion-demo -n "not __fish_seen_subcommand_from $root" -l help -d '' -complete -c picocompletion-demo -n "not __fish_seen_subcommand_from $root" -s h -d '' +complete -c picocompletion-demo --condition "not __fish_seen_subcommand_from $root" --long-option version --short-option V -d '' +complete -c picocompletion-demo --condition "not __fish_seen_subcommand_from $root" --long-option help --short-option h -d '' # _picocli_picocompletion_demo completion set -l _picocli_picocompletion_demo sub1 sub1-alias sub2 sub2-alias -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" -a sub1 -d 'First level subcommand 1' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1" -l num -d 'a number' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1" -l str -d 'a String' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1" -l candidates -a 'aaa bbb ccc' -d 'with candidates' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" -a sub1-alias -d 'First level subcommand 1' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1-alias" -l num -d 'a number' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1-alias" -l str -d 'a String' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub1-alias" -l candidates -a 'aaa bbb ccc' -d 'with candidates' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" -a sub2 -d 'First level subcommand 2' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2" -l num2 -d 'another number' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2" -l directory -d 'a directory' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2" -s d -d 'a directory' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" -a sub2-alias -d 'First level subcommand 2' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2-alias" -l num2 -d 'another number' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2-alias" -l directory -d 'a directory' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2-alias" -s d -d 'a directory' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" --arguments sub1 -d 'First level subcommand 1' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub1" --long-option num -d 'a number' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub1" --long-option str -d 'a String' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub1" --long-option candidates --no-files --arguments 'aaa bbb ccc' -d 'with candidates' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" --arguments sub1-alias -d 'First level subcommand 1' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub1-alias" --long-option num -d 'a number' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub1-alias" --long-option str -d 'a String' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub1-alias" --long-option candidates --no-files --arguments 'aaa bbb ccc' -d 'with candidates' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" --arguments sub2 -d 'First level subcommand 2' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2" --long-option num2 -d 'another number' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2" --long-option directory --short-option d -d 'a directory' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" --arguments sub2-alias -d 'First level subcommand 2' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2-alias" --long-option num2 -d 'another number' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2-alias" --long-option directory --short-option d -d 'a directory' # _picocli_picocompletion_demo_sub2 completion set -l _picocli_picocompletion_demo_sub2 subsub1 sub2child1-alias subsub2 sub2child2-alias subsub3 sub2child3-alias -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a subsub1 -d 'Second level sub-subcommand 1' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub1" -n '__fish_seen_subcommand_from sub2' -l host -d 'a host' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub1" -n '__fish_seen_subcommand_from sub2' -s h -d 'a host' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a sub2child1-alias -d 'Second level sub-subcommand 1' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child1-alias" -n '__fish_seen_subcommand_from sub2' -l host -d 'a host' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child1-alias" -n '__fish_seen_subcommand_from sub2' -s h -d 'a host' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a subsub2 -d 'Second level sub-subcommand 2' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2' -l timeUnit -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2' -s u -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2' -l timeout -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2' -s t -d '' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a sub2child2-alias -d 'Second level sub-subcommand 2' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2' -l timeUnit -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2' -s u -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2' -l timeout -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2' -s t -d '' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a subsub3 -d 'Second level sub-subcommand 3' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" -n '__fish_seen_subcommand_from sub2' -a sub2child3-alias -d 'Second level sub-subcommand 3' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" --condition '__fish_seen_subcommand_from sub2' --arguments subsub1 -d 'Second level sub-subcommand 1' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from subsub1" --condition '__fish_seen_subcommand_from sub2' --long-option host --short-option h -d 'a host' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" --condition '__fish_seen_subcommand_from sub2' --arguments sub2child1-alias -d 'Second level sub-subcommand 1' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2child1-alias" --condition '__fish_seen_subcommand_from sub2' --long-option host --short-option h -d 'a host' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" --condition '__fish_seen_subcommand_from sub2' --arguments subsub2 -d 'Second level sub-subcommand 2' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from subsub2" --condition '__fish_seen_subcommand_from sub2' --long-option timeUnit --short-option u --no-files --arguments 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from subsub2" --condition '__fish_seen_subcommand_from sub2' --long-option timeout --short-option t -d '' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" --condition '__fish_seen_subcommand_from sub2' --arguments sub2child2-alias -d 'Second level sub-subcommand 2' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2child2-alias" --condition '__fish_seen_subcommand_from sub2' --long-option timeUnit --short-option u --no-files --arguments 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2child2-alias" --condition '__fish_seen_subcommand_from sub2' --long-option timeout --short-option t -d '' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" --condition '__fish_seen_subcommand_from sub2' --arguments subsub3 -d 'Second level sub-subcommand 3' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2" --condition '__fish_seen_subcommand_from sub2' --arguments sub2child3-alias -d 'Second level sub-subcommand 3' # _picocli_picocompletion_demo_sub2alias completion set -l _picocli_picocompletion_demo_sub2alias subsub1 sub2child1-alias subsub2 sub2child2-alias subsub3 sub2child3-alias -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a subsub1 -d 'Second level sub-subcommand 1' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub1" -n '__fish_seen_subcommand_from sub2-alias' -l host -d 'a host' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub1" -n '__fish_seen_subcommand_from sub2-alias' -s h -d 'a host' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a sub2child1-alias -d 'Second level sub-subcommand 1' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child1-alias" -n '__fish_seen_subcommand_from sub2-alias' -l host -d 'a host' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child1-alias" -n '__fish_seen_subcommand_from sub2-alias' -s h -d 'a host' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a subsub2 -d 'Second level sub-subcommand 2' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2-alias' -l timeUnit -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2-alias' -s u -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2-alias' -l timeout -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from subsub2" -n '__fish_seen_subcommand_from sub2-alias' -s t -d '' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a sub2child2-alias -d 'Second level sub-subcommand 2' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2-alias' -l timeUnit -a 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2-alias' -s u -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2-alias' -l timeout -d '' -complete -c picocompletion-demo -n "__fish_seen_subcommand_from sub2child2-alias" -n '__fish_seen_subcommand_from sub2-alias' -s t -d '' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a subsub3 -d 'Second level sub-subcommand 3' -complete -c picocompletion-demo -f -n "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" -n '__fish_seen_subcommand_from sub2-alias' -a sub2child3-alias -d 'Second level sub-subcommand 3' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" --condition '__fish_seen_subcommand_from sub2-alias' --arguments subsub1 -d 'Second level sub-subcommand 1' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from subsub1" --condition '__fish_seen_subcommand_from sub2-alias' --long-option host --short-option h -d 'a host' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" --condition '__fish_seen_subcommand_from sub2-alias' --arguments sub2child1-alias -d 'Second level sub-subcommand 1' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2child1-alias" --condition '__fish_seen_subcommand_from sub2-alias' --long-option host --short-option h -d 'a host' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" --condition '__fish_seen_subcommand_from sub2-alias' --arguments subsub2 -d 'Second level sub-subcommand 2' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from subsub2" --condition '__fish_seen_subcommand_from sub2-alias' --long-option timeUnit --short-option u --no-files --arguments 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from subsub2" --condition '__fish_seen_subcommand_from sub2-alias' --long-option timeout --short-option t -d '' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" --condition '__fish_seen_subcommand_from sub2-alias' --arguments sub2child2-alias -d 'Second level sub-subcommand 2' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2child2-alias" --condition '__fish_seen_subcommand_from sub2-alias' --long-option timeUnit --short-option u --no-files --arguments 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub2child2-alias" --condition '__fish_seen_subcommand_from sub2-alias' --long-option timeout --short-option t -d '' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" --condition '__fish_seen_subcommand_from sub2-alias' --arguments subsub3 -d 'Second level sub-subcommand 3' +complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo_sub2alias" --condition '__fish_seen_subcommand_from sub2-alias' --arguments sub2child3-alias -d 'Second level sub-subcommand 3' From 2f757283f09da70b26456ac5c1443fb50ca27086 Mon Sep 17 00:00:00 2001 From: serg-v Date: Sat, 25 Feb 2023 12:51:19 +0300 Subject: [PATCH 06/11] picocli fish completion: fixed root options --- src/main/java/picocli/AutoComplete.java | 1 + .../dejagnu.fishtests/completion/picocompletion-demo.exp | 8 ++++---- src/test/resources/picocompletion-demo_completion.fish | 7 ++----- 3 files changed, 7 insertions(+), 9 deletions(-) diff --git a/src/main/java/picocli/AutoComplete.java b/src/main/java/picocli/AutoComplete.java index 93d6dc44d..5254370ec 100644 --- a/src/main/java/picocli/AutoComplete.java +++ b/src/main/java/picocli/AutoComplete.java @@ -549,6 +549,7 @@ public static String fish(String scriptName, CommandLine commandLine) { for (CommandDescriptor descriptor : hierarchy) { if (descriptor.parentFunctionName.equals("")) { rootDescriptor = descriptor; + parentFunction = descriptor.functionName; continue; } if (!descriptor.parentFunctionName.equals(parentFunction)) { diff --git a/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp b/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp index a0287213f..b6f4fdfd9 100644 --- a/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp +++ b/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp @@ -19,7 +19,7 @@ run_completion_test $cmd $test $candidates # set test "Tab should not show completions for '${cmd}'" # there is completion from root level -# set cmd "picocompletion-demo sub1 -" -# set test "Tab should show sub1 options for '${cmd}'" -# set candidates "-h --candidates --candidates= (with candidates) --num (a number) --version" -# run_completion_test $cmd $test $candidates +set cmd "picocompletion-demo sub1 -" +set test "Tab should show sub1 options for '${cmd}'" +set candidates "--candidates.*--candidates=.*--num.*--str.*" +run_completion_test $cmd $test $candidates diff --git a/src/test/resources/picocompletion-demo_completion.fish b/src/test/resources/picocompletion-demo_completion.fish index 8b3163cb8..feccfd286 100644 --- a/src/test/resources/picocompletion-demo_completion.fish +++ b/src/test/resources/picocompletion-demo_completion.fish @@ -1,11 +1,8 @@ -# root completion -set -l root -complete -c picocompletion-demo --condition "not __fish_seen_subcommand_from $root" --long-option version --short-option V -d '' -complete -c picocompletion-demo --condition "not __fish_seen_subcommand_from $root" --long-option help --short-option h -d '' - # _picocli_picocompletion_demo completion set -l _picocli_picocompletion_demo sub1 sub1-alias sub2 sub2-alias +complete -c picocompletion-demo --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" --long-option version --short-option V -d '' +complete -c picocompletion-demo --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" --long-option help --short-option h -d '' complete -c picocompletion-demo --no-files --condition "not __fish_seen_subcommand_from $_picocli_picocompletion_demo" --arguments sub1 -d 'First level subcommand 1' complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub1" --long-option num -d 'a number' complete -c picocompletion-demo --condition "__fish_seen_subcommand_from sub1" --long-option str -d 'a String' From 811f4df11ec5b8c79b1f74e09ac0ae3f1ab2d9c2 Mon Sep 17 00:00:00 2001 From: serg-v Date: Sat, 25 Feb 2023 16:13:29 +0300 Subject: [PATCH 07/11] picocli fish completion: run fish dejagnu tests from java --- .github/workflows/dejagnu.yml | 22 +++ docs/man/index.html | 150 +++++++++--------- docs/zh/picocli-2.0-do-more-with-less.html | 150 +++++++++--------- ...icocli-2.0-groovy-scripts-on-steroids.html | 150 +++++++++--------- .../completion/basicExample.exp | 3 +- .../completion/picocompletion-demo.exp | 1 - src/test/dejagnu.fishtests/lib/completion.exp | 4 + src/test/dejagnu.fishtests/lib/library.exp | 4 +- src/test/dejagnu.fishtests/runCompletion | 3 + .../java/picocli/AutoCompleteDejaGnuTest.java | 14 +- 10 files changed, 268 insertions(+), 233 deletions(-) create mode 100644 .github/workflows/dejagnu.yml create mode 100755 src/test/dejagnu.fishtests/runCompletion diff --git a/.github/workflows/dejagnu.yml b/.github/workflows/dejagnu.yml new file mode 100644 index 000000000..b0364ecc4 --- /dev/null +++ b/.github/workflows/dejagnu.yml @@ -0,0 +1,22 @@ +name: DejaGnu Tests + +on: [ push, pull_request ] + +jobs: + test: + runs-on: ubuntu-latest + steps: + - name: Install Fish shell and DejaGnu + run: | + sudo apt-get update + sudo apt-get install -y fish dejagnu + - name: Check versions + run: | + fish --version + runtest --version + - name: Checkout + uses: actions/checkout@ac593985615ec2ede58e132d2e21d2b1cbd6127c # v2 + - name: Run DejaGnu fish tests + run: | + cd src/test/dejagnu.fishtests + ./runCompletion diff --git a/docs/man/index.html b/docs/man/index.html index d2a045cc5..ff8bc783e 100644 --- a/docs/man/index.html +++ b/docs/man/index.html @@ -435,81 +435,81 @@ #footer-text{color:rgba(0,0,0,.6);font-size:.9em}} @media amzn-kf8{#header,#content,#footnotes,#footer{padding:0}} - - - + + + diff --git a/docs/zh/picocli-2.0-do-more-with-less.html b/docs/zh/picocli-2.0-do-more-with-less.html index beba3896a..1e37c9a85 100644 --- a/docs/zh/picocli-2.0-do-more-with-less.html +++ b/docs/zh/picocli-2.0-do-more-with-less.html @@ -525,81 +525,81 @@ .CodeRay .change .change{color:#66f} .CodeRay .head .head{color:#f4f} - - - + + + diff --git a/docs/zh/picocli-2.0-groovy-scripts-on-steroids.html b/docs/zh/picocli-2.0-groovy-scripts-on-steroids.html index dd1f0061a..3001a2378 100644 --- a/docs/zh/picocli-2.0-groovy-scripts-on-steroids.html +++ b/docs/zh/picocli-2.0-groovy-scripts-on-steroids.html @@ -525,81 +525,81 @@ .CodeRay .change .change{color:#66f} .CodeRay .head .head{color:#f4f} - - - + + + diff --git a/src/test/dejagnu.fishtests/completion/basicExample.exp b/src/test/dejagnu.fishtests/completion/basicExample.exp index eee1b41dd..87b8ad714 100644 --- a/src/test/dejagnu.fishtests/completion/basicExample.exp +++ b/src/test/dejagnu.fishtests/completion/basicExample.exp @@ -19,6 +19,5 @@ run_completion_test $cmd $test $candidates set cmd "basicExample --timeUnit=" set test "Tab should show time unit enum values for '$cmd'" -#set candidates "1 2 3" -set candidates "\u2026timeUnit=DAYS \u2026timeUnit=MICROSECONDS \u2026timeUnit=MINUTES \u2026timeUnit=SECONDS\r\n\u2026timeUnit=HOURS \u2026timeUnit=MILLISECONDS \u2026timeUnit=NANOSECONDS " +set candidates ".*timeUnit=DAYS.*timeUnit=MICROSECONDS.*timeUnit=MINUTES.*timeUnit=SECONDS.*timeUnit=HOURS.*timeUnit=MILLISECONDS.*timeUnit=NANOSECONDS.*" run_completion_test $cmd $test $candidates diff --git a/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp b/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp index b6f4fdfd9..b7fe60c88 100644 --- a/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp +++ b/src/test/dejagnu.fishtests/completion/picocompletion-demo.exp @@ -18,7 +18,6 @@ run_completion_test $cmd $test $candidates # set cmd "picocompletion-demo sub1 " # set test "Tab should not show completions for '${cmd}'" -# there is completion from root level set cmd "picocompletion-demo sub1 -" set test "Tab should show sub1 options for '${cmd}'" set candidates "--candidates.*--candidates=.*--num.*--str.*" diff --git a/src/test/dejagnu.fishtests/lib/completion.exp b/src/test/dejagnu.fishtests/lib/completion.exp index c5df2c1ad..073f24663 100644 --- a/src/test/dejagnu.fishtests/lib/completion.exp +++ b/src/test/dejagnu.fishtests/lib/completion.exp @@ -1,4 +1,8 @@ exp_spawn fish --no-config expect -re "(.+>)" +# Set terminal size to my notebook's resolution +send "stty rows 53 cols 190\r" +expect -re "(.+>)" + source $::srcdir/lib/library.exp diff --git a/src/test/dejagnu.fishtests/lib/library.exp b/src/test/dejagnu.fishtests/lib/library.exp index 670de975f..e2fb3f33f 100644 --- a/src/test/dejagnu.fishtests/lib/library.exp +++ b/src/test/dejagnu.fishtests/lib/library.exp @@ -1,11 +1,11 @@ proc run_completion_test {cmd test candidates} { + exp_internal 1 send "${cmd}\t" expect { -re "(\n${candidates}\u001b)" { pass $test } timeout { fail $test } } - puts "###Output" - puts "$expect_out(1,string)" + exp_internal 0 send "\x03" expect ">" } diff --git a/src/test/dejagnu.fishtests/runCompletion b/src/test/dejagnu.fishtests/runCompletion new file mode 100755 index 000000000..a475f1f18 --- /dev/null +++ b/src/test/dejagnu.fishtests/runCompletion @@ -0,0 +1,3 @@ +#!/bin/bash +mkdir -p log +runtest --outdir log --tool completion diff --git a/src/test/java/picocli/AutoCompleteDejaGnuTest.java b/src/test/java/picocli/AutoCompleteDejaGnuTest.java index 0c2363c98..280baeb50 100644 --- a/src/test/java/picocli/AutoCompleteDejaGnuTest.java +++ b/src/test/java/picocli/AutoCompleteDejaGnuTest.java @@ -67,11 +67,19 @@ public void tryRunDejaGnuCompletionTests() throws Exception { // ignores test if dejagnu not installed org.junit.Assume.assumeTrue("dejagnu must be installed to run this test", isDejaGnuInstalled()); - runDejaGnuCompletionTests(); + runDejaGnuCompletionTests("src/test/dejagnu.tests"); } - private void runDejaGnuCompletionTests() throws Exception { - final File testDir = new File("src/test/dejagnu.tests"); + @Test + public void tryRunFishDejaGnuCompletionTests() throws Exception { + // ignores test if dejagnu not installed + org.junit.Assume.assumeTrue("dejagnu must be installed to run this test", isDejaGnuInstalled()); + runDejaGnuCompletionTests("src/test/dejagnu.fishtests"); + } + + + private void runDejaGnuCompletionTests(String pathname) throws Exception { + final File testDir = new File(pathname); assertTrue(testDir.getAbsolutePath() + " should exist", testDir.exists()); File runCompletionScript = new File(testDir, "runCompletion"); assertTrue(runCompletionScript.getAbsolutePath() + " should exist", runCompletionScript.exists()); From 3479683b70119699a90cbea068b17ccd9448e898 Mon Sep 17 00:00:00 2001 From: serg-v Date: Sat, 25 Feb 2023 16:38:38 +0300 Subject: [PATCH 08/11] picocli fish completion: fish test fix --- src/test/resources/basic.fish | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/test/resources/basic.fish b/src/test/resources/basic.fish index d2e18458e..2ac7ce4ef 100644 --- a/src/test/resources/basic.fish +++ b/src/test/resources/basic.fish @@ -1,5 +1,5 @@ -# root completion -set -l root -complete -c basicExample --condition "not __fish_seen_subcommand_from $root" --long-option timeUnit --short-option u --no-files --arguments 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' -complete -c basicExample --condition "not __fish_seen_subcommand_from $root" --long-option timeout --short-option t -d '' +# _picocli_basicExample completion +set -l _picocli_basicExample +complete -c basicExample --condition "not __fish_seen_subcommand_from $_picocli_basicExample" --long-option timeUnit --short-option u --no-files --arguments 'NANOSECONDS MICROSECONDS MILLISECONDS SECONDS MINUTES HOURS DAYS' -d '' +complete -c basicExample --condition "not __fish_seen_subcommand_from $_picocli_basicExample" --long-option timeout --short-option t -d '' From cf51a16a2cc229592a6a83c59694098743029685 Mon Sep 17 00:00:00 2001 From: serg-v Date: Sat, 25 Feb 2023 16:42:37 +0300 Subject: [PATCH 09/11] picocli fish completion: install fish 3.6.0 --- .github/workflows/dejagnu.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/workflows/dejagnu.yml b/.github/workflows/dejagnu.yml index b0364ecc4..7f87820a5 100644 --- a/.github/workflows/dejagnu.yml +++ b/.github/workflows/dejagnu.yml @@ -8,6 +8,7 @@ jobs: steps: - name: Install Fish shell and DejaGnu run: | + sudo apt-add-repository -y ppa:fish-shell/release-3 sudo apt-get update sudo apt-get install -y fish dejagnu - name: Check versions From bb4d76a28adaff62ae15fda77a1c669ee06c5f8d Mon Sep 17 00:00:00 2001 From: serg-v Date: Sat, 25 Feb 2023 16:44:12 +0300 Subject: [PATCH 10/11] picocli fish completion: added bash tests --- .github/workflows/dejagnu.yml | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.github/workflows/dejagnu.yml b/.github/workflows/dejagnu.yml index 7f87820a5..7e7e696b7 100644 --- a/.github/workflows/dejagnu.yml +++ b/.github/workflows/dejagnu.yml @@ -21,3 +21,7 @@ jobs: run: | cd src/test/dejagnu.fishtests ./runCompletion + - name: Run DejaGnu bash tests + run: | + cd src/test/dejagnu.tests + ./runCompletion From d5c79bdb59cdb91a3c6ced60f3dc1f28ffc7d53b Mon Sep 17 00:00:00 2001 From: serg-v Date: Sat, 25 Feb 2023 21:08:04 +0300 Subject: [PATCH 11/11] picocli fish completion: added tcllib to github workflow --- .github/workflows/dejagnu.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/dejagnu.yml b/.github/workflows/dejagnu.yml index 7e7e696b7..d71fafef9 100644 --- a/.github/workflows/dejagnu.yml +++ b/.github/workflows/dejagnu.yml @@ -10,7 +10,7 @@ jobs: run: | sudo apt-add-repository -y ppa:fish-shell/release-3 sudo apt-get update - sudo apt-get install -y fish dejagnu + sudo apt-get install -y fish dejagnu tcllib - name: Check versions run: | fish --version