This is an automated email from the ASF dual-hosted git repository.

emilles pushed a commit to branch GROOVY_4_0_X
in repository https://gitbox.apache.org/repos/asf/groovy.git

commit b7ff4541f3b9610c5a377ab9705e85912bee2daa
Author: Eric Milles <[email protected]>
AuthorDate: Thu Feb 23 17:52:50 2023 -0600

    GROOVY-10937: update `record` component decompile
---
 .../ast/decompiled/ClassSignatureParser.java       |  17 ++-
 .../org/codehaus/groovy/classgen/RecordTest.groovy | 156 +++++++++++----------
 2 files changed, 93 insertions(+), 80 deletions(-)

diff --git 
a/src/main/java/org/codehaus/groovy/ast/decompiled/ClassSignatureParser.java 
b/src/main/java/org/codehaus/groovy/ast/decompiled/ClassSignatureParser.java
index 443a810dad..e3c7429257 100644
--- a/src/main/java/org/codehaus/groovy/ast/decompiled/ClassSignatureParser.java
+++ b/src/main/java/org/codehaus/groovy/ast/decompiled/ClassSignatureParser.java
@@ -27,7 +27,6 @@ import org.objectweb.asm.signature.SignatureVisitor;
 
 import java.util.ArrayList;
 import java.util.List;
-import java.util.stream.Collectors;
 
 class ClassSignatureParser {
 
@@ -60,7 +59,9 @@ class ClassSignatureParser {
         }
 
         if (!stub.recordComponents.isEmpty()) {
-            
classNode.setRecordComponents(stub.recordComponents.stream().map(rc -> {
+            List<RecordComponentNode> recordComponents =
+                    new ArrayList<>(stub.recordComponents.size());
+            for (RecordComponentStub rc : stub.recordComponents) {
                 ClassNode[] type = 
{resolver.resolveType(Type.getType(rc.descriptor))};
                 if (rc.signature != null) {
                     new SignatureReader(rc.signature).accept(new 
TypeSignatureParser(resolver) {
@@ -69,14 +70,16 @@ class ClassSignatureParser {
                             type[0] = applyErasure(result, type[0]);
                         }
                     });
+                } else {
+                    type[0] = type[0].getPlainNodeReference();
                 }
-                ClassNode rcType = type[0];
-                Annotations.addTypeAnnotations(rc, rcType, resolver);
 
-                RecordComponentNode recordComponent = new 
RecordComponentNode(classNode, rc.name, rcType);
+                RecordComponentNode recordComponent = new 
RecordComponentNode(classNode, rc.name, type[0]);
                 Annotations.addAnnotations(rc, recordComponent, resolver);
-                return recordComponent;
-            }).collect(Collectors.toList()));
+                Annotations.addTypeAnnotations(rc, type[0], resolver);
+                recordComponents.add(recordComponent);
+            }
+            classNode.setRecordComponents(recordComponents);
         }
     }
 
diff --git a/src/test/org/codehaus/groovy/classgen/RecordTest.groovy 
b/src/test/org/codehaus/groovy/classgen/RecordTest.groovy
index 4c7c026ccd..2ebdc3c1ea 100644
--- a/src/test/org/codehaus/groovy/classgen/RecordTest.groovy
+++ b/src/test/org/codehaus/groovy/classgen/RecordTest.groovy
@@ -18,9 +18,9 @@
  */
 package org.codehaus.groovy.classgen
 
-import org.codehaus.groovy.ast.AnnotationNode
 import org.codehaus.groovy.ast.ClassHelper
 import org.codehaus.groovy.ast.ClassNode
+import org.codehaus.groovy.ast.RecordComponentNode
 import org.codehaus.groovy.ast.decompiled.AsmDecompiler
 import org.codehaus.groovy.ast.decompiled.AsmReferenceResolver
 import org.codehaus.groovy.ast.decompiled.DecompiledClassNode
