互联网架构-Spring5.0源码深度解析-019:理解Configuration注解

1 Spring5.0深度源码分析课程介绍

Spring5.0源码深度解析课程安排
1.Spring5.0注解配置启动方式与常用组件
2.Spring5.0IOC容器源码分析
3.Spring5.0声明事务源码分析
4.Spring5.0 Aop切面编程源码分析
5.SpringMVC源码深度解析
6.SpringBoot2.0源码深度解析
7.纯手写SpringIOC注解方式
8.纯手写SpringMVC注解方式
9.纯手写SpringBoot2.0
Spring5.0、SpringMVC 、SpringBoot2.0

课题内容:
1.Spring5.0框架环境搭建
2.基于XML环境搭建Spring环境
3.基于注解环境搭建Spring环境
4.Configuration的作用
5.@Scope、@Lazy注解的作用

2 简单回顾Spring基础知识内容

Spring框架快速入门
什么是Spring框架

Spring 框架是 Java 应用最广的框架,它的成功来源于理念,而不是技术本身,它的理念包括 IoC (Inversion of Control,控制反转)AOP(Aspect Oriented Programming,面向切面编程)
理念:每个bean与bean之间的关系统一交给SpringIOC容器管理

New UserService(); 扫包、注解形式注入 使用容器帮助我们创建对象 底层大量反射机制。

Spring体系结构
1、Spring Core:主要组件是BeanFactory,创建JavaBean的工厂,使用控制反转(IOC) 模式 将应用程序的配置和依赖性规范与实际的应用程序代码分开。
2、Spring AOP:集成了面向切面的编程功能(AOP把一个业务流程分成几部分,例如权限检查、业务处理、日志记录,每个部分单独处理,然后把它们组装成完整的业务流程。每个部分被称为切面),可以将声明性事物管理集成到应用程序中。
3、Spring Context:一个核心配置文件,为Spring框架提供上下文信息。
4、Spring Do:Spring操作数据库的模块。
5、Spring ORM:Spring集成了各种orm(object relationship mapping 对象关系映射)框架的模块,集成mybatis
6、Spring Web集成各种优秀的web层框架的模块(Struts、Springmvc)
7、Spring web MVC:Spring web层框架

思考一个问题,为什么启动SpringBoot项目的时候需要加上@Configuration、@ComponentScan

3 基于Xml方式搭建Spring5.0环境

快速构建Spring环境
Maven依赖信息

<dependency>
  <groupId>org.springframework</groupId>
  <artifactId>spring-context</artifactId>
  <version>5.0.0.RELEASE</version>
</dependency>

Xml方式环境搭建
applicationContext.xml

<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:p="http://www.springframework.org/schema/p"
       xmlns:context="http://www.springframework.org/schema/context"
       xsi:schemaLocation="
        http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd">
    <!-- bean id 容器id  class 使用java的反射机制初始化-->
    <bean id="userEntity" class="com.mayikt.v1.entity.UserEntity">
        <property name="userId" value="10"/>
        <property name="userName" value="mayikt"/>
    </bean>
</beans>

注册的bean对象

public class UserEntity {

    private String userName;
    private Integer userId;

    public void setUserName(String userName) {
        this.userName = userName;
    }

    public void setUserId(Integer userId) {
        this.userId = userId;
    }

    @Override
    public String toString() {
        return "UserEntity{" +
                "userName='" + userName + '\'' +
                ", userId=" + userId +
                '}';
    }
}

测试类

public class V1TestSpring {
    private static ClassPathXmlApplicationContext applicationContext;
    public static void main(String[] args) {
        applicationContext= new ClassPathXmlApplicationContext("applicationContext.xml");
        UserEntity userEntity = (UserEntity) applicationContext.getBean("userEntity");
        System.out.println(userEntity.toString()); //UserEntity{userName='mayikt', userId=10}
        // spring中的beanid 如果重复的话会怎么样?
        // 启动的时候报错
    }
}

4 基于注解形式搭建Spring5.0环境

注解方式环境搭建
使用Configuration 配置容器

@Configuration  // @Configuration等同于spirng xml
public class MySpringConfig {

    // <bean id = "userEntity" class = "方法名称">
    @Bean
    public UserEntity userEntity(){
        return new UserEntity("mayikt",666);
    }
}

注册的bean对象

public class UserEntity {

    private String userName;
    private Integer userId;

    public void setUserName(String userName) {
        this.userName = userName;
    }

    public void setUserId(Integer userId) {
        this.userId = userId;
    }

    @Override
    public String toString() {
        return "UserEntity{" +
                "userName='" + userName + '\'' +
                ", userId=" + userId +
                '}';
    }

    public UserEntity(String userName, Integer userId) {
        this.userName = userName;
        this.userId = userId;
    }
}

使用注解形式形式加载IOC

public class V2TestSpring {
    private static AnnotationConfigApplicationContext annotationConfigApplicationContext;

    public static void main(String[] args) {
        annotationConfigApplicationContext = new AnnotationConfigApplicationContext(MySpringConfig.class);
        UserEntity userEntity = annotationConfigApplicationContext.getBean("userEntity", UserEntity.class);
        System.out.println(userEntity.toString()); //UserEntity{userName='mayikt', userId=666}
    }
}

5 @ComponentScan使用方法

MySpringConfig

