Spring 全家桶
- Spring Framework
- Spring Boot
- Spring Cloud (微服务)
- Spring Cloud Data Flow (数据集成)
Spring Framework
- Spring Core
- IoC 面向对象、AOP 面向切面编程-----(用来管理对象bean的一种思想)
- Spring Data Access
- Transactions、Spring MyBatis
- Web Servlet
- Spring MVC
- Integration
- Email、Scheduling、AMQP、Security
Spring IoC
- Inversion of Control 控制反转,一种面向对象的编程的设计思想 (减少对象之间的耦合度)eg : 自己管理对象 a.set(b) 建立对象a,b之间的关系 。耦合度高
- Dependency Injection 依赖注入,IoC的实现方式
- IoC Container IoC容器,实现依赖注入的关键,本质是一个工厂
在CommunityApplication.java 中SpringApplication.run(CommunityApplication.class, args); 会自动创建容器。
package com.myproject.community; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; @SpringBootApplication public class CommunityApplication { public static void main(String[] args) { //自动创建Spring容器,扫描配置类和其子类的包会被扫描到。 //需要写注解才能被扫描 4个 // @Service 业务 // @Component 通用的 // @Repository 数据库访问 // @Controller 处理请求 SpringApplication.run(CommunityApplication.class, args); } }
如果其他类需要获得容器,只需要implement ApplicationContextAware 接口并且重写set方法。
假设有一个AlphaDao 接口,AlphaDaoHibernateImpl (类内注解 @Repository("alphaHibernate") 起别名)和 AlphaDaoMyBatisImpl (默认优先级较高,类内注解 @Primary 实现)都是其具体实现。
默认调用时,会调用优先级高的,但也指定调用 applicationContext.getBean("alphaHibernate",AlphaDao.class);
AlphaDao
package com.myproject.community.dao; public interface AlphaDao { String select(); }
AlphaDaoHibernateImpl
package com.myproject.community.dao; import org.springframework.stereotype.Repository; @Repository("alphaHibernate") //访问数据库使用 Repository ,获取bean并自动装配 public class AlphaDaoHibernateImpl implements AlphaDao{ @Override public String select() { return "Hibernate"; } }
AlphaDaoMyBatisImpl
package com.myproject.community.dao; import org.springframework.context.annotation.Primary; import org.springframework.stereotype.Repository; @Repository @Primary //拥有更高优先级,优先装配 public class AlphaDaoMyBatisImpl implements AlphaDao{ @Override public String select() { return "MyBatis"; } }
AlphaService
@Service //@Scope("prototype") //默认是单例@Scope("singleton"),初始化一个对象 public class AlphaService { @Autowired private AlphaDao alphaDao; public AlphaService(){ System.out.println("实例化/构造AlphaService"); } @PostConstruct //让容器在合适的时候调用这个方法,这个方法会在构造器之后调用 public void init(){ System.out.println("初始化AlphaService"); } @PreDestroy //在销毁对象之前调用 public void destory(){ System.out.println("销毁 AlphaService"); } public String find(){ return alphaDao.select(); } }
测试代码 分主动获取和依赖注入。
package com.myproject.community; import com.myproject.community.dao.AlphaDao; import com.myproject.community.service.AlphaService; import org.junit.jupiter.api.Test; import org.springframework.beans.BeansException; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationContextAware; import org.springframework.test.context.ContextConfiguration; import java.text.SimpleDateFormat; import java.util.Date; @SpringBootTest @ContextConfiguration (classes = CommunityApplication.class) //保证测试类的配置类和正式环境是一样的 //Ioc 是Spring 容器,容器是自动被创建的,如何得到这个容器呢? // 想要获得容器的类 实现ApplicationContextAware接口,并且实现set方法 , // ApplicationContext、继承于HierarchicalBeanFactory继承于BeanFactory---Spring容器的顶层接口, // 子接口比父接口扩展了更多的方法 class CommunityApplicationTests implements ApplicationContextAware { private ApplicationContext applicationContext; @Override public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { this.applicationContext = applicationContext; } //—————————————————————————————主动获取的方式———————————————————————————————————————— @Test void testApplicationContext() { System.out.println(applicationContext); // 使用这个容器管理 bean AlphaDao alphaDao = applicationContext.getBean(AlphaDao.class); System.out.println(alphaDao.select()); //强制获取 alphaDao = applicationContext.getBean("alphaHibernate",AlphaDao.class); System.out.println(alphaDao.select()); } @Test //测试ApplicationContext 对于对象的初始化和销毁 void testBeanManage(){ AlphaService alphaService = applicationContext.getBean(AlphaService.class); System.out.println(alphaService); alphaService = applicationContext.getBean(AlphaService.class); System.out.println(alphaService); //被Spring容器管理的bean默认是单例的,只被实例化一次.通常情况下都是单例的。 } @Test //测试ApplicationContext 对于对象的初始化和销毁 void testBeanConfig(){ SimpleDateFormat simpleDateFormat = applicationContext.getBean(SimpleDateFormat.class); System.out.println(simpleDateFormat.format(new Date())); } //—————————————————————————————依赖注入——————————————————————————————————————— //依赖注解可以通过 构造器,set方法注入,但是通常加在属性之前,直接注入给属性 @Autowired @Qualifier("alphaHibernate") private AlphaDao alphaDao; @Autowired private SimpleDateFormat simpleDateFormat; @Autowired private AlphaService alphaService; @Test public void testDI(){ System.out.println(alphaDao); System.out.println(simpleDateFormat.format(new Date())); System.out.println(alphaService); } }
依赖注入 @Autowired
获取指定名称AAA的 @Qualifier("AAA")
主动获取
被Spring容器管理的bean默认是单例的,只被实例化一次(打印输出的地址相同),多例需要在对应Service中使用 @Scope("prototype") 通常情况下都是单例的。
使用这个容器管理 bean,默认获取优先级高的,也可以强制获取。
自定义Bean(AlphaConfig )
simpleDateFormat 方法名就是 Bean的名字
@Configuration 注解表示这个是配置类,不是一个普通的类
package com.myproject.community.config; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import java.text.SimpleDateFormat; @Configuration //注解表示这个是配置类,不是一个普通的类 public class AlphaConfig { //因为项目中时间格式基本都一样,所以装配到Bean中可以反复用,即方法返回的对象将会被装配到容器中 //simpleDateFormat 方法名就是 Bean的名字 @Bean public SimpleDateFormat simpleDateFormat(){ return new SimpleDateFormat("yyyy-MM-dd HH:mm:ss"); } }
项目结构
开发过程之中,controller处理浏览器的请求,过程中会调用业务组件service处理业务,业务组件会调用dao去访问数据,相互依赖。 他们的依赖关系就可以用依赖注入的方式实现。
AlphaController
package com.myproject.community.controller; import com.myproject.community.service.AlphaService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Controller; import org.springframework.stereotype.Repository; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.ResponseBody; @Controller @RequestMapping("/alpha") //给这个类取一个名 public class AlphaController { @Autowired private AlphaService alphaService; //依赖注入 @RequestMapping("/hello") ///给这个方法取一个名 @ResponseBody // 如果不加,默认是返回一个网页,加上默认返回字符串 public String sayHello (){ return "Hello Spring Boot."; } @RequestMapping("/data") @ResponseBody public String getData(){ return alphaService.find(); } }
AlphaService
package com.myproject.community.service; import com.myproject.community.dao.AlphaDao; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Scope; import org.springframework.stereotype.Service; import javax.annotation.PostConstruct; import javax.annotation.PreDestroy; import javax.swing.*; @Service //@Scope("prototype") public class AlphaService { @Autowired private AlphaDao alphaDao; public AlphaService(){ System.out.println("实例化/构造AlphaService"); } @PostConstruct //让容器在合适的时候调用这个方法,这个方法会在构造器之后调用 public void init(){ System.out.println("初始化AlphaService"); } @PreDestroy //在销毁对象之前调用 public void destory(){ System.out.println("销毁 AlphaService"); } public String find(){ return alphaDao.select(); } }
AlphaDao
package com.myproject.community.dao; public interface AlphaDao { String select(); }
本期代码版本
链接:https://pan.baidu.com/s/1XZXMUhpoNvPLRIYVOzaggA
提取码:tqra
复制这段内容后打开百度网盘手机App,操作更方便哦