@@ -104,7 +104,7 @@ final class RecordTest {
                 import java.lang.annotation.*;
                 import java.util.*;
 
-                public record Person(@NotNull @NotNull2 String name, int age, 
@NotNull2 @NotNull3 List<String> locations, String[] titles) {}
+                public record Person(@NotNull @NotNull2 @NotNull3 String name, 
int age, @NotNull2 @NotNull3 List<String> locations, String[] titles) {}
 
                 @Retention(RetentionPolicy.RUNTIME)
                 @Target({ElementType.RECORD_COMPONENT})
@@ -124,85 +124,95 @@ final class RecordTest {
             cu.addSources(a)
             cu.compile()
 
-            Class personClazz = loader.loadClass('Person')
-            Class notNullClazz = loader.loadClass('NotNull')
-            Class notNull2Clazz = loader.loadClass('NotNull2')
-            Class notNull3Clazz = loader.loadClass('NotNull3')
-
-            def rcs = personClazz.recordComponents
-            assert rcs.length == 4
-
-            assert rcs[0].name == 'name' && rcs[0].type == String
-            def annotations = rcs[0].annotations
-            assert annotations.length == 2
-            assert annotations[0].annotationType() == notNullClazz
-            assert annotations[1].annotationType() == notNull2Clazz
-            def typeAnnotations = rcs[0].getAnnotatedType().getAnnotations()
-            assert typeAnnotations.length == 1
-            assert notNull2Clazz == typeAnnotations[0].annotationType()
-
-            assert rcs[1].name == 'age'       && rcs[1].type == int
-            assert rcs[2].name == 'locations' && rcs[2].type == List
-            assert rcs[3].name == 'titles'    && rcs[3].type == String[]
+            def personClass   = loader.loadClass('Person')
+            def notNullClass  = loader.loadClass('NotNull')
+            def notNull2Class = loader.loadClass('NotNull2')
+            def notNull3Class = loader.loadClass('NotNull3')
+
+            def personComponents = personClass.recordComponents
+            assert personComponents.size() == 4
+
+            assert personComponents[0].name == 'name'
+            assert personComponents[0].type == String
+            def annotations = personComponents[0].annotations
+            assert annotations.size() == 2
+            assert annotations[0].annotationType() == notNullClass
+            assert annotations[1].annotationType() == notNull2Class
+            def typeAnnotations = personComponents[0].annotatedType.annotations
+            assert typeAnnotations.size() == 2
+            assert typeAnnotations[0].annotationType() == notNull2Class
+            assert typeAnnotations[1].annotationType() == notNull3Class
+
+            assert personComponents[1].name == 'age'       && 
personComponents[1].type == int
+            assert personComponents[2].name == 'locations' && 
personComponents[2].type == List
+            assert personComponents[3].name == 'titles'    && 
personComponents[3].type == String[]
+
+            assert personComponents[2].annotations.size() == 1
+            assert personComponents[2].annotations[0].annotationType() == 
notNull2Class
+            assert personComponents[2].genericSignature == 
'Ljava/util/List<Ljava/lang/String;>;'
+            assert personComponents[2].genericType.toString() == 
'java.util.List<java.lang.String>'
+
+            typeAnnotations = personComponents[2].annotatedType.annotations
+            assert typeAnnotations.size() == 2
+            assert typeAnnotations[0].annotationType() == notNull2Class
+            assert typeAnnotations[1].annotationType() == notNull3Class
+
+            def personClassNode   = ClassHelper.make(personClass)
+            def notNullClassNode  = ClassHelper.make(notNullClass)
+            def notNull2ClassNode = ClassHelper.make(notNull2Class)
+            def notNull3ClassNode = ClassHelper.make(notNull3Class)
+
+            def checkNativeRecordClassNode = { ClassNode classNode ->
+                assert classNode.isRecord()
+                assert classNode.recordComponents.size() == 4
+                classNode.recordComponents.eachWithIndex { RecordComponentNode 
rcn, Integer index ->
+                    switch (index) {
+                      case 0:
+                        assert rcn.name == 'name'
+                        assert rcn.type == ClassHelper.STRING_TYPE
+                        assert rcn.type !== ClassHelper.STRING_TYPE // 
GROOVY-10937
+                        assert rcn.annotations.size() == 2
+                        assert rcn.annotations[0].classNode == notNullClassNode
+                        assert rcn.annotations[1].classNode == 
notNull2ClassNode
+                        assert rcn.type.typeAnnotations.size() == 2
+                        assert rcn.type.typeAnnotations[0].classNode == 
notNull2ClassNode
+                        assert rcn.type.typeAnnotations[1].classNode == 
notNull3ClassNode
+                        break
+                      case 1:
+                          assert rcn.name == 'age'
+                          assert rcn.type == ClassHelper.int_TYPE
+                        break
+                      case 2:
+                        assert rcn.name == 'locations'
+                        assert rcn.type == ClassHelper.LIST_TYPE
+                        assert rcn.type !== ClassHelper.LIST_TYPE
+                        assert rcn.type.genericsTypes.size() == 1
+                        assert rcn.type.genericsTypes[0].type == 
ClassHelper.STRING_TYPE
+                        assert rcn.annotations.size() == 1
+                        assert rcn.annotations[0].classNode == 
notNull2ClassNode
+                        assert rcn.type.typeAnnotations.size() == 2
+                        assert rcn.type.typeAnnotations[0].classNode == 
notNull2ClassNode
+                        assert rcn.type.typeAnnotations[1].classNode == 
notNull3ClassNode
+                        break
+                      case 3:
+                        assert rcn.name == 'titles'
+                        assert rcn.type == ClassHelper.STRING_TYPE.makeArray()
+                    }
+                }
+            }
 
-            assert rcs[2].genericSignature == 
'Ljava/util/List<Ljava/lang/String;>;'
-            assert rcs[2].genericType as String == 
'java.util.List<java.lang.String>'
+            checkNativeRecordClassNode(personClassNode)
 
-            def annotations2 = rcs[2].annotations
-            assert annotations2.length == 1
-            assert annotations2[0].annotationType() == notNull2Clazz
-            def typeAnnotations2 = rcs[2].annotatedType.annotations
-            assert typeAnnotations2.length == 2
-            assert typeAnnotations2[0].annotationType() == notNull2Clazz
-            assert typeAnnotations2[1].annotationType() == notNull3Clazz
-
-            ClassNode personClassNode = ClassHelper.make(personClazz)
-            ClassNode notNullClassNode = ClassHelper.make(notNullClazz)
-            ClassNode notNull2ClassNode = ClassHelper.make(notNull2Clazz)
-            ClassNode notNull3ClassNode = ClassHelper.make(notNull3Clazz)
-            checkNativeRecordClassNode(personClassNode, notNullClassNode, 
notNull2ClassNode, notNull3ClassNode)
-
-            def resource = 
loader.getResource(personClazz.getName().replace('.', '/') + '.class')
-            def stub = AsmDecompiler.parseClass(resource)
-            def unit = new CompilationUnit(loader)
-            def personDecompiledClassNode = new DecompiledClassNode(stub, new 
AsmReferenceResolver(new ClassNodeResolver(), unit))
-            checkNativeRecordClassNode(personDecompiledClassNode, 
notNullClassNode, notNull2ClassNode, notNull3ClassNode)
+            def stub = 
AsmDecompiler.parseClass(loader.getResource(personClass.getName().replace('.', 
'/') + '.class'))
+            def resolver = new AsmReferenceResolver(new ClassNodeResolver(), 
new CompilationUnit(loader))
+            def personDecompiledClassNode = new DecompiledClassNode(stub, 
resolver)
+            checkNativeRecordClassNode(personDecompiledClassNode)
         } finally {
             sourceDir.deleteDir()
             config.targetDirectory.deleteDir()
         }
     }
 
