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

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


The following commit(s) were added to refs/heads/GROOVY_5_0_X by this push:
     new e5647650c5 GROOVY-11899: Static methods in Traits do not compile in 
Java/Groovy joint compiliation
e5647650c5 is described below

commit e5647650c5934380706cb2366a9bebb87389aafd
Author: Paul King <[email protected]>
AuthorDate: Sat Apr 4 10:22:42 2026 +1000

    GROOVY-11899: Static methods in Traits do not compile in Java/Groovy joint 
compiliation
---
 .../groovy/tools/javac/JavaStubGenerator.java      |  1 +
 .../TraitStaticMethodsStubTest.groovy              | 64 ++++++++++++++++++++++
 2 files changed, 65 insertions(+)

diff --git 
a/src/main/java/org/codehaus/groovy/tools/javac/JavaStubGenerator.java 
b/src/main/java/org/codehaus/groovy/tools/javac/JavaStubGenerator.java
index 92f32fcc5b..71398d30a6 100644
--- a/src/main/java/org/codehaus/groovy/tools/javac/JavaStubGenerator.java
+++ b/src/main/java/org/codehaus/groovy/tools/javac/JavaStubGenerator.java
@@ -720,6 +720,7 @@ public class JavaStubGenerator {
         if (methodNode.isStaticConstructor()) return;
         if (methodNode.isPrivate() || 
!Utilities.isJavaIdentifier(methodNode.getName())) return;
         if (methodNode.isSynthetic() && 
("$getStaticMetaClass".equals(methodNode.getName()))) return;
+        if (methodNode.isStatic() && Traits.isTrait(classNode)) return; // 
GROOVY-11899
 
         printAnnotations(out, methodNode);
         if (!isInterfaceOrTrait(classNode)) {
diff --git 
a/src/test/groovy/org/codehaus/groovy/tools/stubgenerator/TraitStaticMethodsStubTest.groovy
 
b/src/test/groovy/org/codehaus/groovy/tools/stubgenerator/TraitStaticMethodsStubTest.groovy
new file mode 100644
index 0000000000..4063cd85fb
--- /dev/null
+++ 
b/src/test/groovy/org/codehaus/groovy/tools/stubgenerator/TraitStaticMethodsStubTest.groovy
@@ -0,0 +1,64 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ */
+package org.codehaus.groovy.tools.stubgenerator
+
+/**
+ * GROOVY-11899: Static methods in traits should not appear in the trait stub,
+ * as they are compiled into the $Trait$Helper companion class. Including them
+ * as bodyless static methods produces invalid Java (static interface methods
+ * require a body), breaking joint compilation.
+ */
+final class TraitStaticMethodsStubTest extends StringSourcesStubTestCase {
+
+    @Override
+    Map<String, String> provideSources() {
+        [
+            'MyTrait.groovy': '''
+                trait MyTrait {
+                    static String getMessage() { return "hello" }
+                    String getGreeting() { return "hi" }
+                }
+            ''',
+            'MyClass.groovy': '''
+                class MyClass implements MyTrait {
+                    @groovy.transform.CompileStatic
+                    String test() { return getMessage() }
+                }
+            ''',
+            'MyJavaClass.java': '''
+                public class MyJavaClass {
+                    public static void main(String[] args) {
+                        MyClass obj = new MyClass();
+                    }
+                }
+            ''',
+        ]
+    }
+
+    @Override
+    void verifyStubs() {
+        String traitStub = stubJavaSourceFor('MyTrait')
+        assert !traitStub.contains('getMessage') : 'static method should not 
appear in trait stub'
+        assert  traitStub.contains('getGreeting') : 'instance method should 
still appear in trait stub'
+
+        String classStub = stubJavaSourceFor('MyClass')
+        assert  classStub.contains('getMessage') : 'static method should 
appear in implementing class stub'
+        assert  classStub.contains('getGreeting') : 'instance method should 
appear in implementing class stub'
+    }
+}

Reply via email to