Spring框架(IOC、AOP、DI)

1.几个常用注释:
1)@Controller:用来声明控制器类
2)@RequestMapping("/def"):用来声明controller方法的映射路径
3)@POSTMapping("/postdef"):用来声明controller方法的映射路径,只接收POST请求。效果同@RequestMapping(value="postdef",method = RequestMethod.POST,
4)@GERMapping(“getdef”):用来声明controller方法的映射路径,只接收GET请求@RequestMapping(value="postdef",method = RequestMethod.GET,
5)@ResponseBody:用来将controller方法返回的对象写入到响应(response)对象的body数据区。如果controller类内的方法返回中文,可以在@RequestMapping中添加produces设置防止中文乱码。
6) @Autowired //根据类型从容器中注入对象
7) @Resource //默认根据变量名称(对象名)注入,当找不到与名称匹配的bean时才会按类型注入

    value 指定匹配的映射路径
    method 指定允许访问的HTTP请求方式
    produces 指定 返回 内容格式和返回值编码,需要配合@ResponseBody一起使用
    consumes 指定 请求 的提交内容格式(Content-Type)
        				text/html : HTML格式
      				    text/plain :纯文本格式
        				text/xml : XML格式
        				application/json: JSON数据格式
        				application/x-www-form-urlencoded: <form>表单提交数据格式
       				    multipart/form-data : 需要在表单中进行文件上传时,就需要使用该格式
   
    @RequestMapping(value="t",
           		    method = RequestMethod.POST,
            		produces = "text/html; charset=utf-8",
            		consumes = "application/x-www-form-urlencoded")

3-1 元素的常用属性
1)name:name可以为Bean指定多个名称,每个名称之间用逗号或者分号隔开。
2)scope:用于设定Bean示例的作用域,其默认值是singleton
3)property:的子元素,原理是 调用Bean实例中的setter方法完成依赖注入。该元素的name属性用于指定Bean实例中相应的属性名。
4)lazy-init:懒加载。该属性只有当scope = singleton才有效(等同单例模式)。
当值为true时(等同于懒汉式),在容器首次请求对象时才会创建Bean实例
当值为false时(等同于饿汉式),在容器启动时就创建Bean实例。

 <!-- 声明一个bean,这个bean对应的类会被tomcat容器创建对象-->
    <bean id="hw" name="mr3" class="com.st.model.User" scope="singleton" lazy-init="false">
        <!-- 指定属性值 -->
        <property name="name" value="jack" />
    </bean>

3-2 bean的作用域:scope属性
spring容器在初始化一个Bean实例时,同时会指定该实例的作用域。
1)singleton:单例模式(默认值)。表示在Spring容器中只有一个Bean实例,Bean以单例的方式存在。
2)prototype:原型模式,表示每次通过Spring容器获取Bean时,容器都会创建一个Bean原理。
3)application:类似于singleton。
区别:
singleton表示每个IOC容器中仅有一个Bean实例。而一个Web应用中可能会有多个LOC容器(所以singleton表示一个Web应用中可能有多个Bean实例),一个Web应用中只会有一个ServletContext。
application表示同一个web会共享一个Bean实例,该作用域在ServletContext内有效。
可以说application才是Web中真正的单例模式。
4)request:每次HTTP请求,容器都会创建一个Bean实例,该作用域只在当前HTTP的request内有效。
5)session:同一个HTTP session共享一个Bean实例,不同的session使用不同的Bean实例,该作用域仅在HTTP session内有效。

2-1 IOC控制反转(Spring框架)
1)IOC 控制反转,指的是将对象的创建权交给 Spring容器去创建
2)由 IoC 容器管理的对象称为 Spring Bean,Spring Bean 就是 Java 对象;
3)Spring 通过读取 XML 或 Java 注解中的信息来获取哪些对象需要实例化
4)IOC容器会自动扫描包路径下的所有被@Controller、@Service、 @Repository、@Component四个注解声明的类,并为其创建对象。
@Controller一般声明controller层的类
@Service一般声明Service层的类
@Repository一般声明dao层的类
@Component其他没有特殊要求的层用该注解修饰

	 <!-- IOC 自动扫描service层,所有被@Service声明的类将会被扫描到-->
    <context:component-scan base-package="com.st.service" />
    <!-- IOC 自动扫描dao层,所有被@Repository声明的类将会被扫描到-->
    <context:component-scan base-package="com.st.dao" />
    <!-- IOC 自动扫描其他业务层,所有被@Component注解声明的类将会被扫描到-->
    <context:component-scan base-package="com.st.model" />

2-2 DI依赖注入
1) DI(Dependency Injection) 依赖注入,从容器中获取指定类的对象
@Autowired //根据类型从容器中注入对象
@Resource //默认根据变量名称(对象名)注入,当找不到与名称匹配的bean时才会按类型注入

    @Autowired
    @Resource
    private DefService defService;

4.AOP面向切面编程(Spring框架)
1)定义:
AOP 的全称是“Aspect Oriented Programming”,译为“面向切面编程”,和 OOP(面向对象编程)类似,它也是一种编程思想。
AOP 是通过横向的抽取机制实现的。它将应用中的一些非业务的通用功能抽取出来单独维护,并通过声明的方式(例如配置文件、注解等)定义这些功能要以何种方式作用在哪个应用中,
而不是在业务模块的代码中直接调用。
应用场景:日志记录,事务管理,权限验证,效率检查
AOP是OOP(面向对象编程)的一种增强,不能说AOP替代OOP。
AOP的核心思想:复用(把重复代码封装成方法,放在某个类中,通过类名.方法名调用)。
Spring两大特点:IOC和AOP