-    private static void checkNativeRecordClassNode(ClassNode personClassNode, 
ClassNode notNullClassNode, ClassNode notNull2ClassNode, ClassNode 
notNull3ClassNode) {
-        assert personClassNode.isRecord()
-        def rcns = personClassNode.getRecordComponents()
-        assert rcns.size() == 4
-        assert rcns[0].name == 'name' && rcns[0].type == 
ClassHelper.STRING_TYPE
-        List<AnnotationNode> annotationNodes = rcns[0].getAnnotations()
-        assert annotationNodes.size() == 2
-        assert annotationNodes[0].getClassNode() == notNullClassNode
-        assert annotationNodes[1].getClassNode() == notNull2ClassNode
-        def typeAnnotationNodes = rcns[0].getType().getTypeAnnotations()
-        assert typeAnnotationNodes.size() == 1
-        assert typeAnnotationNodes[0].getClassNode() == notNull2ClassNode
-
-        assert rcns[1].name == 'age' && rcns[1].type == ClassHelper.int_TYPE
-
-        assert rcns[2].name == 'locations' && rcns[2].type == 
ClassHelper.LIST_TYPE
-        def genericsTypes = rcns[2].type.genericsTypes
-        assert genericsTypes.size() == 1
-        assert genericsTypes[0].type == ClassHelper.STRING_TYPE
-        def annotationNodes2 = rcns[2].getAnnotations()
-        assert annotationNodes2.size() == 1
-        assert annotationNodes2[0].getClassNode() == notNull2ClassNode
-        def typeAnnotationNodes2 = rcns[2].getType().getTypeAnnotations()
-        assert typeAnnotationNodes2.size() == 2
-        assert typeAnnotationNodes2[0].getClassNode() == notNull2ClassNode
-        assert typeAnnotationNodes2[1].getClassNode() == notNull3ClassNode
-
-        assert rcns[3].name == 'titles' && rcns[3].type == 
ClassHelper.STRING_TYPE.makeArray()
-    }
-
     
//--------------------------------------------------------------------------
 
     private final GroovyShell shell = GroovyShell.withConfig {

Reply via email to