8142384: JShell tool: New command: /imports, /i which show the list of imported packages or classes, etc..
Reviewed-by: rfield, jlahoda
This commit is contained in:
parent
9bf5e9c8f4
commit
fadea54488
@ -675,6 +675,9 @@ public class JShellTool {
|
||||
registerCommand(new Command("/classes", "/c", null, "list the declared classes",
|
||||
arg -> cmdClasses(),
|
||||
EMPTY_COMPLETION_PROVIDER));
|
||||
registerCommand(new Command("/imports", "/i", null, "list the imported items",
|
||||
arg -> cmdImports(),
|
||||
EMPTY_COMPLETION_PROVIDER));
|
||||
registerCommand(new Command("/exit", "/x", null, "exit the REPL",
|
||||
arg -> cmdExit(),
|
||||
EMPTY_COMPLETION_PROVIDER));
|
||||
@ -1256,6 +1259,12 @@ public class JShellTool {
|
||||
}
|
||||
}
|
||||
|
||||
private void cmdImports() {
|
||||
state.imports().forEach(ik -> {
|
||||
hard(" import %s%s", ik.isStatic() ? "static " : "", ik.fullname());
|
||||
});
|
||||
}
|
||||
|
||||
private void cmdUseHistoryEntry(int index) {
|
||||
List<Snippet> keys = state.snippets();
|
||||
if (index < 0)
|
||||
|
@ -68,6 +68,29 @@ public class ImportSnippet extends PersistentSnippet {
|
||||
return key().name();
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* The qualified name of the import. For any imports
|
||||
* ({@link jdk.jshell.Snippet.SubKind#TYPE_IMPORT_ON_DEMAND_SUBKIND},
|
||||
* ({@link jdk.jshell.Snippet.SubKind#STATIC_IMPORT_ON_DEMAND_SUBKIND}),
|
||||
* ({@link jdk.jshell.Snippet.SubKind#SINGLE_TYPE_IMPORT_SUBKIND} or
|
||||
* ({@link jdk.jshell.Snippet.SubKind#SINGLE_STATIC_IMPORT_SUBKIND})
|
||||
* that is the full specifier including any
|
||||
* qualifiers and the asterisks.
|
||||
* @return the fullname of the import
|
||||
*/
|
||||
public String fullname() {
|
||||
return fullname;
|
||||
}
|
||||
|
||||
/**
|
||||
* When this snippet represent static import, this method returns true.
|
||||
* @return true when this snippet represent static import, otherwise false
|
||||
*/
|
||||
public boolean isStatic() {
|
||||
return isStatic;
|
||||
}
|
||||
|
||||
/**** internal access ****/
|
||||
|
||||
@Override
|
||||
@ -75,10 +98,6 @@ public class ImportSnippet extends PersistentSnippet {
|
||||
return (ImportKey) super.key();
|
||||
}
|
||||
|
||||
boolean isStatic() {
|
||||
return isStatic;
|
||||
}
|
||||
|
||||
@Override
|
||||
String importLine(JShell state) {
|
||||
return source();
|
||||
|
@ -468,6 +468,22 @@ public class JShell implements AutoCloseable {
|
||||
.collect(collectingAndThen(toList(), Collections::unmodifiableList));
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the active import snippets.
|
||||
* This convenience method is equivalent to <code>snippets()</code> filtered for
|
||||
* {@link jdk.jshell.Snippet.Status#isActive status(snippet).isActive}
|
||||
* <code>&& snippet.kind() == Kind.IMPORT</code>
|
||||
* and cast to ImportSnippet.
|
||||
* @return the active declared import declarations.
|
||||
* @throws IllegalStateException if this JShell instance is closed.
|
||||
*/
|
||||
public List<ImportSnippet> imports() throws IllegalStateException {
|
||||
return snippets().stream()
|
||||
.filter(sn -> status(sn).isActive && sn.kind() == Snippet.Kind.IMPORT)
|
||||
.map(sn -> (ImportSnippet) sn)
|
||||
.collect(collectingAndThen(toList(), Collections::unmodifiableList));
|
||||
}
|
||||
|
||||
/**
|
||||
* Return the status of the snippet.
|
||||
* This is updated either because of an explicit <code>eval()</code> call or
|
||||
|
@ -27,11 +27,10 @@ import java.io.PrintStream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Predicate;
|
||||
import java.util.regex.Matcher;
|
||||
import java.util.regex.Pattern;
|
||||
@ -62,6 +61,7 @@ public class ReplToolTesting {
|
||||
private Map<String, VariableInfo> variables;
|
||||
private Map<String, MethodInfo> methods;
|
||||
private Map<String, ClassInfo> classes;
|
||||
private Map<String, ImportInfo> imports;
|
||||
private boolean isDefaultStartUp = true;
|
||||
|
||||
public JShellTool repl = null;
|
||||
@ -127,6 +127,10 @@ public class ReplToolTesting {
|
||||
return assertMembers("Classes", classes);
|
||||
}
|
||||
|
||||
public Consumer<String> assertImports() {
|
||||
return assertMembers("Imports", imports);
|
||||
}
|
||||
|
||||
public String getCommandOutput() {
|
||||
String s = cmdout.toString();
|
||||
cmdout.reset();
|
||||
@ -184,9 +188,21 @@ public class ReplToolTesting {
|
||||
variables = new HashMap<>();
|
||||
methods = new HashMap<>();
|
||||
classes = new HashMap<>();
|
||||
imports = new HashMap<>();
|
||||
if (isDefaultStartUp) {
|
||||
methods.put("printf (String,Object...)void",
|
||||
new MethodInfo("", "(String,Object...)void", "printf"));
|
||||
imports.putAll(
|
||||
Stream.of(
|
||||
"java.util.*",
|
||||
"java.io.*",
|
||||
"java.math.*",
|
||||
"java.net.*",
|
||||
"java.util.concurrent.*",
|
||||
"java.util.prefs.*",
|
||||
"java.util.regex.*")
|
||||
.map(s -> new ImportInfo("", "", s))
|
||||
.collect(Collectors.toMap(Object::toString, Function.identity())));
|
||||
}
|
||||
}
|
||||
|
||||
@ -300,6 +316,19 @@ public class ReplToolTesting {
|
||||
addKey(after, clazz);
|
||||
}
|
||||
|
||||
public void loadImport(boolean after, String src, String type, String name) {
|
||||
ImportInfo i = new ImportInfo(src, type, name);
|
||||
addKey(after, i, imports);
|
||||
addKey(after, i);
|
||||
}
|
||||
|
||||
public void assertImport(boolean after, String src, String type, String name) {
|
||||
ImportInfo i = new ImportInfo(src, type, name);
|
||||
assertCommandCheckOutput(after, src, i.checkOutput());
|
||||
addKey(after, i, imports);
|
||||
addKey(after, i);
|
||||
}
|
||||
|
||||
private <T extends MemberInfo> void addKey(boolean after, T memberInfo, Map<String, T> map) {
|
||||
if (after) {
|
||||
map.entrySet().removeIf(e -> e.getValue().equals(memberInfo));
|
||||
@ -347,6 +376,10 @@ public class ReplToolTesting {
|
||||
dropKey(after, cmd, name, classes);
|
||||
}
|
||||
|
||||
public void dropImport(boolean after, String cmd, String name) {
|
||||
dropKey(after, cmd, name, imports);
|
||||
}
|
||||
|
||||
public void assertCommand(boolean after, String cmd, String out) {
|
||||
assertCommand(after, cmd, out, "", null, "", "");
|
||||
}
|
||||
@ -580,6 +613,31 @@ public class ReplToolTesting {
|
||||
}
|
||||
}
|
||||
|
||||
public static class ImportInfo extends MemberInfo {
|
||||
public ImportInfo(String source, String type, String fullname) {
|
||||
super(source, type, fullname);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Consumer<String> checkOutput() {
|
||||
return s -> assertTrue("".equals(s), "Expected: '', actual: " + s);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (o instanceof ImportInfo) {
|
||||
ImportInfo i = (ImportInfo) o;
|
||||
return name.equals(i.name) && type.equals(i.type);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return String.format("import %s%s", type.equals("static") ? "static " : "", name);
|
||||
}
|
||||
}
|
||||
|
||||
class WaitingTestingInputStream extends TestingInputStream {
|
||||
|
||||
@Override
|
||||
|
@ -24,7 +24,6 @@
|
||||
/*
|
||||
* @test
|
||||
* @summary Tests for Basic tests for REPL tool
|
||||
* @ignore 8139873
|
||||
* @library /tools/lib
|
||||
* @build KullaTesting TestingInputStream ToolBox Compiler
|
||||
* @run testng ToolBasicTest
|
||||
@ -139,7 +138,13 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
(a) -> assertCommand(a, "class A {}\u0003", ""),
|
||||
(a) -> assertCommandCheckOutput(a, "/c", assertClasses()),
|
||||
(a) -> assertClass(a, "interface A {}", "interface", "A"),
|
||||
(a) -> assertCommandCheckOutput(a, "/c", assertClasses())
|
||||
(a) -> assertCommandCheckOutput(a, "/c", assertClasses()),
|
||||
(a) -> assertCommand(a, "import java.util.stream." + s, ""),
|
||||
interrupt,
|
||||
(a) -> assertCommand(a, "import java.util.stream.\u0003", ""),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports()),
|
||||
(a) -> assertImport(a, "import java.util.stream.Stream", "", "java.util.stream.Stream"),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports())
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -364,6 +369,35 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
);
|
||||
}
|
||||
|
||||
public void defineImports() {
|
||||
test(
|
||||
(a) -> assertCommandCheckOutput(a, "/l", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/list", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports()),
|
||||
(a) -> assertCommandCheckOutput(a, "/imports", assertImports()),
|
||||
(a) -> assertImport(a, "import java.util.stream.Stream;", "", "java.util.stream.Stream"),
|
||||
(a) -> assertCommandCheckOutput(a, "/l", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/list", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports()),
|
||||
(a) -> assertCommandCheckOutput(a, "/imports", assertImports()),
|
||||
(a) -> assertImport(a, "import java.util.stream.*;", "", "java.util.stream.*"),
|
||||
(a) -> assertCommandCheckOutput(a, "/l", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/list", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports()),
|
||||
(a) -> assertCommandCheckOutput(a, "/imports", assertImports()),
|
||||
(a) -> assertImport(a, "import static java.lang.Math.PI;", "static", "java.lang.Math.PI"),
|
||||
(a) -> assertCommandCheckOutput(a, "/l", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/list", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports()),
|
||||
(a) -> assertCommandCheckOutput(a, "/imports", assertImports()),
|
||||
(a) -> assertImport(a, "import static java.lang.Math.*;", "static", "java.lang.Math.*"),
|
||||
(a) -> assertCommandCheckOutput(a, "/l", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/list", assertList()),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports()),
|
||||
(a) -> assertCommandCheckOutput(a, "/imports", assertImports())
|
||||
);
|
||||
}
|
||||
|
||||
public void testClasspathDirectory() {
|
||||
Compiler compiler = new Compiler();
|
||||
Path outDir = Paths.get("testClasspathDirectory");
|
||||
@ -443,10 +477,13 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
(a) -> assertCommandCheckOutput(a, "/m", assertMethods()),
|
||||
(a) -> assertClass(a, "class A { }", "class", "A"),
|
||||
(a) -> assertCommandCheckOutput(a, "/c", assertClasses()),
|
||||
(a) -> assertImport(a, "import java.util.stream.*;", "", "java.util.stream.*"),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports()),
|
||||
(a) -> assertReset(a, "/reset"),
|
||||
(a) -> assertCommandCheckOutput(a, "/v", assertVariables()),
|
||||
(a) -> assertCommandCheckOutput(a, "/m", assertMethods()),
|
||||
(a) -> assertCommandCheckOutput(a, "/c", assertClasses())
|
||||
(a) -> assertCommandCheckOutput(a, "/c", assertClasses()),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports())
|
||||
);
|
||||
}
|
||||
|
||||
@ -455,22 +492,26 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
Path path = compiler.getPath("testOpen.repl");
|
||||
compiler.writeToFile(path,
|
||||
"int a = 10;\ndouble x = 20;\ndouble a = 10;\n" +
|
||||
"class A { public String toString() { return \"A\"; } }");
|
||||
"class A { public String toString() { return \"A\"; } }\nimport java.util.stream.*;");
|
||||
for (String s : new String[]{"/o", "/open"}) {
|
||||
test(
|
||||
(a) -> assertCommand(a, s + " " + path.toString(), ""),
|
||||
(a) -> assertCommand(a, "a", "| Variable a of type double has value 10.0\n"),
|
||||
(a) -> evaluateExpression(a, "A", "new A();", "\"A\""),
|
||||
(a) -> evaluateExpression(a, "long", "Stream.of(\"A\").count();", "1"),
|
||||
(a) -> {
|
||||
loadVariable(a, "double", "x", "20.0", "20.0");
|
||||
loadVariable(a, "double", "a", "10.0", "10.0");
|
||||
loadVariable(a, "A", "$6", "new A();", "A");
|
||||
loadVariable(a, "A", "$7", "new A();", "A");
|
||||
loadVariable(a, "long", "$8", "Stream.of(\"A\").count();", "1");
|
||||
loadClass(a, "class A { public String toString() { return \"A\"; } }",
|
||||
"class", "A");
|
||||
loadImport(a, "import java.util.stream.*;", "", "java.util.stream.*");
|
||||
assertCommandCheckOutput(a, "/c", assertClasses());
|
||||
},
|
||||
(a) -> assertCommandCheckOutput(a, "/m", assertMethods()),
|
||||
(a) -> assertCommandCheckOutput(a, "/v", assertVariables())
|
||||
(a) -> assertCommandCheckOutput(a, "/v", assertVariables()),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports())
|
||||
);
|
||||
Path unknown = compiler.getPath("UNKNOWN.repl");
|
||||
test(
|
||||
@ -536,6 +577,7 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
(a) -> assertVariable(a, "int", "a"),
|
||||
(a) -> assertVariable(a, "double", "b", "10", "10.0"),
|
||||
(a) -> assertMethod(a, "void f() {}", "()V", "f"),
|
||||
(a) -> assertImport(a, "import java.util.stream.*;", "", "java.util.stream.*"),
|
||||
(a) -> assertCommand(a, "/s " + startUpFile.toString(), null),
|
||||
(a) -> assertCommand(a, "/setstart " + startUpFile.toString(), null)
|
||||
);
|
||||
@ -549,10 +591,12 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
loadVariable(a, "int", "a");
|
||||
loadVariable(a, "double", "b", "10.0", "10.0");
|
||||
loadMethod(a, "void f() {}", "()void", "f");
|
||||
loadImport(a, "import java.util.stream.*;", "", "java.util.stream.*");
|
||||
assertCommandCheckOutput(a, "/c", assertClasses());
|
||||
},
|
||||
(a) -> assertCommandCheckOutput(a, "/v", assertVariables()),
|
||||
(a) -> assertCommandCheckOutput(a, "/m", assertMethods())
|
||||
(a) -> assertCommandCheckOutput(a, "/m", assertMethods()),
|
||||
(a) -> assertCommandCheckOutput(a, "/i", assertImports())
|
||||
);
|
||||
} finally {
|
||||
removeStartup();
|
||||
@ -768,9 +812,12 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
a -> dropMethod(a, drop + " 2", "b ()I"),
|
||||
a -> assertClass(a, "class A {}", "class", "A"),
|
||||
a -> dropClass(a, drop + " 3", "class A"),
|
||||
a -> assertImport(a, "import java.util.stream.*;", "", "java.util.stream.*"),
|
||||
a -> dropImport(a, drop + " 4", "import java.util.stream.*"),
|
||||
a -> assertCommandCheckOutput(a, "/v", assertVariables()),
|
||||
a -> assertCommandCheckOutput(a, "/m", assertMethods()),
|
||||
a -> assertCommandCheckOutput(a, "/c", assertClasses())
|
||||
a -> assertCommandCheckOutput(a, "/c", assertClasses()),
|
||||
a -> assertCommandCheckOutput(a, "/i", assertImports())
|
||||
);
|
||||
test(false, new String[]{"-nostartup"},
|
||||
a -> assertVariable(a, "int", "a"),
|
||||
@ -781,7 +828,8 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
a -> dropClass(a, drop + " A", "class A"),
|
||||
a -> assertCommandCheckOutput(a, "/v", assertVariables()),
|
||||
a -> assertCommandCheckOutput(a, "/m", assertMethods()),
|
||||
a -> assertCommandCheckOutput(a, "/c", assertClasses())
|
||||
a -> assertCommandCheckOutput(a, "/c", assertClasses()),
|
||||
a -> assertCommandCheckOutput(a, "/i", assertImports())
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -814,7 +862,8 @@ public class ToolBasicTest extends ReplToolTesting {
|
||||
a -> assertCommandCheckOutput(a, drop + " a", check),
|
||||
a -> assertCommandCheckOutput(a, "/v", assertVariables()),
|
||||
a -> assertCommandCheckOutput(a, "/m", assertMethods()),
|
||||
a -> assertCommandCheckOutput(a, "/c", assertClasses())
|
||||
a -> assertCommandCheckOutput(a, "/c", assertClasses()),
|
||||
a -> assertCommandCheckOutput(a, "/i", assertImports())
|
||||
);
|
||||
test(
|
||||
a -> assertMethod(a, "int a() { return 0; }", "()int", "a"),
|
||||
|
Loading…
Reference in New Issue
Block a user