Mastering Spring @Resource: Inject Maps, Lists, Arrays, and Single Beans
This guide demonstrates how to use Spring's @Resource annotation to inject collections such as Map, List, and array, as well as single beans, and explains resolution strategies like @Priority, @Primary, BeanFactory, ApplicationContext, @Qualifier, and custom qualifiers.
Environment: Spring 6.1.2
1. Prepare Environment
Define an interface DAO and three implementations: WorkerDAO , StudentDAO , and TeacherDAO .
<code>public interface DAO {}
public class WorkerDAO implements DAO {}
public class StudentDAO implements DAO {}
public class TeacherDAO implements DAO {}
</code>PersonService injects the DAO implementations.
<code>public class PersonService {
@Resource
private Type daos;
public String toString() {
return "PersonService [daos=" + daos + "]";
}
}
</code>The main method registers beans, refreshes the context, and prints the PersonService instance.
<code>public static void main(String[] args) {
try (AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext()) {
context.registerBean("worker", WorkerDAO.class);
context.registerBean("student", StudentDAO.class);
context.registerBean("teacher", TeacherDAO.class);
context.registerBean(PersonService.class);
context.refresh();
System.out.println(context.getBean(PersonService.class));
}
}
</code>2. Type Injection
2.1 Map injection
<code>@Resource
private Map<String, DAO> daos;
</code>Output shows the map keyed by bean names.
<code>PersonService [daos={worker=com.pack.WorkerDAO@..., student=com.pack.StudentDAO@..., teacher=com.pack.TeacherDAO@...}]
</code>2.2 List injection
<code>@Resource
private List<DAO> daos;
</code>Output shows the list of DAO instances.
<code>PersonService [daos=[com.pack.TeacherDAO@..., com.pack.StudentDAO@..., com.pack.WorkerDAO@...]]
</code>2.3 Array injection
<code>@Resource
private DAO[] daos;
</code>Output is similar to the list injection.
<code>PersonService [daos=[com.pack.TeacherDAO@..., com.pack.StudentDAO@..., com.pack.WorkerDAO@...]]
</code>2.4 Single bean injection
<code>@Resource
private DAO daos;
</code>When multiple DAO beans exist, Spring throws NoUniqueBeanDefinitionException .
<code>NoUniqueBeanDefinitionException: No qualifying bean of type 'com.pack.DAO' available: expected single matching bean but found 3: worker,student,teacher
</code>Resolution methods:
@Priority – assign priority values; lower number wins.
<code>@Priority(-1)
public class WorkerDAO implements DAO {}
@Priority(-2)
public class StudentDAO implements DAO {}
@Priority(-3)
public class TeacherDAO implements DAO {}
</code>After setting priorities, TeacherDAO is injected.
<code>PersonService [daos=com.pack.TeacherDAO@...]
</code>@Primary – mark the preferred bean.
<code>@Primary
public class WorkerDAO implements DAO {}
</code>Now WorkerDAO is injected.
<code>PersonService [daos=com.pack.WorkerDAO@...]
</code>Other ways to obtain a specific bean manually:
Using BeanFactory
<code>public class PersonService implements BeanFactoryAware {
private DAO daos;
@Override
public void setBeanFactory(BeanFactory beanFactory) throws BeansException {
this.daos = beanFactory.getBean("student", StudentDAO.class);
}
}
</code>Using ApplicationContext
<code>public class PersonService implements ApplicationContextAware {
private DAO daos;
@Override
public void setApplicationContext(ApplicationContext context) throws BeansException {
this.daos = context.getBean("student", StudentDAO.class);
}
}
</code>Using @Qualifier to specify bean name
<code>@Resource
@Qualifier("student")
private DAO daos;
</code>Custom qualifier annotation example:
<code>@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.FIELD})
public @interface PackInject {}
</code>Register the custom qualifier with Spring:
<code>try (AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext()) {
CustomAutowireConfigurer configurer = new CustomAutowireConfigurer();
configurer.setCustomQualifierTypes(Set.of(PackInject.class));
context.registerBean(CustomAutowireConfigurer.class, () -> configurer);
}
</code>Apply @PackInject to a DAO implementation and to the injection point:
<code>@PackInject
public class StudentDAO implements DAO {}
@Resource
@PackInject
private DAO daos;
</code>All these techniques provide precise control over which bean is injected in a Spring application.
Spring Full-Stack Practical Cases
Full-stack Java development with Vue 2/3 front-end suite; hands-on examples and source code analysis for Spring, Spring Boot 2/3, and Spring Cloud.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.