Why doesn't the spring @Autowire work with java generics

Posted by testing123 on Stack Overflow See other posts from Stack Overflow or by testing123
Published on 2012-06-01T04:37:12Z Indexed on 2012/06/01 4:40 UTC
Read the original article Hit count: 225

Filed under:
|
|
|
|

Inspired by spring data awesomeness I wanted to create a abstract RESTController that I could extend for a lot of my controllers. I created the following class:

@Controller
public abstract class RESTController<E, PK extends Serializable, R extends PagingAndSortingRepository<E, PK>>
{
    @Autowired
    private R repository;

    @RequestMapping(method=RequestMethod.GET, params={"id"})
    @ResponseBody 
    public E getEntity(@RequestParam PK id)
    {
        return repository.findOne(id);
    }

    ...
}

I was hoping that the generics would allow me to @Autowire in the repository but I get the following error:

SEVERE: Allocate exception for servlet appServlet
org.springframework.beans.factory.NoSuchBeanDefinitionException: No unique bean of type [org.springframework.data.repository.PagingAndSortingRepository] is defined: expected single matching bean but found 3: [groupRepository, externalCourseRepository, managedCourseRepository]
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:800)
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:707)
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:478)
    at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:87)
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:284)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1106)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:517)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:456)
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:294)

I understand what the error is telling me, there is more than one match for the @Autowire. I am confused because I thought by creating the following controller it would work:

@Controller
@RequestMapping(value="/managedCourse")
public class ManagedCourseController extends RESTController<ManagedCourse, Long, ManagedCourseRepository>
{
    ...
}

This is easy enough to work around by doing having a method like this in the RESTController:

protected abstract R getRepository();

and then doing this in your implementing class:

@Autowired
private ManagedCourseRepository repository;

@Override
protected ManagedCourseRepository getRepository() 
{
    return repository;
}

I was just wondering if someone had any thoughts of how I could get this to work.

© Stack Overflow or respective owner

Related posts about java

Related posts about spring