changeset 57014:9de0ee33b0f4 amber-demo-II

Automatic merge with records-and-sealed
author mcimadamore
date Tue, 20 Aug 2019 17:45:40 +0000
parents a363100f43a9 befc2bc52f1f
children a0077b5b35d8
files test/langtools/tools/javac/records/mandated_members/CheckRecordMembers.java
diffstat 2 files changed, 45 insertions(+), 31 deletions(-) [+]
line wrap: on
line diff
--- a/test/langtools/tools/javac/records/RecordCompilationTests.java	Tue Aug 20 17:35:45 2019 +0000
+++ b/test/langtools/tools/javac/records/RecordCompilationTests.java	Tue Aug 20 17:45:40 2019 +0000
@@ -24,14 +24,21 @@
  */
 
 import java.io.IOException;
+import java.lang.annotation.ElementType;
+import java.util.EnumMap;
+import java.util.EnumSet;
 import java.util.List;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
 
 import org.testng.ITestResult;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.Test;
 import tools.javac.combo.JavacTemplateTestBase;
 
+import static java.lang.annotation.ElementType.*;
 import static java.util.stream.Collectors.toList;
+import static org.testng.Assert.assertEquals;
 
 /**
  * RecordCompilationTests
@@ -293,31 +300,35 @@
 
     public void testAnnotationCriteria() {
         String imports = "import java.lang.annotation.*;\n";
-        String A_COMPONENT = "@Target({ ElementType.RECORD_COMPONENT }) @interface A {}\n";
-        String A_FIELD = "@Target({ ElementType.FIELD }) @interface A {}\n";
-        String A_METHOD = "@Target({ ElementType.METHOD }) @interface A {}\n";
-        String A_PARAM = "@Target({ ElementType.PARAMETER }) @interface A {}\n";
-        String A_TYPE_USE = "@Target({ ElementType.TYPE_USE }) @interface A {}\n";
-        String A_MULTI = "@Target({ ElementType.RECORD_COMPONENT, ElementType.FIELD, ElementType.METHOD, ElementType.PARAMETER, ElementType.TYPE_USE }) @interface A {}\n";
-        String A_NONE = "@interface A {}\n";
+        String template = "@Target({ # }) @interface A {}\n";
+        EnumMap<ElementType, String> annotations = new EnumMap<>(ElementType.class);
+        for (ElementType e : values())
+            annotations.put(e, template.replace("#", "ElementType." + e.name()));
+        EnumSet<ElementType> goodSet = EnumSet.of(RECORD_COMPONENT, FIELD, METHOD, PARAMETER, TYPE_USE);
+        EnumSet<ElementType> badSet = EnumSet.of(CONSTRUCTOR, PACKAGE, TYPE, LOCAL_VARIABLE, ANNOTATION_TYPE, TYPE_PARAMETER, MODULE);
 
-        String A_CTOR = "@Target({ ElementType.CONSTRUCTOR }) @interface A {}\n";
-        String A_PACKAGE = "@Target({ ElementType.PACKAGE }) @interface A {}\n";
-        String A_TYPE = "@Target({ ElementType.TYPE }) @interface A {}\n";
-        String A_LOCAL = "@Target({ ElementType.LOCAL_VARIABLE }) @interface A {}\n";
-        String A_ANNOTATION_TYPE = "@Target({ ElementType.ANNOTATION_TYPE }) @interface A {}\n";
-        String A_TYPE_PARAMETER = "@Target({ ElementType.TYPE_PARAMETER }) @interface A {}\n";
-        String A_MODULE = "@Target({ ElementType.MODULE }) @interface A {}\n";
-        String A_MORE = "@Target({ ElementType.RECORD_COMPONENT, ElementType.FIELD, ElementType.METHOD, ElementType.PARAMETER, " +
-                       "ElementType.TYPE_USE, ElementType.CONSTRUCTOR, " +
-                       "ElementType.PACKAGE, ElementType.TYPE, ElementType.LOCAL_VARIABLE }) @interface A {}\n";
+        assertEquals(goodSet.size() + badSet.size(), values().length);
+        String A_GOOD = template.replace("#",
+                                         goodSet.stream().map(ElementType::name).map(s -> "ElementType." + s).collect(Collectors.joining(",")));
+        String A_BAD = template.replace("#",
+                                        badSet.stream().map(ElementType::name).map(s -> "ElementType." + s).collect(Collectors.joining(",")));
+        String A_ALL = template.replace("#",
+                                        Stream.of(ElementType.values()).map(ElementType::name).map(s -> "ElementType." + s).collect(Collectors.joining(",")));
+        String A_NONE = "@interface A {}";
 
-        for (String s : List.of(A_COMPONENT, A_FIELD, A_METHOD, A_PARAM, A_TYPE_USE, A_MULTI, A_NONE, A_MORE))
-            assertOK(imports + s + "record R(@A int x) { }");
+        for (ElementType e : goodSet)
+            assertOK(imports + annotations.get(e) + "record R(@A int x) { }");
+        assertOK(imports + A_GOOD + "record R(@A int x) { }");
+        assertOK(imports + A_ALL + "record R(@A int x) { }");
+        assertOK(imports + A_NONE);
 
         // @@@ Should also fail for TYPE_PARAMETER
-        for (String s : List.of(A_PACKAGE, A_CTOR, A_TYPE, A_LOCAL, A_ANNOTATION_TYPE, /* A_TYPE_PARAMETER, */ A_MODULE))
-            assertFail("compiler.err.annotation.type.not.applicable", imports + s + "record R(@A int x) { }");
+        for (ElementType e : badSet) {
+            if (e == TYPE_PARAMETER) continue; // @@@ temporary hack awaiting fix
+            assertFail("compiler.err.annotation.type.not.applicable", imports + annotations.get(e) + "record R(@A int x) { }");
+        }
+        // @@@ Also should fail, pending TYPE_PARAMETER fix
+        //assertFail("compiler.err.annotation.type.not.applicable", imports + A_BAD + "record R(@A int x) { }");
 
         // TODO: OK to redeclare with or without same annos
     }