@Configuration  // @Configuration等同于spirng xml
@ComponentScan("com.mayikt.v2")
public class MySpringConfig {

    // <bean id = "userEntity" class = "方法名称">
    @Bean
    public UserEntity userEntity(){
        return new UserEntity("mayikt",666);
    }
}

自己写的类注入

@Controller
public class UserController {
}
@Repository
public class UserDao {
}
@Service
public class UserService {
}

测试类

public class V2TestSpring {
    private static AnnotationConfigApplicationContext annotationConfigApplicationContext;

    public static void main(String[] args) {
        annotationConfigApplicationContext = new AnnotationConfigApplicationContext(MySpringConfig.class);

        UserService userService = annotationConfigApplicationContext.getBean("userService", UserService.class);
        System.out.println("userService:" + userService);
        // 获取spring注入的对象
        String[] beanDefinitionNames = annotationConfigApplicationContext.getBeanDefinitionNames();
        for(String i : beanDefinitionNames){
            System.out.println(i);
        }
    }
}

如果需要将外部的jar包注入spring容器中 @Bean
自己写的类注入@Service、@Repository 、@Controller
@ComponentScan 扫包注入spring容器

运行结果:
在这里插入图片描述

6 Spring装配bean单例与多例

@Scope
默认情况Spring容器是单例的

public class V2TestSpring {
    private static AnnotationConfigApplicationContext annotationConfigApplicationContext;

    public static void main(String[] args) {
        annotationConfigApplicationContext = new AnnotationConfigApplicationContext(MySpringConfig.class);
        UserService userService1 = annotationConfigApplicationContext.getBean("userService", UserService.class);
        UserService userService2 = annotationConfigApplicationContext.getBean("userService", UserService.class);
        System.out.println(userService1 == userService2); // true
    }
}

singleton单例模式:全局有且仅有一个实例。
prototype原型模式:每次获取Bean的时候都会有一个新的实例。

@Service
@Scope("prototype")
public class UserService {
}
public class V2TestSpring {
    private static AnnotationConfigApplicationContext annotationConfigApplicationContext;

    public static void main(String[] args) {
        annotationConfigApplicationContext = new AnnotationConfigApplicationContext(MySpringConfig.class);
        UserService userService1 = annotationConfigApplicationContext.getBean("userService", UserService.class);
        UserService userService2 = annotationConfigApplicationContext.getBean("userService", UserService.class);
        System.out.println(userService1 == userService2); // false
    }
}

7 Spring装配Bean懒汉式与饿汉式

@Lazy
Lazy表示为懒加载,当真正需要引用获取的时候才会被加载;
1.不写@Lazy的情况下(或者写@Lazy(false)),默认饿汉式,在IOC容器加载的时候被创建;

@Service
public class UserService {
    public UserService(){
        System.out.println("无参构造函数被执行...");
    }
}
public class V2TestSpring {
    private static AnnotationConfigApplicationContext annotationConfigApplicationContext;

    public static void main(String[] args) {
        annotationConfigApplicationContext = new AnnotationConfigApplicationContext(MySpringConfig.class);
        System.out.println("启动配置加载完毕...");
        UserService userService1 = annotationConfigApplicationContext.getBean("userService", UserService.class);
    }
}

运行结果:
在这里插入图片描述
2.写@Lazy/@Lazy(true)表示懒汉式;

@Service
@Lazy
public class UserService {

    public UserService(){
        System.out.println("无参构造函数被执行...");
    }
}

运行结果:
在这里插入图片描述

8 ComponentScan排除用法

@ComponentScan FilterType 有四种类型
ANNOTATION:注解类型
ASSIGNABLE_TYPE:ANNOTATION:指定的类型
ASPECTJ:按照Aspectj的表达式,基本上不会用到
REGEX:按照正则表达式
CUSTOM:自定义规则

包含扫包范围

@Configuration  // @Configuration等同于spirng xml
@ComponentScan(value = "com.mayikt.v2",
        includeFilters = {@ComponentScan.Filter(type = FilterType.ANNOTATION, classes = Service.class)}, useDefaultFilters = false)
public class MySpringConfig {

    // <bean id = "userEntity" class = "方法名称">
    @Bean
    public UserEntity userEntity() {
        return new UserEntity("mayikt", 666);
    }
}
public class V2TestSpring {
    private static AnnotationConfigApplicationContext annotationConfigApplicationContext;

    public static void main(String[] args) {
        annotationConfigApplicationContext = new AnnotationConfigApplicationContext(MySpringConfig.class);
        System.out.println("启动配置加载完毕...");
        String[] beanDefinitionNames = annotationConfigApplicationContext.getBeanDefinitionNames();
        for(String i : beanDefinitionNames){
            System.out.println(i);
        }
    }
}

只有类上有@Service注解的会注入到spring容器

运行结果:
在这里插入图片描述
不包含扫包范围

@Configuration  // @Configuration等同于spirng xml
@ComponentScan(value = "com.mayikt.v2",
        excludeFilters = {@ComponentScan.Filter(type = FilterType.ANNOTATION, classes = Service.class)}, useDefaultFilters = true)
public class MySpringConfig {

    // <bean id = "userEntity" class = "方法名称">
    @Bean
    public UserEntity userEntity() {
        return new UserEntity("mayikt", 666);
    }
}

运行结果:
在这里插入图片描述

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值