Details
-
Bug
-
Status: Closed
-
Critical
-
Resolution: Fixed
-
2.3.8
-
None
Description
Consider the following interfaces:
package f; import java.io.Serializable; public interface CrudRepository<T, S extends Serializable> { void delete(S arg); void delete(T arg); }
package f; public interface MyRepository extends CrudRepository<String, Long> { }
The following implementation class:
package f; public class MyRepositoryImpl implements MyRepository { @Override public void delete(String arg) { System.out.println("String"); } @Override public void delete(Long arg) { System.out.println("Long"); } }
And the following Groovy class:
package f import groovy.transform.CompileStatic; import groovy.transform.TypeChecked; @TypeChecked class MyClass { static MyRepository factory() { return new MyRepositoryImpl() } static void main(String[] args) { MyRepository r = factory() r.delete('foo') } }
Static type checking returns the following error:
MyClass.groovy: 15: [Static type checking] - Cannot call f.MyRepository#delete(S) with arguments [java.lang.String]
The same applies if you use @CompileStatic instead of @TypeChecked.
Note that if, In the previous code, you change the method main by replacing:
MyRepository r = factory()
with:
MyRepository r = new MyRepositoryImpl()
compilation succeeds. However in real code this might not be possible (the MyRepository instance may be injected and auto-generated, think of Spring Data for instance).
The only workaround is (yet again...) to disable static type checking and static compilation.
Attachments
Issue Links
- relates to
-
GROOVY-10820 SC: static choice of Class vs Object extension for Type dot name
- Closed
- links to