1. Introduction
The @Import
annotation is used in Spring to import Java configuration classes, regular component classes, or even bean definition classes into the current application context. It allows for modularizing your application configuration and managing bean definitions across multiple configuration files or components.
2. Basic Definition
@Target({ElementType.TYPE}) @Retention(RetentionPolicy.RUNTIME) @Documented public @interface Import { Class<?>[] value(); }
- The
@Import
annotation is placed on a@Configuration
class (or a@SpringBootApplication
class). - It accepts one or more classes as arguments, and Spring will import their beans into the application context.
3. Use Cases of @Import
Use Case | Description |
Modular configuration | Organize configurations into multiple classes |
Enable third-party configurations | Import configs from libraries or external modules |
Avoid component scanning | Manually register beans instead of using @ComponentScan |
Conditional bean loading | Use in combination with @Conditional , @Profile , or @ConditionalOnProperty |
4. Example: Importing Configuration Classes
Suppose you have two configuration classes:
DatabaseConfig.java
@Configuration public class DatabaseConfig { @Bean public DataSource dataSource() { return new HikariDataSource(); // example } }
SecurityConfig.java
@Configuration public class SecurityConfig { @Bean public SecurityManager securityManager() { return new SecurityManager(); } }
MainApplication.java
@SpringBootApplication @Import({DatabaseConfig.class, SecurityConfig.class}) public class MainApplication { public static void main(String[] args) { SpringApplication.run(MainApplication.class, args); } }
This tells Spring to include both DatabaseConfig
and SecurityConfig
when building the application context.
5. Importing Component Classes (Non-Configuration)
You can also use @Import
to bring in regular component classes that are not marked with @Component
.
UtilityService.java
public class UtilityService { public String getMessage() { return "Hello from UtilityService"; } }
AppConfig.java
@Configuration @Import(UtilityService.class) public class AppConfig { }
Now, UtilityService
will be available as a Spring-managed bean even though it is not annotated with @Component
.
6. Using @Import
with @Enable...
Annotations
Many Spring annotations like @EnableAsync
, @EnableScheduling
, @EnableTransactionManagement
, etc., internally use @Import
to register configuration classes.
@EnableAsync // internally uses @Import(AsyncConfigurationSelector.class) @Configuration public class AppConfig { }
7. ImportSelector and DeferredImportSelector
You can write custom logic to determine which classes to import at runtime using:
public class MyImportSelector implements ImportSelector { @Override public String[] selectImports(AnnotationMetadata importingClassMetadata) { return new String[] { "com.example.MyBeanConfig" }; } }
Using the selector:
@Configuration @Import(MyImportSelector.class) public class AppConfig { }
DeferredImportSelector
is a special interface. Used for deferring the import decision until all @Configuration
classes are processed.
8. Comparison with @ComponentScan
and @Bean
Feature | @Import | @ComponentScan | @Bean |
Registers class directly? | Yes | No, scans package for @Component classes | No |
Requires annotations in target class? | No | Yes (@Component , etc.) | No |
Programmatic control? | Yes (with ImportSelector ) | Limited | Yes |