Java-Spring入门指南(十)纯Java类配备与@Configuration实战
2025-09-18 08:34 tlnshuju 阅读(0) 评论(0) 收藏 举报Java-Spring入门指南(十)纯Java类配置与@Configuration实战
- 前言
- 一、纯Java类配置的核心:@Configuration
- 1.1 @Configuration的作用
- 1.2 实战:创建第一个配置类
- 二、手动定义@Bean
- 2.1 基本用法
- 2.2 测试@Bean定义的Bean
- 2.3 自定义Bean的id
- 三、@ComponentScan
- 3.1 基本用法
- 3.2 测试组件扫描
- 3.3 @ComponentScans:组合多个扫描规则
- 四、@Import:组合多个配置类
- 4.1 实战:用@Import组合配置类
- 4.2 测试@Import
- 五、完整代码结构与测试
- 5.1 代码结构
- 5.2 各文件代码
- MyConfig.java
- MyConfig1.java
- Student.java
- Teacher.java
- MyTest.java
前言
在前几篇博客中,我们从XML配置逐步过渡到注解驱动开发,掌握了@Component
、@Autowired
等核心注解。但注解仍需依赖少量XML(如<context:component-scan>
),有没有办法彻底摆脱XML,让所有配置都“写在Java类里”?
答案就是Spring的纯Java类配置(Java-based Configuration)。通过@Configuration
注解,我们可以把原本写在XML里的配置(如组件扫描、Bean定义)全部转移到Java类中,让配置与业务代码更紧密地结合。
本文将聚焦@Configuration
的核心用法,实战@Bean
定义Bean、@ComponentScan
扫描组件、@Import
组合配置类,带大家体验“无XML”的Spring配置新方式。
一、纯Java类配置的核心:@Configuration
@Configuration
是Spring纯Java配置的“入口注解”,被它标记的类会被Spring视为配置类(相当于XML配置文件),类中可以定义Bean、指定组件扫描规则等。
1.1 @Configuration的作用
- 替代XML配置文件,让配置“代码化”;
- 配置类本身也会被Spring管理,作为一个Bean存在于容器中;
- 支持通过
@Bean
、@ComponentScan
等注解,在类中完成所有Spring配置。
1.2 实战:创建第一个配置类
我们先写一个最简单的配置类,感受它如何替代XML:
package com.niit.config;
import org.springframework.context.annotation.Configuration;
// @Configuration:标记当前类为Spring的配置类,相当于beans.xml
@Configuration
public class MyConfig
{
// 这里暂时为空,后续添加Bean定义和扫描规则
}
二、手动定义@Bean
@Bean
是配置类中定义Bean的核心注解,作用相当于XML中的<bean>
标签。被@Bean
标记的方法,其返回值会被Spring注册为Bean,方法名默认作为Bean的id
。
2.1 基本用法
假设我们有一个Student
类,需要将其注册为Bean:
package com.niit.pojo;
public class Student
{
private String name = "默认学生";
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
'}';
}
}
在配置类中,用@Bean
定义这个Student的Bean:
package com.niit.config;
import com.niit.pojo.Student;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class MyConfig
{
// @Bean:将方法返回的Student对象注册为Spring的Bean,id默认为方法名“getStudent”
@Bean
public Student getStudent() {
return new Student();
}
}
2.2 测试@Bean定义的Bean
通过AnnotationConfigApplicationContext
加载配置类,获取Bean:
import com.niit.config.MyConfig;
import com.niit.pojo.Student;
import org.junit.Test;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
public class MyTest
{
@Test
public void testBean() {
// 加载配置类(替代ClassPathXmlApplicationContext加载XML)
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(MyConfig.class)
;
// 获取Bean,id为方法名“getStudent”
Student student = context.getBean("getStudent", Student.class)
;
System.out.println(student);
// 输出:Student{name='默认学生'}
context.close();
}
}
2.3 自定义Bean的id
如果不想用方法名作为Bean的id
,可以给@Bean
指定name
属性:
@Bean(name = "myStudent")
public Student getStudent() {
return new Student();
}
测试时,通过新的id
获取:
Student student = context.getBean("myStudent", Student.class)
;
三、@ComponentScan
@ComponentScan
的作用和XML中的<context:component-scan>
一致,用于指定Spring要扫描的包,自动注册带有@Component
、@Service
、@Repository
等注解的类为Bean。
3.1 基本用法
假设com.niit.pojo
包下有一个带@Component
的类:
package com.niit.pojo;
import org.springframework.stereotype.Component;
@Component
public class Teacher
{
private String name = "张老师";
@Override
public String toString() {
return "Teacher{" +
"name='" + name + '\'' +
'}';
}
}
在配置类中添加@ComponentScan
,指定扫描com.niit.pojo
包:
package com.niit.config;
import com.niit.pojo.Student;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
@Configuration
// 扫描com.niit.pojo包下的组件
@ComponentScan(basePackages = {
"com.niit.pojo"
})
public class MyConfig
{
@Bean
public Student getStudent() {
return new Student();
}
}
3.2 测试组件扫描
加载配置类后,不仅能获取@Bean
定义的Student
,还能获取扫描到的Teacher
:
@Test
public void testComponentScan() {
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(MyConfig.class)
;
// 获取@Bean定义的Student
Student student = context.getBean("getStudent", Student.class)
;
System.out.println(student);
// 获取扫描到的Teacher(id为类名首字母小写“teacher”)
Teacher teacher = context.getBean("teacher", Teacher.class)
;
System.out.println(teacher);
// 输出:Teacher{name='张老师'}
context.close();
}
3.3 @ComponentScans:组合多个扫描规则
如果需要同时扫描多个包或配置复杂的扫描规则,可以用@ComponentScans
组合多个@ComponentScan
:
@Configuration
@ComponentScans({
@ComponentScan(basePackages = "com.niit.pojo"),
@ComponentScan(basePackages = "com.niit.service")
})
public class MyConfig
{
// ...
}
四、@Import:组合多个配置类
当配置类较多时,可通过@Import
将多个配置类合并,统一加载。
4.1 实战:用@Import组合配置类
假设有两个配置类MyConfig
和MyConfig1
:
// MyConfig.java
package com.niit.config;
import com.niit.pojo.Student;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
@Configuration
@ComponentScan(basePackages = {
"com.niit.pojo"
})
public class MyConfig
{
@Bean
public Student getStudent() {
return new Student();
}
}
// MyConfig1.java
package com.niit.config;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
@Configuration
@Import(MyConfig.class)
// 导入MyConfig配置类
public class MyConfig1
{
// 可添加自己的Bean定义或扫描规则
}
4.2 测试@Import
只需加载MyConfig1
,即可同时包含MyConfig
的配置:
@Test
public void testImport() {
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(MyConfig1.class)
;
// 能获取MyConfig中定义的Student
Student student = context.getBean("getStudent", Student.class)
;
System.out.println(student);
// 能获取MyConfig扫描到的Teacher
Teacher teacher = context.getBean("teacher", Teacher.class)
;
System.out.println(teacher);
context.close();
}
五、完整代码结构与测试
5.1 代码结构
com.niit
├─ config
│ ├─ MyConfig.java
│ └─ MyConfig1.java
├─ pojo
│ ├─ Student.java
│ └─ Teacher.java
└─ test
└─ MyTest.java
5.2 各文件代码
MyConfig.java
package com.niit.config;
import com.niit.pojo.Student;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
@Configuration
@ComponentScan(basePackages = {
"com.niit.pojo"
})
public class MyConfig
{
@Bean
public Student getStudent() {
return new Student();
}
}
MyConfig1.java
package com.niit.config;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
@Configuration
@Import(MyConfig.class)
public class MyConfig1
{
}
Student.java
package com.niit.pojo;
public class Student
{
private String name = "默认学生";
@Override
public String toString() {
return "Student{" +
"name='" + name + '\'' +
'}';
}
}
Teacher.java
package com.niit.pojo;
import org.springframework.stereotype.Component;
@Component
public class Teacher
{
private String name = "张老师";
@Override
public String toString() {
return "Teacher{" +
"name='" + name + '\'' +
'}';
}
}
MyTest.java
import com.niit.config.MyConfig;
import com.niit.config.MyConfig1;
import com.niit.pojo.Student;
import com.niit.pojo.Teacher;
import org.junit.Test;
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
public class MyTest
{
@Test
public void test() {
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(MyConfig.class)
;
Student student = context.getBean("getStudent", Student.class)
;
System.out.println(student);
Teacher teacher = context.getBean("teacher", Teacher.class)
;
System.out.println(teacher);
context.close();
}
@Test
public void testImport() {
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(MyConfig1.class)
;
Student student = context.getBean("getStudent", Student.class)
;
System.out.println(student);
Teacher teacher = context.getBean("teacher", Teacher.class)
;
System.out.println(teacher);
context.close();
}
}
我的个人主页,欢迎来阅读我的其他文章
https://blog.csdn.net/2402_83322742?spm=1011.2415.3001.5343
我的Java-Spring入门指南知识文章专栏
欢迎来阅读指出不足
https://blog.csdn.net/2402_83322742/category_13040333.html?spm=1001.2014.3001.5482
非常感谢您的阅读,喜欢的话记得三连哦 |
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/907000.shtml
如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!