@@ -347,5 +358,13 @@
                 "        record RR(int x) { public int x() { return y; }};\n" +
                 "    }\n" +
                 "}");
+
+        // Can't self-shadow
+        assertFail("compiler.err.already.defined",
+                   "class R { \n" +
+                   "    void m() { \n" +
+                   "        record R(int x) { };\n" +
+                   "    }\n" +
+                   "}");
     }
 }
--- a/test/langtools/tools/javac/records/mandated_members/CheckRecordMembers.java	Tue Aug 20 17:35:45 2019 +0000
+++ b/test/langtools/tools/javac/records/mandated_members/CheckRecordMembers.java	Tue Aug 20 17:45:40 2019 +0000
@@ -94,7 +94,7 @@
     );
 
     static final String sourceTemplate =
-            "record Data(#{FT[0]} f0, #{FT[1]} f1) { }";
+            "public record Data(#{FT[0]} f0, #{FT[1]} f1) { }";
 
     public static void main(String... args) throws Exception {
         new combo.ComboTestHelper<CheckRecordMembers>()
@@ -109,17 +109,17 @@
     @Override
     public void doWork() throws Throwable {
         newCompilationTask()
-                .withSourceFromTemplate(sourceTemplate)
+                .withSourceFromTemplate("Data", sourceTemplate)
                 .generate(this::check);
     }
 
     void check(ComboTask.Result<Iterable<? extends JavaFileObject>> result) {
+        if (result.hasErrors() || result.hasWarnings())
+            fail("Compilation errors not expected: " + result.compilationInfo());
+
         List<Object> f0s = dataValues.get(fieldType[0]);
         List<Object> f1s = dataValues.get(fieldType[1]);
 
-        if (result.hasErrors() || result.hasWarnings())
-            fail("Compilation errors not expected: " + result.compilationInfo());
-
         Iterable<? extends PathFileObject> pfoIt = (Iterable<? extends PathFileObject>) result.get();
         PathFileObject pfo = pfoIt.iterator().next();
         Class<?> clazz;
@@ -147,11 +147,6 @@
                 || fieldF1.getType() != fieldType[1].clazz)
                 fail("Unexpected field or getter type: " + result.compilationInfo());
 
-            for (AccessibleObject o : List.of(ctor, getterF0, getterF1, equalsMethod, hashCodeMethod, toStringMethod)) {
-                // @@@ Why do we need this?
-                o.setAccessible(true);
-            }
-
             for (Object f0 : f0s) {
                 for (Object f1 : f1s) {
                     // Create object