目录
Spring概述
spring全家桶:spring,springmvc,springboot,springcloud…..
框架怎么学:框架是一个软件,其他人写好的软件。
1、知道框架能做什么。myabtis--访问数据库,对表中的数据执行增删改查。
2、框架的语法,框架要完成一个功能,需要一定的步骤支持的。
3、框架的内容实现,框架内部怎么做。原理是什么,
4、通过学习,可以实现一个框架。
- spring:
- 出现是在2002左右,解决企业开发难度大的问题,减轻对项目模块之间的管理类和类之间的管理,帮助开发人员创建对象,管理对象之间的关系。
- spring核心技术IOC,AOP。能实现模块之间,类之间的解耦合。
- Spring的优点:
- 轻量
- Spring框架使用的jar都比较小,一般在1M以下或者几百kb。Spring核心功能的所需的jar总共在3M左右。
- Spring框架运行占用的资源少,运行效率高。不依赖其他jar
- 针对接口编程,解耦合
- Spring提供了IOC控制反转,由容器管理对象,对象的依赖关系。原来在程序代码中的对象创建方式,现在由容器完成。对象之间的依赖解耦合。
- AOP编程的支持
- 通过Spring提供的AOP功能,方便进行面向切面的编程,许多不容易用传统OOP实现得到功能可以通过AOP轻松应付。
- 在Spring中,开发人员可以从繁杂的事务管理代码中解脱出来,通过声明式方式灵活地进行事务的管理,提高开发效率和质量。
- 方便集成各种优秀框架
- Spring不排斥各种优秀的开源框架,相反Spring可以降低各种框架的使用难度,Spring提供了对各种优秀框架(Struts,Hibernate,MyBatis)等的直接支持。简化框架的使用,Spring像插线板一样,其他框架是插头,可以容易的组合到一起。需要使用哪个框架,就把这个插头放入插线板。不需要可以轻易的移除。
- 轻量
IOC控制反转
- IOC(Inversion Of Control):控制反转,是一个理论,概念,思想。
- 描述:把对象的创建,赋值,管理工作都交给代码之外的容器实现,也就是对象的创建是有其他外部资源完成的。
- 控制:创建对象,对象的属性赋值,对象之间的关系管理。
- 反转:把原来的开发人员管理,创建对象的权限转移给代码之外的容器实现。由容器代替开发人员管理对象。创建对象,给属性赋值。
- 正转:由开发人员在代码中,使用 new 构造方法创建对象,开发人员主动管理对象
- 容器:一个服务器软件,一个框架(Spring)
- 为什么要使用IOC:
- 目的就是减少对代码的改动,也能实现不同的功能。实现解耦合。
- Java中创建对象有哪些方式:
- 1、构造方法
- 2、反射
- 3、序列化
- 4、克隆
- 5、IOC:容器创建对象
- 6、动态代理
- IOC的体现:
- 1、创建类继承HttpServlet
- 2、在web.xml注册servlet
<servlet-name>MyServlet<servlet-name>
<servlet-class>com.li.controller.MyServlet<servlet-class>
- 3、没有创建Servlet对象,没有 MyServlet myServlet = new MyServlet();
- 4、Servlet是Tomcat服务器给你创建的,Tomcat也称为容器
Tomcat作为容器:里面存放的由Servlet对象,Listenner,Filter对象
- IOC的技术实现:
- DI是IOC的技术实现
- DI(Dependency Injection):依赖注入,只需要在程序中提供要使用的对象名称就可以,至于对象如何在容器中创建赋值,查找都由容器内部实现。
Spring是使用的DI实现了IOC的功能,Spring底层创建对象,使用的是反射机制。
Spring是一个容器,管理对象,给属性赋值,底层是反射创建对象。
- set注入的注意事项
- 1、属性必须有set方法,不然会报错
- 2、如果属性为name,set方法必须为setName(),不然会报错
- 引用类型属性自动注入
- byName方式自动注入
- byType方式自动注入
- 多个配置文件的优势
- 1、每个文件的大小比一个文件要小很多,效率高。
- 2、避免多人竞争带来的冲突
- 多文件的分配方式
- 1、按功能模块,一个模块一个配置文件
- 2、按类的功能,数据库相关的配置一个配置文件,做事务的功能一个配置文件,做service功能的一个配置文件等
- 基于注解的di,通过注解完成java对象创建,属性赋值。使用注解的步骤:
- 1、加入maven的依赖spring-context,在你加入spring-context的同时,间接加入spring-aop的依赖。使用注解必须使用spring-aop依赖
- 2、在类中加入spring的注解(多个不同功能的注解)
- 3、在spring 的配置文件中,加入一个组件扫描器的标签,说明注解在你的项目中的位置
- 学习的注解:
- @Component
- @Repository
- @Service
- @Controller
- @Value
- @Autowired
- @Resource
AOP面向切面编程
- 动态代理
- jdk动态代理
- jdk动态代理,使用jdk中的Proxy,Methpd,InvocationHandler创建代理对象。
- jdk动态代理要求目标类必须实现接口
- cglib动态代理
- 第三方的工具库,创建代理对象,原理是继承。通过继承目标类,创建子类。
- 子类就是代理对象。要求目标类不能是final的,方法也不能是final的。
- jdk动态代理
- 动态代理的作用:
- 1、在目标类源代码不改变的情况下,增加功能
- 2、减少代码的重复
- 3、专注业务逻辑代码
- 4、解耦合,让你的业务功能和日志,事务非业务功能分离。
- AOP:
- 面向切面编程,基于动态代理的,可以使用jdk,cglib两种代理方式。
- AOP就是动态代理的规范化,把动态代理的实现步骤,方式都定义好了。
- 让开发人员用一种统一的方式,使用动态代理。
- AOP(Aspect Orient Programming):面向切面编程
- Aspect:切面,给你的目标类增加的功能,就是切面。像上面用的日志,事务都是切面。
切面的特点:一般都是非业务方法,独立使用的。
- Orient:面向
- Programming:编程
- OOP:面向对象编程
- 怎么理解面向切面编程?
- 1、需要在分析项目功能时,找出切面。
- 2、合理的安排切面的执行时间 (在目标方法前,还是目标方法后)
- 3、合理的安排切面执行的位置,在哪个类,哪个方法增加增强功能
- 术语:
- 1、Aspect:切面,表示增强的功能,就是一堆代码,完成某个功能。非业务功能,
常见的切面功能有日志,事务,统计信息,参数检查,权限验证。
- 2、JoinPoint:连接点,连接业务方法和切面的位置。就是某类中的业务方法
- 3、PointCut:切入点,指多个连接点方法的集合。多个方法
- 4、目标对象:给哪个类的方法增加功能,这个类就是目标对象
- 5、Advice:通知,通知表示切面功能执行的时间。
- 一个切面的三个关键的要素:
- 1、切面的功能代码,切面干什么
- 2、切面的执行位置,使用PointCut表示切面执行的位置
- 3、切面的执行时间,使用Advice表示时间,在目标方法之前,还是目标方法之后
- 一个切面的三个关键的要素:
- 1、切面的功能代码,切面干什么
- 2、切面的执行位置,使用PointCut表示切面执行的位置
- 3、切面的执行时间,使用Advice表示时间,在目标方法之前,还是目标方法之后
- AOP的实现
- AOP是一个规范,是动态的一个规范化,一个标准
- AOP的技术实现框架:
- 1、spring:
- spring在内部实现了AOP规范,能做AOP的工作。
- spring主要在事务处理时使用AOP
- 我们项目开发中很少使用spring的AOP实现。因为spring的AOP比较笨重
- 2、aspectJ:
- 一个开源的专门做AOP的框架。
- spring框架集成了aspectJ框架,通过spring就能使用aspectJ的功能。
- aspectJ框架实现OAP有两种方式:
- 1、使用xml的配置文件:配置全局事务
- 2、使用注解,我们在项目要做AOP功能,一般都使用注解,aspectJ有五个注解。
- aspectJ框架的使用:
- 1、切面的执行时间,这个执行时间在规范中叫做Advice(通知,增强),在aspectJ框架中使用注解表示的。也可以使用xml配置文件中的标签
- 1、@Before
- 2、@AfterReturning
- 3、@Around
- 4、@AfterThrowing
- 5、@After
- 1、切面的执行时间,这个执行时间在规范中叫做Advice(通知,增强),在aspectJ框架中使用注解表示的。也可以使用xml配置文件中的标签
- 没有接口是cglib动态代理
- 目标类没有接口,使用cglib动态代理。spring框架会自动应用cglib
- com.li.bao07.MyServiceImpl$$EnhancerBySpringCGLIB$$83fec1d
Spring集成MyBatis
把mybatis框架和spring集成在一起,向一个框架一样使用。用的技术是IOC。
- 为什么是IOC:
- 能把mybatis和spring集成在一起,像一个框架,是因为IOC能创建对象。
- 可以把mybatis框架中的对象交给spring统一创建,开发人员从spring中获取对象。
- 开发人员就不用同时面对两个或多个框架了,就面对一个spring
- mybatis使用步骤
- 1、定义dao接口,StudentDao
- 2、定义mapper文件,StudentDao.xml
- 3、定义mybatis的主配置文件 mybatis.xml
- 4、创建dao的代理对象,StudentDao dao = SqlSession.getMapper(StudentDao.class);
- List<Student> students = dao.selectStudents();
- 要使用dao对象,需要使用getMapper()方法,需要那些条件呢
- 1、获取SqlSession对象,需要使用SqlSessionFactory的openSession()方法
- 2、创建SqlSessionFactory对象,通过读取mybatis的主配置文件,能创建SqlSessionFactory对象
- 需要SqlSessionFactory对象,使用Factory能获取SqlSession,有了SqlSession就能有dao,目的就是获取dao对象
- Factory创建需要读取主配置文件
- 我们会使用独立的连接池类替换mybatis默认自己带的,把连接池类也交给spring创建。
- myabtis的主配置文件:
- 1、数据库信息
- <environment id="develop">
- <transactionManager type="JDBC" />
- <dataSource type="POOLED">
- <property name="driver" value="com.mysql.jdbc.Driver" />
- <property name="url" value="jdbc:mysql://localhost:3306/springdb" />
- <property name="username" value="root" />
- <property name="password" value="1212">
- </dataSource>
- </environment>
- <environment id="develop">
- mapper文件的位置
- <mappers>
- <mapper resource="com/li/dao/StudentDao.xml" />
- </mappers>
- <mappers>
- 1、数据库信息
- 通过以上的说明,我们需要让spring创建以下对象
- 1、独立的连接池类的对象,使用来的druid连接池
- 2、SqlSessionFactory对象
- 3、创建出dao对象
- 需要学习就是上面三个对象的创建语法,使用xml的bean标签
Spring事务
- 事务处理的一些问题
- 什么是事务
- 讲mysql的时候,提出了事务。事务是值一组sql语句的集合,集合中有多条sql语句可能是insert,update,select,delete,我们希望这些多个sql语句都能成功,或者都失败,这些sql语句的执行时一致的,作为一个整体执行。
- 在什么时候想到使用事务
- 当我的操作,涉及多个表,或者是多个sql语句的insert,update,delete。需要保证这个语句都是成功才能完成我的功能,或者都失败,保证操作是符合要求的。
- 在java代码中写程序,控制事务,此时事务应该放在哪里呢?
- service类的业务方法上,因为业务方法会调用多个dao方法,执行多个sql语句
- 通常使用JDBC,mybatis,hibernate访问数据库怎么处理事务
- jdbc访问数据库,处理事务,Connection conn;conn.commit();conn.rollback();
- mybatis访问数据库,处理事务,SqlSession.commit();SqlSession.rollback();
- hibernate访问数据库,处理事务,Session.commit();Session.rollback();
- 问题中事务的处理方式,有什么不足
- 1、不同的数据库访问数据,处理事务的对象,方法不同。
- 什么是事务
需要了解不同数据库访问技术使用事务的原理
- 2、掌握多种数据库中事务的处理逻辑。什么时候提交事务,什么时候回滚事务。
- 3、处理事务的多种方式。
- 总结:就是多种数据库的访问技术,有不同的事务处理的机制,对象,方法。
- 怎么解决不足
- spring提供一种处理事务的统一模型,能使用统一步骤,方式完成多种不同数据库访问技术的事务处理。
- 使用spring 的事务处理机制,可以完成mybatis访问数据库的事务处理
- 使用spring的事务处理机制,可以完成hibernate访问数据库的事务处理
- 处理事务,需要怎么做,做什么
- spring处理事务的模型,使用的步骤都是固定的,把事务使用的信息提供给spring就可以了
- 1、事务内部提交,回滚事务,使用的事务管理器对象,代替你完成commit,rollback
- 事务管理器是一个接口和它的众多实现类
- 接口:PlatformTransactionManager,定义了事务重要方法commit,rollback
- 实现类:spring把每一种数据库访问技术对应的事务处理类都创建好了
- mybatis访问数据库--spring创建好的是DataSourceTransactionManager
- hibernate访问数据库--spring创建的是HibernateTransactionManager
- 怎么使用:你需要告诉spring 你用的是那种数据库的访问技术,怎么告诉spring呢?
- 声明数据库访问技术对应的事务管理器实现类,在spring的配置文件中使用<bean>声明就可以了
- 例如,你要使用mybatis访问数据库,你应该在xml配置文件中
- <bean id="XXX" class="…DataSourceTransactionManager" />
- 2、你的业务方法需要什么样的事务,说明需要事务的类型。
- 1)事务的隔离级别:有四个值
- DEFAULT:采用DB默认的事务隔离级别。MySql的默认为REPEATABLE_READ:Oracle默认为READ_COMMITTED
- READ_UNCOMMITTED:读未提交。未解决任何并发问题
- READ_COMMITED:读已提交。解决脏读,存在不可重复读与幻读。
- REPEATABLE_READ:可重复读,解决脏读,不可重复读,存在幻读
- SERIALIZABLE:串行化。不存在并发问题。
- 2)事务的超时时间:
- 表示一个方法最长的执行时间,如果方法执行时超过了时间,事务就回滚。
- 单位是秒,整数值,默认是-1
- 3)事务的传播行为:
- 控制业务方法是不是有事务的,是什么样的事务
- 7个传播行为,表示你的业务方法调用时,事务在方法之间是如何使用的。
- PROPAGATION_REQUIRED:你有事务我用你的,如果没有我用我的
- PROPAGATION_REQUIRED_NEW:不管你有没有,我都新建事务
- PROPAGATION_SUPPORTS:你有事务我就用,没有我就不用
- PROPAGATION_MANDATORY
- PROPAGATION_NESTED
- PROPAGATION_NEVER
- PROPAGATION_NOT_SUPPORTED
- 1)事务的隔离级别:有四个值
- 3、提交事务,回滚事务的时机
- 1、当你的业务方法,执行成功,没有异常抛出,当方法执行完毕,spring在方法执行后提交事务。事务管理器commit
- 2、当你的业务方法抛出运行时异常或ERROR,spring执行回滚,调用事务管理器的rollback
- 3、当你的业务方法抛出非运行时异常,主要是受查异常时,提交事务
- 受查异常:在你写代码中,必须处理的异常。例如IOException,SQLException
- 总结spring的事务
- 1、管理事务的是事务管理和它的实现类
- 2、spring的事务是一个统一模型
- 1、指定要使用的事务管理器实现类,使用<bean>
- 2、指定那些类,那些方法需要加入事务的功能
- 3、指定方法需要的隔离级别,传播行为,超时
- 你需要告诉spring,你的项目中类信息,方法的名称,方法的事务传播行为。
- spring框架中提供的事务处理方案,适合中小项目使用的,注解方案
- spring框架自己用aop实现给业务方法增加事务的功能,使用@Transactional注解增加事务。
- @Transactional注解是spring框架自己的注解,放在public方法的上面,表示当前方法具有事务。
- 可以给注解的属性赋值,表示具体的隔离级别,传播行为,异常信息等等。
- 使用@Transactional的步骤
- 1、需要声明事务管理器对象
- <bean id="xxx" class="DataSourceTransactionManager">
- 2、开启事务注解驱动,告诉spring框架,我要使用注解的方式管理事务。
- spring使用aop机制,创建@Transactional所在类代理对象,给方法加入事务的功能。
- spring给业务方法加入事务:
- 在你的业务方法执行之前,先开启事务,在业务方法之后提交或回滚事务,使用aop的环绕通知
- @Around("你要增加的事务功能的业务方法名称")
- Object myAround(){
- try{
- buy(1001,10);
- spring的事务管理.commit();
- }catch(Exception e){
- spring的事务管理.rollback();
- }
- try{
- }
- 3、在你的方法的上面加入@Transactional
- 1、需要声明事务管理器对象
- spring框架中提供的事务处理方案,适合大型项目。
- 有很多的类,方法,需要大量的配置事务,使用aspectj框架功能,在spring配置文件中声明类,
方法需要的事务。这种方式业务方法和事务配置完全分离。
- 实现步骤:都是在xml配置文件中实现的
- 1、要使用的是aspectj框架,需要加入依赖
- <dependency>
- <groupId>org.springframeword</groupId>
- <artifactId>spring-aspects</artifactId>
- <version>5.2.5RELEASE</version>
- </dependency>
- <dependency>
- 2、声明事务管理器对象
- <bean id="xxx" class="DataSourceTransactionManager">
- 3、声明方法需要的事务类型(配置方法的事务属性:隔离级别,传播行为,超时)
- 4、配置aop:指定那些类要创建代理。
- 1、要使用的是aspectj框架,需要加入依赖
Spring与Web
- 做的是javase项目中有main方法的,执行diamante是执行main方法的。
- 在main里面创建的容器对象
- web项目中是在tomcat服务器上运行的。tomcat已启动,项目一直运行的。
- web项目中容器对象只需要创建一次,把容器对象放入到全局作用域ServletContext中
- 使用监听器,当全局作用域对象被创建时,创建容器,存入ServletContext
- 监听器作用:
- 1、创建容器对象,执行 ApplicationContext ac = new ClassPathXmlApplication(config);
- 2、把容器对象放入到ServletContext,ServletContext.setAttribute(key,ac);
- 监听器可以自己创建,也可以使用框架中提供好的ContextLoadListener
- 使用监听器需要加入依赖
- <dependency>
- <groupId>org.springframework</groupId>
- <artifactId>spring-web</artifactId>
- <version>5.2.5.RELEASE</version>
- </dependency>
- <dependency>
- 部分源码
- private WebApplicationContext context;
- public interface WebApplicationContext extends ApplicationContext
- ApplicationContext:javase项目中使用的容器对象
- WebApplicationContext:web项目中的使用的容器对象
- 把创建的容器对象,放入到全局作用域
- key:WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE
- vlaue:this.context
- ServletContext.setAttribute(key,value);