From 39f2f16a6ba92addb19f523fa38e45f153b2b464 Mon Sep 17 00:00:00 2001 From: Pavel Vojtechovsky Date: Thu, 29 Jun 2017 22:53:46 +0200 Subject: [PATCH 1/3] test type access and type arguments --- src/test/java/spoon/test/template/TemplateTest.java | 4 ++++ .../testclasses/TypeReferenceClassAccessTemplate.java | 6 ++++++ 2 files changed, 10 insertions(+) diff --git a/src/test/java/spoon/test/template/TemplateTest.java b/src/test/java/spoon/test/template/TemplateTest.java index fae101d4100..4f2fe4bd933 100644 --- a/src/test/java/spoon/test/template/TemplateTest.java +++ b/src/test/java/spoon/test/template/TemplateTest.java @@ -1041,5 +1041,9 @@ public void substituteTypeAccessReference() throws Exception { assertEquals("spoon.test.template.TypeReferenceClassAccess.Example", method.getParameters().get(0).getType().toString()); assertEquals("o = spoon.test.template.TypeReferenceClassAccess.Example.out", method.getBody().getStatement(0).toString()); assertEquals("spoon.test.template.TypeReferenceClassAccess.Example ret = new spoon.test.template.TypeReferenceClassAccess.Example()", method.getBody().getStatement(1).toString()); + assertEquals("o = spoon.test.template.TypeReferenceClassAccess.Example.currentTimeMillis()", method.getBody().getStatement(2).toString()); + assertEquals("o = spoon.test.template.TypeReferenceClassAccess.Example.class", method.getBody().getStatement(3).toString()); + assertEquals("o = (o) instanceof spoon.test.template.TypeReferenceClassAccess.Example", method.getBody().getStatement(4).toString()); + assertEquals("java.util.function.Supplier p = spoon.test.template.TypeReferenceClassAccess.Example::currentTimeMillis", method.getBody().getStatement(5).toString()); } } diff --git a/src/test/java/spoon/test/template/testclasses/TypeReferenceClassAccessTemplate.java b/src/test/java/spoon/test/template/testclasses/TypeReferenceClassAccessTemplate.java index 9970681ff0f..d04676d2098 100644 --- a/src/test/java/spoon/test/template/testclasses/TypeReferenceClassAccessTemplate.java +++ b/src/test/java/spoon/test/template/testclasses/TypeReferenceClassAccessTemplate.java @@ -1,5 +1,7 @@ package spoon.test.template.testclasses; +import java.util.function.Supplier; + import spoon.reflect.reference.CtTypeReference; import spoon.template.ExtensionTemplate; import spoon.template.Local; @@ -11,6 +13,10 @@ public class TypeReferenceClassAccessTemplate extends ExtensionTemplate { $Type$ someMethod($Type$ param) { o = $Type$.out; $Type$ ret = new $Type$(); + o = $Type$.currentTimeMillis(); + o = $Type$.class; + o = o instanceof $Type$; + Supplier p = $Type$::currentTimeMillis; return ret; } From b6fa2036caca57eb3e4e8fc8177ce2553b1057e7 Mon Sep 17 00:00:00 2001 From: Pavel Vojtechovsky Date: Sun, 24 Sep 2017 10:09:45 +0200 Subject: [PATCH 2/3] fix: printing of type access in context without generics --- .../visitor/DefaultJavaPrettyPrinter.java | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-) diff --git a/src/main/java/spoon/reflect/visitor/DefaultJavaPrettyPrinter.java b/src/main/java/spoon/reflect/visitor/DefaultJavaPrettyPrinter.java index bd46338d4c2..2da9d841f82 100644 --- a/src/main/java/spoon/reflect/visitor/DefaultJavaPrettyPrinter.java +++ b/src/main/java/spoon/reflect/visitor/DefaultJavaPrettyPrinter.java @@ -18,6 +18,7 @@ import spoon.SpoonException; import spoon.compiler.Environment; +import spoon.reflect.code.BinaryOperatorKind; import spoon.reflect.code.CtAnnotationFieldAccess; import spoon.reflect.code.CtArrayAccess; import spoon.reflect.code.CtArrayRead; @@ -482,7 +483,12 @@ public void visitCtBinaryOperator(CtBinaryOperator operator) { printer.write(" "); printer.write(OperatorHelper.getOperatorText(operator.getKind())); printer.write(" "); - scan(operator.getRightHandOperand()); + try (Writable _context = context.modify()) { + if (operator.getKind() == BinaryOperatorKind.INSTANCEOF) { + _context.ignoreGenerics(true); + } + scan(operator.getRightHandOperand()); + } exitCtExpression(operator); } @@ -778,7 +784,7 @@ public void visitCtFieldWrite(CtFieldWrite fieldWrite) { private void printCtFieldAccess(CtFieldAccess f) { enterCtExpression(f); try (Writable _context = context.modify()) { - if (f.getVariable().isStatic() && f.getTarget() instanceof CtTypeAccess) { + if ((f.getVariable().isStatic() || "class".equals(f.getVariable().getSimpleName())) && f.getTarget() instanceof CtTypeAccess) { _context.ignoreGenerics(true); } CtExpression target = f.getTarget(); @@ -1374,7 +1380,12 @@ public void visitCtLambda(CtLambda lambda) { @Override public > void visitCtExecutableReferenceExpression(CtExecutableReferenceExpression expression) { enterCtExpression(expression); - scan(expression.getTarget()); + try (Writable _context = context.modify()) { + if (expression.getExecutable().isStatic()) { + _context.ignoreGenerics(true); + } + scan(expression.getTarget()); + } printer.write("::"); if (expression.getExecutable().isConstructor()) { printer.write("new"); From 81313da2600312fbe337bdcadead615be0ca4b8a Mon Sep 17 00:00:00 2001 From: Pavel Vojtechovsky Date: Sun, 24 Sep 2017 11:05:34 +0200 Subject: [PATCH 3/3] fix: force wildcard generics --- .../spoon/reflect/visitor/DefaultJavaPrettyPrinter.java | 2 +- .../java/spoon/reflect/visitor/ElementPrinterHelper.java | 6 +++++- src/main/java/spoon/reflect/visitor/PrintingContext.java | 8 ++++++++ src/test/java/spoon/test/template/TemplateTest.java | 2 +- 4 files changed, 15 insertions(+), 3 deletions(-) diff --git a/src/main/java/spoon/reflect/visitor/DefaultJavaPrettyPrinter.java b/src/main/java/spoon/reflect/visitor/DefaultJavaPrettyPrinter.java index 2da9d841f82..28fa4ae2d72 100644 --- a/src/main/java/spoon/reflect/visitor/DefaultJavaPrettyPrinter.java +++ b/src/main/java/spoon/reflect/visitor/DefaultJavaPrettyPrinter.java @@ -485,7 +485,7 @@ public void visitCtBinaryOperator(CtBinaryOperator operator) { printer.write(" "); try (Writable _context = context.modify()) { if (operator.getKind() == BinaryOperatorKind.INSTANCEOF) { - _context.ignoreGenerics(true); + _context.forceWildcardGenerics(true); } scan(operator.getRightHandOperand()); } diff --git a/src/main/java/spoon/reflect/visitor/ElementPrinterHelper.java b/src/main/java/spoon/reflect/visitor/ElementPrinterHelper.java index fb166564702..e669a323221 100644 --- a/src/main/java/spoon/reflect/visitor/ElementPrinterHelper.java +++ b/src/main/java/spoon/reflect/visitor/ElementPrinterHelper.java @@ -232,7 +232,11 @@ public void writeActualTypeArguments(CtActualTypeContainer ctGenericElementRefer for (CtTypeReference argument : arguments) { if (!argument.isImplicit()) { lp.printSeparatorIfAppropriate(); - prettyPrinter.scan(argument); + if (prettyPrinter.context.forceWildcardGenerics()) { + printer.write('?'); + } else { + prettyPrinter.scan(argument); + } } } } diff --git a/src/main/java/spoon/reflect/visitor/PrintingContext.java b/src/main/java/spoon/reflect/visitor/PrintingContext.java index dae8a28e9d8..802beb424bb 100644 --- a/src/main/java/spoon/reflect/visitor/PrintingContext.java +++ b/src/main/java/spoon/reflect/visitor/PrintingContext.java @@ -31,6 +31,7 @@ public class PrintingContext { private long SKIP_ARRAY = 1 << 2; private long IGNORE_STATIC_ACCESS = 1 << 3; private long IGNORE_ENCLOSING_CLASS = 1 << 4; + private long FORCE_WILDCARD_GENERICS = 1 << 5; private long state; @@ -49,6 +50,9 @@ public boolean ignoreStaticAccess() { public boolean ignoreEnclosingClass() { return (state & IGNORE_ENCLOSING_CLASS) != 0L; } + public boolean forceWildcardGenerics() { + return (state & FORCE_WILDCARD_GENERICS) != 0L; + } public class Writable implements AutoCloseable { private long oldState; @@ -81,6 +85,10 @@ public T ignoreEnclosingClass(boolean v) { setState(IGNORE_ENCLOSING_CLASS, v); return (T) this; } + public T forceWildcardGenerics(boolean v) { + setState(FORCE_WILDCARD_GENERICS, v); + return (T) this; + } private void setState(long mask, boolean v) { state = v ? state | mask : state & ~mask; } diff --git a/src/test/java/spoon/test/template/TemplateTest.java b/src/test/java/spoon/test/template/TemplateTest.java index 4f2fe4bd933..3110bbe3200 100644 --- a/src/test/java/spoon/test/template/TemplateTest.java +++ b/src/test/java/spoon/test/template/TemplateTest.java @@ -1043,7 +1043,7 @@ public void substituteTypeAccessReference() throws Exception { assertEquals("spoon.test.template.TypeReferenceClassAccess.Example ret = new spoon.test.template.TypeReferenceClassAccess.Example()", method.getBody().getStatement(1).toString()); assertEquals("o = spoon.test.template.TypeReferenceClassAccess.Example.currentTimeMillis()", method.getBody().getStatement(2).toString()); assertEquals("o = spoon.test.template.TypeReferenceClassAccess.Example.class", method.getBody().getStatement(3).toString()); - assertEquals("o = (o) instanceof spoon.test.template.TypeReferenceClassAccess.Example", method.getBody().getStatement(4).toString()); + assertEquals("o = (o) instanceof spoon.test.template.TypeReferenceClassAccess.Example", method.getBody().getStatement(4).toString()); assertEquals("java.util.function.Supplier p = spoon.test.template.TypeReferenceClassAccess.Example::currentTimeMillis", method.getBody().getStatement(5).toString()); } }