Spring一.Spring概述1.什么是Spring代码语言:javascript代码运行次数:0运行复制Spring是分层的JavaEE应用 full-stack(全栈) 轻量级开源框架。
Spring的核心是IOC(Inverse Of Control:控制反转)和 AOP(Aspect Oriented Programming:面向切面编程)
Spring一个全栈应用框架, 提供了表现层 Spring MVC 和持久层 Spring JDBC 以及业务层事务管理等众多应用技术
Spring还能整合开源世界众多著名的第三方框架和类库,逐渐成为使用最多的 Java EE 企业应用开源框架
==Spring理念 : 使现有技术更加实用 . 本身就是一个大杂烩 , 整合现有的框架技术。2.为什么要学习Spring最大程度的简化了开发代码语言:javascript代码运行次数:0运行复制 Spring是一个非常优秀的java框架,其目标是为了简化java企业级开发,Spring出来已经二十几年了,这期间也一直围绕着这个目标在进行,像后面需要学习的Springmvc、Springboot、Springcloud,这些技术也都是围绕着简化开发的目标在努力,到目前为止已经做的足够好了,可以说Spring除不能帮助我们实现业务逻辑代码之外,其他的事情Spring都尽量去帮我们简化,使用Spring可以帮助我们节约大量开发时间。
不使用Spring的情况下,开发一个项目可能需要2个月,用了Spring可能1个月都不需要,你说这样的技术你想学么?大量公司使用代码语言:javascript代码运行次数:0运行复制目前99%的公司使用了Spring,可以去各大招聘网站看一下,Spring算是必备技能,所以一定要掌握。顶尖的源代码代码语言:javascript代码运行次数:0运行复制Spring框架源码设计非常优秀,在java开源项目中可以说是顶级的,目前为止还未发现比Spring更优秀的开源项目,所以想提升代码能力的,强烈建议多看看Spring的源码;关于提升代码能力的,还可以去看一下jdk的源码,也是非常棒的,里面有很多大师的杰作。3.Spring的发展历程代码语言:javascript代码运行次数:0运行复制 要谈Spring的历史,就要先谈J2EE。J2EE应用程序的广泛实现是在1999年和2000年开始的,它的出现带来了诸如事务管理之类的核心中间层概念的标准化,但是在实践中并没有获得绝对的成功,因为开发效率,开发难度和实际的性能都令人失望。
曾经使用过EJB开发JAVAEE应用的人,一定知道,在EJB开始的学习和应用非常的艰苦,很多东西都不能一下子就很容易的理解。EJB要严格地实现各种不同类型的接口,类似的或者重复的代码大量存在。而配置也是复杂和单调,同样使用JNDI进行对象查找的代码也是单调而枯燥。虽然有一些开发工作随着xdoclet的出现,而有所缓解,但是学习EJB的高昂代价,和极低的开发效率,极高的资源消耗,都造成了EJB的使用困难。而Spring出现的初衷就是为了解决类似的这些问题。
Spring的形成,最初来自Rod Jahnson所著的一本很有影响力的书籍《Expert One-on-One J2EE Design and Development》,就是在这本书中第一次出现了Spring的一些核心思想,该书出版于2002年。2004年编著《Expert one-on-one J2EE Development without EJB》阐述了JavaEE开发时不使用EJB的解决方式(Spring 雏形),同年4月spring1.0诞生。2006年10月,发布 Spring2.0 2009年12月,发布 Spring3.0 2013年12月,发布 Spring4.0 2017年9月, 发布最新 Spring5.0 通用版(GA)
4.Spring的特点及优点 Spring 除了不能帮我们写业务逻辑.其余的几乎什么什么都能帮助我们简化开发
方便解耦,简化开发
通过Spring提供的IoC容器,我们可以将对象之间的依赖关系交由Spring进行控制,避免硬编码所造成的过度程序耦合。有了Spring,用户不必再为单实例模式类、属性文件解析等这些很底层的需求编写代码,可以更专注于上层的应用。
AOP编程的支持
通过Spring提供的AOP功能,方便进行面向切面的编程,许多不容易用传统OOP实现的功能可以通过AOP轻松应付。
声明式事务的支持
在Spring中,我们可以从单调烦闷的事务管理代码中解脱出来,通过声明式方式灵活地进行事务的管理,提高开发效率和质量。
方便程序的测试
可以用非容器依赖的编程方式进行几乎所有的测试工作,在Spring里,测试不再是昂贵的操作,而是随手可做的事情。例如:Spring对Junit4支持,可以通过注解方便的测试Spring程序。
方便集成各种优秀框架
Spring不排斥各种优秀的开源框架,相反,Spring可以降低各种框架的使用难度,Spring提供了对各种优秀框架(如Struts,Hibernate、Hessian、Quartz)等的直接支持。
降低Java EE API的使用难度
Spring对很多难用的Java EE API(如JDBC,JavaMail,远程调用等)提供了一个薄薄的封装层,通过Spring的简易封装,这些Java EE API的使用难度大为降低。
Java 源码是经典学习范例
Spring的源码设计精妙、结构清晰、匠心独运,处处体现着大师对Java设计模式灵活运用以及对Java技术的高深造诣。Spring框架源码无疑是Java技术的最佳实践范例。如果想在短时间内迅速提高自己的Java技术水平和应用开发水平,学习和研究Spring源码将会使你收到意想不到的效果。
==一句话概括:Spring是一个轻量级的控制反转(IoC)和面向切面(AOP)的容器(框架)==
5.Spring体系结构二.IoC快速入门1.Ioc引入dao层代码语言:javascript代码运行次数:0运行复制public interface UserDao {
public void login();
}代码语言:javascript代码运行次数:0运行复制public class UserDaoImpl implements UserDao {
@Override
public void login() {
System.out.println("dao层登录成功!!!");
}
}service层代码语言:javascript代码运行次数:0运行复制public interface UserService {
public void login();
}代码语言:javascript代码运行次数:0运行复制public class UserServiceImpl implements UserService {
//注入业务层
private UserDao userDao = new UserDaoImpl();
@Override
public void login() {
System.out.println("业务层 登录!!!");
//调用dao层方法
this.userDao.login();
}
}测试代码语言:javascript代码运行次数:0运行复制public class UserServiceTest {
//测试
@Test
public void login() {
UserService userService = new UserServiceImpl();
userService.login();
}
}2.反思代码语言:javascript代码运行次数:0运行复制【思考分析】
代码过于耦合,上层代码过度依赖于下一层代码的实现:
UserDAO userDAO = new UserDAOImpl();
如果要更换实现类,必须要修改原来的业务代码!代码语言:javascript代码运行次数:0运行复制 解决方案:采用IoC(Inverse of Control,控制反转)的思想。
简单的说就是引入工厂(第三者),将原来在程序中手动创建管理的依赖的UserDAO对象,交给工厂来创建管理。在Spring框架中,这个工厂就是Spring中的工厂,因此,也可以说,将创建管理UserDAO对象的控制权被反转给了Spring框架了。3.IoC的本质代码语言:javascript代码运行次数:0运行复制 控制反转IoC(Inversion of Control),是一种设计思想,而不是一种新的技术。DI(依赖注入)是实现IoC的一种方法,也有人认为DI只是IoC的另一种说法(不对)。没有IoC的程序中,我们使用面向对象编程,对象的创建与对象间的依赖关系完全硬编码在程序中,对象的创建由程序自己控制,控制反转后将对象的创建转移给第三方。
所谓控制反转就是:获得依赖对象的方式反转
IoC是Spring框架的核心内容,使用多种方式完美的实现了IoC,可以使用XML配置,也可以使用注解,
新版本的Spring也可以零配置实现IoC。
Spring容器在初始化时先读取配置文件,根据配置文件或元数据创建与组织对象存入容器中,程序使用
时再从Ioc容器中取出需要的对象4.IOC实现4.1添加spring相关依赖代码语言:javascript代码运行次数:0运行复制
4.2核心配置文件applicationContext.xml 约束头代码语言:javascript代码运行次数:0运行复制
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
* @Auther: yanqi
* @Desc 业务层
*/
public class UserServiceImpl implements UserService {
//注入业务层
// private UserDao userDao = new UserDaoImpl();
@Override
public void login() {
System.out.println("业务层登录!!!");
//现在要通过spring工厂来获取bean对象,如何获取呢?
//1、找到bean对象所在的applicationContext.xml配置文件
//ClassPathXmlApplicationContext 会默认加载resources下的applicationContext.xml
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//2、找到工厂中bean的唯一标识
//方式一
UserDao userDao1 = (UserDao) applicationContext.getBean("userDao");
//方式二
UserDao userDao2 = applicationContext.getBean("userDao", UserDao.class);
//方式三 通过找到接口类实现对象的创建,省去了bean的id或name --了解
UserDao userDao3 = applicationContext.getBean(UserDao.class);
UserDao userDao4 = applicationContext.getBean(UserDaoImpl.class);
//调用dao层方法
userDao3.login();
}
}三.DI依赖注入代码语言:javascript代码运行次数:0运行复制DI Dependency Injection 依赖注入,在Spring框架负责创建Bean对象时,动态的将依赖对象注入到Bean组件
简单的说,可以将一个bean对象动态的注入到另外一个bean中5.1配置文件applicationContext.xml
代码语言:javascript代码运行次数:0运行复制
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">
* @Auther: yanqi
* @Desc 业务层
*/
public class UserServiceImpl implements UserService {
//属性注入
private UserDao userDao;
public void setUserDao(UserDao userDao) {
this.userDao = userDao;
}
@Override
public void login() {
System.out.println("业务层 登录!!!");
//调用dao层方法
userDao.login();
}
}5.3测试代码语言:javascript代码运行次数:0运行复制/**
* @Auther: yanqi
* @Desc 测试类
*/
public class UserServiceTest {
@Test
public void login() {
// UserService userService = new UserServiceImpl();
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//获取bean对象
UserService userService = applicationContext.getBean("userService", UserService.class);
userService.login();
}
}6.Spring核心接口BeanFactory 这是IOC容器的顶级接口 它定义了IOC的最基础的功能, 但是其功能比较简单,一般面向Spring自身使用
在第一次使用到某个Bean时(调用getBean()),才对该Bean进行加载实例化[用的时候再创建] --> 【懒汉设计】
ApplicationContext 这是在BeanFactory基础上衍生出的接口,它扩展了BeanFactory的功能,一般面向程序员使用
在容器启动时,一次性创建并加载了所有的Bean [初始化的时候全创建好] --> 【饿汉设计】
上面两种方式创建的对象都是单例, 只是创建对象的时机不同
代码语言:javascript代码运行次数:0运行复制public class UserServiceTest {
@Test
public void login() {
// UserService userService = new UserServiceImpl();
// ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//BeanFactory是bean工厂的顶级接口,了解即可
BeanFactory beanFactory = new XmlBeanFactory(newClassPathResource("applicationContext.xml"));
//获取bean对象
UserService userService = beanFactory.getBean("userService", UserService.class);
userService.login();
}
}四.基于XML配置方式实例化Bean的四种方式第一种 无参数构造器 (最常用*)代码语言:javascript代码运行次数:0运行复制public class Bean1 {
}代码语言:javascript代码运行次数:0运行复制
public void login() {
//获取配置文件
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//获取bean对象
Bean1 bean1 = applicationContext.getBean("bean1", Bean1.class);
System.out.println(bean1);
}第二种 静态方式代码语言:javascript代码运行次数:0运行复制public class Product {
private Integer id;
private String name;
}代码语言:javascript代码运行次数:0运行复制public class StaticFactory {
static Product getInstance(){
return new Product();
}
}代码语言:javascript代码运行次数:0运行复制
public void login() {
//获取配置文件
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//获取bean对象
Bean2 bean2 = applicationContext.getBean("bean2", Bean2.class);
System.out.println(bean2);
}第三种 普通方法代码语言:javascript代码运行次数:0运行复制public class Product {
private Integer id;
private String name;
}代码语言:javascript代码运行次数:0运行复制public class ProFactory {
public Product getProduct(){
return new Product();
}
}代码语言:javascript代码运行次数:0运行复制
public void login() {
//获取配置文件
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
Product product = (Product) ac.getBean("product");
System.out.println(product);
}第四种 FactoryBean方式-了解代码语言:javascript代码运行次数:0运行复制public class Bean4 {
}代码语言:javascript代码运行次数:0运行复制/**
* @Desc 实现FactoryBean接口
*/
public class Bean4Test implements FactoryBean
//返回bean对象即可
@Override
public Bean4 getObject() throws Exception {
return new Bean4();
}
@Override
public Class> getObjectType() {
return null;
}
}代码语言:javascript代码运行次数:0运行复制
public void login() {
//获取配置文件
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//获取bean对象
Bean4 bean4 = applicationContext.getBean("bean4", Bean4.class);
System.out.println(bean4);
}五.Bean对象配置相关属性属性名
描述
id
在ioc容器的唯一标识
class
创建对象实例的全限定名
scope
声明此对象的作用范围
singleton:单例对象(默认)
prototype:多例对象
init-method
在对象创建时,执行此方法
destroy-method
在对象销毁时,执行此方法
Bean的作用域 Singleton: 在一个spring容器中,对象只有一个实例。(默认值)
Prototype: 在一个spring容器中,存在多个实例,每次getBean 返回一个新的实例
代码语言:javascript代码运行次数:0运行复制public class SingletonBean {
public SingletonBean() {
System.out.println("我是单例。。。");
}
}代码语言:javascript代码运行次数:0运行复制public class PrototypeBean {
public PrototypeBean() {
System.out.println("我是多例。。。。");
}
}代码语言:javascript代码运行次数:0运行复制
代码语言:javascript代码运行次数:0运行复制 @Test
public void login() {
//获取配置文件
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//作用域
SingletonBean singletonBean1 = applicationContext.getBean("singletonBean", SingletonBean.class);
SingletonBean singletonBean2 = applicationContext.getBean("singletonBean", SingletonBean.class);
System.out.println(singletonBean1);
System.out.println(singletonBean2);
PrototypeBean prototypeBean1 = applicationContext.getBean("prototypeBean", PrototypeBean.class);
PrototypeBean prototypeBean2 = applicationContext.getBean("prototypeBean", PrototypeBean.class);
System.out.println(prototypeBean1);
System.out.println(prototypeBean2);
}Bean的生命周期 生命周期主要演示对象的创建和销毁时机!!!
需要用到两个属性: init-method 和 destroy-method
lifecycle
代码语言:javascript代码运行次数:0运行复制public class LifecycleDemo {
public LifecycleDemo() {
System.out.println("对象实例化了");
}
public LifecycleDemo(String name) { //带一个参数的构造方法
}
public void initBean(){
System.out.println("bean初始化");
}
public void DistroyBean(){
System.out.println("bean销毁");
}
}代码语言:javascript代码运行次数:0运行复制
public void login() {
//获取配置文件
ApplicationContext ac = new ClassPathXmlApplicationContext("applicationContext.xml");
LifecycleDemo lifecycleDemo = applicationContext.getBean("lifecycleDemo", LifecycleDemo.class);
System.out.println(lifecycleDemo);
} 查看结果:
对象实例化了 初始化 我是单例。。。 cn.yanqi.lifecycle.LifecycleDemo@7b69c6ba
代码语言:javascript代码运行次数:0运行复制测试查看控制台打印,发现销毁方法没有执行。
原因:销毁方法的执行必须满足两个条件:
1) 单例(singleton)的bean才可以手动销毁。
2) 必须手动关闭容器(close)时,才会执行手动销毁的方法。
多例没就destroy-method 方法,只对单例有作用手动关闭代码语言:javascript代码运行次数:0运行复制 @Test
public void login() {
//获取配置文件
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
LifecycleDemo lifecycleDemo = applicationContext.getBean("lifecycleDemo", LifecycleDemo.class);
System.out.println(lifecycleDemo);
//使用junit调用时,当调用完毕时,junit会强制关jvm,但些时spring容器还没来的及关闭,所以不会有销毁方法
//想要看到销毁方法,需要手动关闭
((ClassPathXmlApplicationContext)applicationContext).close();
}六.Bean属性的依赖注入 什么是Bean属性的注入?就是对 一个对象的属性赋值
constructor
1.构造方法注入有参注入和无参注入
代码语言:javascript代码运行次数:0运行复制public class Car {
private Integer id;
private String name;
private Double price;
//提供有参无参构造方法,set get方法 toString方法
//可以写索引序号
}代码语言:javascript代码运行次数:0运行复制
代码语言:javascript代码运行次数:0运行复制 @Test
public void login() {
//获取配置文件
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//传统写法
Car car = new Car(1008,"单车",2d);
System.out.println(car);
//构造器属性注入
Car car2 = applicationContext.getBean("car", Car.class);
System.out.println(car2);
}2.set方法注入代码语言:javascript代码运行次数:0运行复制
我再创建一个person对象
代码语言:javascript代码运行次数:0运行复制public class Person {
private Integer id;
private String name;
private Car car;
//提供有参无参构造方法,set get方法 toString方法
} 代码语言:javascript代码运行次数:0运行复制
代码语言:javascript代码运行次数:0运行复制 @Test
public void login() {
//获取配置文件
ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
//set属性注入
Person person = applicationContext.getBean("person", Person.class);
System.out.println(person);
} 结果: Person{id=88, name='java', car=Car{id=1009, name='共享单车', price=1.5}}
3.P命名空间注入 p名称空间出现的目地为了简化以上两种注入方式
引入p名称空间约束头
代码语言:javascript代码运行次数:0运行复制 xmlns:p="http://www.springframework.org/schema/p" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd">代码语言:javascript代码运行次数:0运行复制 public void login() { //获取配置文件 ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); //set属性注入 Person person = applicationContext.getBean("person2", Person.class); System.out.println(person); } 查看结果: Person{id=99, name='rose', car=Car{id=1009, name='共享单车', price=1.5}} 4.集合类型属性注入代码语言:javascript代码运行次数:0运行复制@Data public class ConllectionBean { private List private Set private Map private Properties properties; }代码语言:javascript代码运行次数:0运行复制 代码语言:javascript代码运行次数:0运行复制 @Test public void login() { //获取配置文件 ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); //set属性注入 ConllectionBean conllectionBean = applicationContext.getBean("conllectionBean", ConllectionBean.class); System.out.println(conllectionBean); }七.基于注解配置方式spring-ioc-annotation bean对象-注解Spring 的【XML开发】和【注解开发】 导入依赖包是相同的 代码语言:javascript代码运行次数:0运行复制public interface UserDao { public void login(); }代码语言:javascript代码运行次数:0运行复制@Component("userDao")// 相当于 public class UserDaoImpl implements UserDao { @Override public void login() { System.out.println("dao层登录成功!!!"); } }代码语言:javascript代码运行次数:0运行复制public interface UserService { public void login(); }代码语言:javascript代码运行次数:0运行复制/** @Component("userService") 相当于 @Autowired 相当于 */ @Component("userService") public class UserServiceImpl implements UserService { //注入dao层对象 @Autowired private UserDao userDao; @Override public void login() { System.out.println("业务层 登录!!!"); userDao.login(); } }applicationContext.xml 注意,这里用注释方式,约束引入context 名称空间 代码语言:javascript代码运行次数:0运行复制 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 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"> 三个子注解具有分层含义 @Controller @Service @Repository代码语言:javascript代码运行次数:0运行复制@Repository("userDao") public class UserDaoImpl implements UserDao { @Override public void login() { System.out.println("dao层登录成功!!!"); } }代码语言:javascript代码运行次数:0运行复制@Service("userService") public class UserServiceImpl implements UserService { @Autowired private UserDao userDao; @Override public void login() { System.out.println("业务层 登录!!!"); userDao.login();}} 代码语言:javascript代码运行次数:0运行复制 @Test public void login() { ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); UserService userService = applicationContext.getBean("userService", UserService.class); userService.login(); }Bean属性的依赖注入 简单数据类型依赖注入 @Value("22") 代码语言:javascript代码运行次数:0运行复制@Data @Component public class Car { @Value("22") private Integer id; @Value("单车") private String name; @Value("1.5") private Double price; }代码语言:javascript代码运行次数:0运行复制 @Test public void login() { ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); Car car = applicationContext.getBean("car", Car.class); System.out.println(car); } 查看结果: Car(id=22, name=单车, price=1.5) 复杂类型数据依赖注入 @Autowired @Resource 代码语言:javascript代码运行次数:0运行复制@Service("userService") public class UserServiceImpl implements UserService { //第一种注入方式 @Autowired //第二种注入方式 // @Resource private UserDao userDao; @Override public void login() { System.out.println("业务层 登录!!!"); userDao.login(); } }代码语言:javascript代码运行次数:0运行复制 @Test public void login() { ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); UserService userService = applicationContext.getBean("userService", UserService.class); userService.login(); }Bean的初始化方法和销毁方法 @PostConstruct //初始化 == init-method @PreDestroy //销毁 == destory-method 代码语言:javascript代码运行次数:0运行复制@Component public class liftBean { @PostConstruct //初始化 == init-method public void aa(){ System.out.println("我初始化了"); } @PreDestroy //销毁 == destory-method public void bb(){ System.out.println("我over了"); } }代码语言:javascript代码运行次数:0运行复制 @Test public void login() { ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); applicationContext.getBean("liftBean", liftBean.class); //手动关闭,才会销毁 ((ClassPathXmlApplicationContext)applicationContext).close(); }Bean的作用域 @Scope("singleton")//单例 @Scope("prototype")//多例 代码语言:javascript代码运行次数:0运行复制@Component @Scope("singleton")//单例 @Scope("prototype")//多例 public class LiftBean { @PostConstruct //初始化 == init-method public void aa(){ System.out.println("我初始化了"); } @PreDestroy //销毁 == destory-method public void bb(){ System.out.println("我over了"); } }代码语言:javascript代码运行次数:0运行复制 @Test public void login() { ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); liftBean liftBean = applicationContext.getBean("liftBean", liftBean.class); liftBean liftBean2 = applicationContext.getBean("liftBean", liftBean.class); System.out.println(liftBean); System.out.println(liftBean2); }XML和注解混合配置 (重点)代码语言:javascript代码运行次数:0运行复制public class UserDaoImpl implements UserDao { @Override public void login() { System.out.println("dao层登录成功!!!"); } }代码语言:javascript代码运行次数:0运行复制public class UserServiceImpl implements UserService { @Autowired private UserDao userDao; @Override public void login() { System.out.println("业务层 登录!!!"); userDao.login(); } }代码语言:javascript代码运行次数:0运行复制 public void login() { ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); UserService userService = applicationContext.getBean("userService", UserService.class); userService.login(); }代码语言:javascript代码运行次数:0运行复制提示:因为采用注解开发时, 11.Spring的junit测试集成代码实现 Spring提供 spring-test.jar 可以整合junit。 好处:可以简化测试代码(不需要手动创建上下文) 代码语言:javascript代码运行次数:0运行复制 spring整合junit代码实现 代码语言:javascript代码运行次数:0运行复制@RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration(locations = "classpath:applicationContext.xml") public class UserServiceTest { //注入业务层 @Autowired private UserService userService; @Test public void login() { /*ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml"); UserService userService = applicationContext.getBean("userService", UserService.class);*/ userService.login(); } }代码语言:javascript代码运行次数:0运行复制@Service //直接注入不用再写对象名了 public class UserServiceImpl implements UserService { @Autowired private UserDao userDao; @Override public void login() { System.out.println("业务层 登录!!!"); userDao.login(); } }代码语言:javascript代码运行次数:0运行复制@Repository //直接注入不用再写对象名了 public class UserDaoImpl implements UserDao { @Override public void login() { System.out.println("dao层登录成功!!!"); } }