基础认知
上图可见为让Spring IoC工作需要输入两个东西:
1.configuration metada
2.POJOS
所以使用Spring IoC容器要给它一份配置元数据,一些POJO
configuration metada
何为配置元数据?它应该包含哪些内容?
官方文档的描述:
This configuration metadata represents how you, as an application developer, tell the Spring container to instantiate, configure, and assemble the objects in your application.
大意为: configuration metadata 是开发者用来告诉Spring 容器如何实例化,配置和组装应用中的对象
如上所述,使用IoC的大致过程应该是:
因此我们可得到一个作为IoC的使用者,我们第一个todo-list
- 先要有(创建)一个容器。
- “喂”configuration metadata给这个容器
- 取出容器中的值使用
正式开始
task1 创建容器
如果我们使用Spring 容器,最终的使用方式应该是什么样子的,看看官网上的例子:
The ApplicationContext is the interface for an advanced factory capable of maintaining a registry of different beans and their dependencies. By using the method T getBean(String name, Class
requiredType), you can retrieve instances of your beans.
The ApplicationContext lets you read bean definitions and access them, as the following example shows:
// create and configure beans
ApplicationContext context =
new ClassPathXmlApplicationContext("services.xml", "daos.xml");
// retrieve configured instance
PetStoreService service = context.getBean("petStore", PetStoreService.class);
// use configured instance
List userList = service.getUsernameList();
为了能够如上使用IoC容器我们又有了新的任务,todo-list变为:
- 先要有(创建)一个容器。
1. 创建一个可以使用Spring IoC的项目 - “喂”configuration metadata给这个容器
- 取出容器中的值使用
task 1.1 创建一个可以使用Spring IoC的项目
spring为我们提供了start.spring.io来简化spring项目的创建,如果只想使用基础的框架,可以不选任何依赖. 项目建立成功后,运行默认携带的主程序或测试,验证项目是否可运行。
当项目运行成功后,我们就有了一个可以使于创建springIoC容器的环境了。至此我们完成了task1.1
,然后观察官网的例子中有一句:
// 创建 并 配置beans
ApplicationContext context =
new ClassPathXmlApplicationContext("services.xml", "daos.xml");
从注释可知此语句的含义为创建了一个容器,使其能够运行通过。此语句中的参数中那两个xml文件即为“configuration metadata”,由此可知:可以通过传递onfiguration metadata 给某个类构造函数的方式创建容器,
进入下一个环节前更新一下todo-list:
- 先要有(创建)一个容器。
1. 创建一个可以使用Spring IoC的项目 - “喂”configuration metadata给这个容器
- 取出容器中的值使用
task2 配置configuration metadata
完成任务1后,进行任务2,Spring 进行配置的方式有三种:
1. XML格式的文件
1. 基于注解的配置
1. 基于java class的配置
我们先开始从第三种结合第二种方式开始学,为了能够从第二种开始,我们需要补充些基础知识其实就一条
我们在task1中创建容器的方式用了ApplicationContext context = new ClassPathXmlApplicationContext("services.xml")
的方式,这是告诉Spring去读类路径(ClassPaht)下的xml配置文件来创建容器的意思。
如果使用基于注解的配置,ClassPathXmlApplicationContext("services.xml")
显然是不行的,我们需要换一种创建方式:new AnnotationConfigApplicationContext(MainConfig.class)
其中参数为基于java class配置的那个类文件。我们此次以Junit测试的方式继续以下的任务,todo-list更新为:
- 先要有(创建)一个容器。
1. 创建一个可以使用Spring IoC的项目 - “喂”configuration metadata给这个容器
- 创建spring 基于java配置的配置文件,并用此创建容器
- 取出容器中的值使用
task2.1创建spring 基于java配置的配置文件
官网描述
Annotating a class with @Configuration indicates that its primary purpose is as a source of bean definitions. Furthermore, @Configuration classes let inter-bean dependencies be defined by calling other @Bean methods in the same class.
由此可知我们需要在一个类上标注注解@Configuration即可成为“基于java配置”的配置类。
先写一个测试:
class ContainerTest {
ApplicationContext context =
new AnnotationConfigApplicationContext(MainConfig.class);
@Test
void shouldCreateContainer() {
assertThat(context).isNotNull();
}
}
运行测试编译不通过,因为我们还没有MainConfig.class
,这就是我们需要创建的配置类:
package com.example.demo.config;
import org.springframework.context.annotation.Configuration;
@Configuration
public class MainConfig {
}
测试代码引入MainConfig.class所在的包,后运行测试通过,表明我们创建了一个基于java配置类的容器。task 2.1完成,接下来我们要向容器里注册bean,为此我们更新我们的todo-list:
1.~~ 先要有(创建)一个容器。~~
创建一个可以使用Spring IoC的项目- “喂”configuration metadata给这个容器
创建spring 基于java配置的配置文件,并用此创建容器- 向容器注册组件
- 取出容器中的值使用
task2.2 向容器注册组件
-
先写个测试
@Test void shouldContianBean() { assertThat(context.containsBean("aPerson")).isTrue(); }
整个测试文件:
class ContainerTest { ApplicationContext context = new AnnotationConfigApplicationContext(MainConfig.class); @Test void shouldCreateContainer() { assertThat(context).isNotNull(); } @Test void shouldContianBean() { assertThat(context.containsBean("aPerson")).isTrue(); } }
-
为使得测试通过在配置类中注册名为“aPerson”的bean
package com.example.demo.config; import com.example.demo.bean.Person; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; @Configuration public class MainConfig { // contianer 默认以方法名作为查找条件, // 既此bean将向container注册是一个id或name为aPerson的bean @Bean public Person aPerson() { return new Person(); } }
-
创建POJO类
package com.example.demo.bean; import lombok.AllArgsConstructor; import lombok.Data; import lombok.NoArgsConstructor; @Data @NoArgsConstructor @AllArgsConstructor public class Person { private String name; private String age; }
至此运行测试通过,task2完成,todo-list更新为:
-
先要有(创建)一个容器。创建一个可以使用Spring IoC的项目
-
“喂”configuration metadata给这个容器创建spring 基于java配置的配置文件,并用此创建容器向容器注册组件
- 取出容器中的值使用
开始task3!
task3 取出容器中的值使用
- 写测试 ,在上个任务的测试类中添加
@Test void shouldGetBean(){ Person bean = (Person) context.getBean("aPerson"); bean.setAge(30); bean.setName("Tom"); assertThat(bean.getAge()).isEqualTo(30); assertThat(bean.getName()).isEqualTo("Tom"); }
测试通过,所有任务都完成,todo-list
-
先要有(创建)一个容器。创建一个可以使用Spring IoC的项目
-
“喂”configuration metadata给这个容器创建spring 基于java配置的配置文件,并用此创建容器向容器注册组件
取出容器中的值使用
总结
- 两个注解:@Configuration、@Bean, 配合使用
- 三个步骤:
- 创建一个配置类,标注@Confguration
- 创建POJO了,在第一步的类中添加用@Bean标注的方法,返回类型为这个POJO的对象
- 使用此文件创建一个AnnotationConfigApplicationContext,getBean获得上一步注册的bean,卡调用bean山的方法进行使用
- 一个关注点:使用POJO类,无需用new来构建,构建有容器完成,我们只需要区容器中拿