Skip to content

Commit aa74ea2

Browse files
MJ Gallegojvalkeal
MJ Gallego
authored andcommitted
Completion proposal support for complete jline parameter
- to allow completing single argument with multiple tab clicks, for example file paths. - Backport #512 - Fixes #834
1 parent 1350f61 commit aa74ea2

File tree

3 files changed

+34
-14
lines changed

3 files changed

+34
-14
lines changed

spring-shell-autoconfigure/src/main/java/org/springframework/shell/boot/CompleterAutoConfiguration.java

+1-1
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ public void complete(LineReader reader, ParsedLine line, List<Candidate> candida
6363
p.description(),
6464
null,
6565
null,
66-
true)
66+
p.complete())
6767
)
6868
.forEach(candidates::add);
6969
}

spring-shell-core/src/main/java/org/springframework/shell/CompletionProposal.java

+16
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,12 @@ public class CompletionProposal {
4949
*/
5050
private boolean dontQuote = false;
5151

52+
/**
53+
* Whether the proposal cant be completed further. By setting complete to false then it will not append an space
54+
* making it easier to continue tab completion
55+
*/
56+
private boolean complete = true;
57+
5258
public CompletionProposal(String value) {
5359
this.value = this.displayText = value;
5460
}
@@ -89,6 +95,16 @@ public CompletionProposal category(String category) {
8995
return this;
9096
}
9197

98+
public CompletionProposal complete(boolean complete) {
99+
this.complete = complete;
100+
return this;
101+
}
102+
103+
public boolean complete() {
104+
return complete;
105+
}
106+
107+
92108
public CompletionProposal dontQuote(boolean dontQuote) {
93109
this.dontQuote = dontQuote;
94110
return this;

spring-shell-standard/src/main/java/org/springframework/shell/standard/FileValueProvider.java

+17-13
Original file line numberDiff line numberDiff line change
@@ -41,19 +41,23 @@ public class FileValueProvider implements ValueProvider {
4141

4242
@Override
4343
public List<CompletionProposal> complete(CompletionContext completionContext) {
44-
String input = completionContext.currentWordUpToCursor();
45-
int lastSlash = input.lastIndexOf(File.separatorChar);
46-
Path dir = lastSlash > -1 ? Paths.get(input.substring(0, lastSlash+1)) : Paths.get("");
47-
String prefix = input.substring(lastSlash + 1, input.length());
44+
String input = completionContext.currentWordUpToCursor();
45+
int lastSlash = input.lastIndexOf(File.separatorChar);
46+
Path dir = lastSlash > -1 ? Paths.get(input.substring(0, lastSlash + 1)) : Paths.get("");
47+
String prefix = input.substring(lastSlash + 1);
4848

49-
try {
50-
return Files
51-
.find(dir, 1, (p, a) -> p.getFileName() != null && p.getFileName().toString().startsWith(prefix),
52-
FOLLOW_LINKS)
53-
.map(p -> new CompletionProposal(p.toString()))
54-
.collect(Collectors.toList());
55-
} catch (IOException e) {
56-
throw new UncheckedIOException(e);
57-
}
49+
try {
50+
return Files
51+
.find(dir, 1, (p, a) -> p.getFileName() != null && p.getFileName().toString().startsWith(prefix),
52+
FOLLOW_LINKS)
53+
.map(p -> {
54+
boolean directory = Files.isDirectory(p);
55+
String value = p.toString() + (directory ? File.separatorChar : "");
56+
return new CompletionProposal(value).complete(!directory);
57+
})
58+
.collect(Collectors.toList());
59+
} catch (IOException e) {
60+
throw new UncheckedIOException(e);
61+
}
5862
}
5963
}

0 commit comments

Comments
 (0)