名词解释:
切面:将非业务的通用功能抽取出来单独维护的类,用于把这些抽取出来的代码插入到指定位置
切入点:切面中的代码要插入的位置,定义为某些类的某些方法
通知:切面类的某个方法,要被插入到哪个位置(切入点)
织入:通知被插入到切入点的动作

程序依然正常进行,只是在指定切入方法点处,按照通知方式(在切入点之前或之后),多执行了一个切入方法。
流程:在pom.xml中配置spring-aop包、在spring.xml中引入aop包
创建切入类,写切入方法。
在spring.xml中声明,让容器创建切入类对象
在spring.xml中配置AOP。包括切面类、切入点、通知类型。
当程序运行到切入方法处时,会根据通知类型,执行切入方法。
2)使用条件:使用aop需要引入spring-aop包

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:aop="http://www.springframework.org/schema/aop"
       xsi:schemaLocation="http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
        http://www.springframework.org/schema/context
        http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/aop
        http://www.springframework.org/schema/aop/spring-aop.xsd ">

3)spring.xml配置文件

	<!-- 声明一个bean,这个bean对应的类会被tomcat容器创建对象-->
    <bean name="aopUtil" class="com.st.util.AopUtil" ></bean>
     <aop:config>
     	 <!--1.定义切面类:切面类名为myAspect,关联类aopUtil-->
        <aop:aspect id="myAspect" ref="aopUtil">
        	<!--2.定义切面点-->
            <aop:pointcut id="myPointCut" expression="execution(* com.st.service.*.get*(..))"/>
            <!--3.定义通知方式-->
            <aop:around pointcut-ref="myPointCut" method="speak"/>
        </aop:aspect>
    </aop:config>

 <!--例如:
com.st.service的所有get*方法都成为切点。切入方法是com.st.util.AopUtil的speak方法
Controller类的方法A执行 System.out.println(defService.getTest());语句:
程序运行:进入Controller类的A方法 ----> 执行到System.out.println(defService.getTest());时,由于该语句调用了切入方法 -----> 所以程序现在进入切入点方法,即com.st.util.AopUtil的speak,而defService.getTest()还会不会执行要看speak方法内有没有显式调用。如下 环绕通知:around 中的例子
-->  

execution(* com.st.service.*.get*(..)) 解释:
第一个 * 表示返回值类型,
第二个 * 表示com.st.service包下的任意类,
第三个*表示该类任意以get开头的方法。
(…) 表示任意个数的参数列表
( * )表示只有一个参数,参数类型为任意
( * ,String)表示有两个参数,第一个参数可以为任意值,第二个为String类型的值。

声明通知类型:
前置通知:before
1 作用:在目标方法执行之前执行的通知
2 用法:
前置通知方法,可以没有参数;
也可以额外接收一个JoinPoint类型参数,通过该对象可以获取目标对象 和 目标方法相关的信息;
如果接收JoinPoint,必须保证其为方法的第一个参数,否则报错
3 应用场景:日志

后置通知:after-returning
1 作用:在目标方法执行成功(即不报异常)之后执行的通知。
2 用法:
后置通知方法,可以没有参数;
也可以接收一个JoinPoint类型的参数,通过该对象可以获取目标对象 和 目标方法相关的信息;
如果接收JoinPoint,必须保证其为方法的第一个参数,否则报错
3 应用场景:日志

   public void speakAfterReturn(JoinPoint jp){
        //获取对象Class类
        Class clz = jp.getTarget().getClass();
        System.out.println(clz.getName());
        //获取切入点对象信息
        Signature signature = jp.getSignature();
        //获取切入点名称
        String name = signature.getName();
        System.out.println(name);
        System.out.println("aop-----after-returning");
    }

环绕通知:around
1 作用:在目标方法执行之前和之后都可以执行额外代码的通知
2 用法:
环绕通知需要有返回值,否则真正调用者将拿不到返回值,只能得到一个null;
在环绕通知中必须显式的调用目标方法,切入点方法才会执行,这个显式调用是通过
ProceedingJoinPoint来实现的;
环绕通知有控制目标(切入点)方法是否执行、有控制是否返回值、有改变返回值的能力
3 应用场景:控制事务 权限控制

public String speakAround(ProceedingJoinPoint joinPoint) {
        System.out.println("aop-----around-----before");
        //开启事务
        try {
            //通过ProceedingJoinPoint显示调用processd,才会执行切入点方法
           //ProceedingJoinPoint调用几次,切入点方法就会执行几次
            Object obj = joinPoint.proceed();//调用切入点方法
            System.out.println(obj);//切入点方法返回值
            //提交事务
        } catch (Throwable e) {
            e.printStackTrace();
            //回滚事务
        }
        System.out.println("aop-----around-----after");
        return "@@@@@aop@@@@@";//切入方法的返回值(也可以改成return obj返回切入点方法返回值)
    }

异常通知:after-throwing
1 作用:在目标方法抛出异常时执行的通知
2 用法:
可以配置传入JoinPoint获取目标对象和目标方法相关信息,但必须处在参数列表第一位
还可以配置参数,让异常通知可以接收到目标方法抛出的异常对象。
3 应用场景:异常处理、控制事务

最终通知:after(先走切入点方法,再走切面方法,最后切入点方法return)
1 作用:在目标方法执行之后(无论执行成功还是异常)执行的通知
2 应用场景:日志

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值