日志切面的配置使用

使用配置文件

applicationContext.xml(spring.xml)配置文件

<?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:aop="http://www.springframework.org/schema/aop"
       xmlns:mvc="http://www.springframework.org/schema/mvc"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:mc="http://www.springframework.org/schema/mvc"
       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
		        http://www.springframework.org/schema/mvc
		        http://www.springframework.org/schema/mvc/spring-mvc.xsd
		        http://www.springframework.org/schema/aop
                http://www.springframework.org/schema/aop/spring-aop.xsd
                ">
    <import resource="spring-*.xml"></import>
    <!--日志的bean-->
    <bean id="log" class="com.teng.util.LogManager"></bean>
<!--配置切面和切入点信息-->
    <aop:config proxy-target-class="true">
        <!--
        配置切入点
        id:切入点名称
        expression:指定切入的表达式
        第一个*:代表方法的返回值类型 任意返回类型
        com.teng.service.impl  包名
        第二个*:任意类
        第三个*:任意方法名
        (..):..任意的参数类型
        execution(* com.teng.service.impl.*.*(..))
        -->
        <aop:pointcut id="pt" expression="execution(* com.teng.service.impl.*.*(..))"></aop:pointcut>
       <!--把切面和切入点关联起来 这个过程就是植入-->
        <aop:advisor advice-ref="log" pointcut-ref="pt"></aop:advisor>
    </aop:config>


    <bean id="myLog" class="com.teng.util.Log"></bean>
    <aop:config>
        <!--切入点-->
        <aop:pointcut id="pt1" expression="execution(* com.teng.dao.impl.*.*(..))"></aop:pointcut>
       <!--自定义切面-->
        <aop:aspect  ref="myLog">
            <!--通知 aop:before前置通知-->
            <aop:before method="before" pointcut-ref="pt1"></aop:before>
            <!--aop":after-returning 后置通知 方法成功返回后通知-->
            <aop:after-returning method="after" pointcut-ref="pt1"></aop:after-returning>
            <!--抛出异常后通知-->
            <aop:after-throwing method="throwing1" pointcut-ref="pt1"></aop:after-throwing>
           <!--环绕通知-->
            <aop:around method="around" pointcut-ref="pt1"></aop:around>
        </aop:aspect>

    </aop:config>

</beans>

spring-dao.xml

<?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:aop="http://www.springframework.org/schema/aop"
       xmlns:mvc="http://www.springframework.org/schema/mvc"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:mc="http://www.springframework.org/schema/mvc"
       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
		        http://www.springframework.org/schema/mvc
		        http://www.springframework.org/schema/mvc/spring-mvc.xsd
		        http://www.springframework.org/schema/aop
                http://www.springframework.org/schema/aop/spring-aop.xsd
                ">
    <import resource="spring-*.xml"></import>
    <!--日志的bean-->
    <bean id="log" class="com.teng.util.LogManager"></bean>
<!--配置切面和切入点信息-->
    <aop:config proxy-target-class="true">
        <!--
        配置切入点
        id:切入点名称
        expression:指定切入的表达式
        第一个*:代表方法的返回值类型 任意返回类型
        com.teng.service.impl  包名
        第二个*:任意类
        第三个*:任意方法名
        (..):..任意的参数类型
        execution(* com.teng.service.impl.*.*(..))
        -->
        <aop:pointcut id="pt" expression="execution(* com.teng.service.impl.*.*(..))"></aop:pointcut>
       <!--把切面和切入点关联起来 这个过程就是植入-->
        <aop:advisor advice-ref="log" pointcut-ref="pt"></aop:advisor>
    </aop:config>


    <bean id="myLog" class="com.teng.util.Log"></bean>
    <aop:config>
        <!--切入点-->
        <aop:pointcut id="pt1" expression="execution(* com.teng.dao.impl.*.*(..))"></aop:pointcut>
       <!--自定义切面-->
        <aop:aspect  ref="myLog">
            <!--通知 aop:before前置通知-->
            <aop:before method="before" pointcut-ref="pt1"></aop:before>
            <!--aop":after-returning 后置通知 方法成功返回后通知-->
            <aop:after-returning method="after" pointcut-ref="pt1"></aop:after-returning>
            <!--抛出异常后通知-->
            <aop:after-throwing method="throwing1" pointcut-ref="pt1"></aop:after-throwing>
           <!--环绕通知-->
            <aop:around method="around" pointcut-ref="pt1"></aop:around>
        </aop:aspect>

    </aop:config>

</beans>

spring-service.xml

<?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:mvc="http://www.springframework.org/schema/mvc"
       xmlns:context="http://www.springframework.org/schema/context"
       xmlns:mc="http://www.springframework.org/schema/mvc"
       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
		        http://www.springframework.org/schema/mvc
		        http://www.springframework.org/schema/mvc/spring-mvc.xsd"
        default-autowire="byType">

      <bean id="userService" class="com.teng.service.impl.UserServiceImpl" autowire="default">

        <!--
        autowire 属性值自动装配
        默认值 no  不装配
        byName 通过属性名装配  前提必须有有参构造
        byType 通过类型装配
        default 跟随着上级的特性
        -->
      <!--  <property name="userDao" ref="UserDao"></property>-->
        <property name="list">
            <list>
                <value>上海</value>
                <value>广州</value>
                <value>深圳</value>
            </list>

        </property>
    </bean>

    <bean id="user" class="com.teng.domain.User">
        <!--
        通过属性赋值
        基本数据类型,String:通过value赋值
        对象数据类型list:通过ref赋值
        集合类型:list:通过list赋值
        集合类型:set:通过set赋值
        -->
        <!--<property name="id" value="22"></property>-->
       <!-- <constructor-arg index="0" value="1"></constructor-arg>
        <constructor-arg index="1" value="你好"></constructor-arg>
        <constructor-arg index="2" value="hello"></constructor-arg>-->
        <constructor-arg type="int" value="22"></constructor-arg>
        <constructor-arg type="java.lang.String" value="牛"></constructor-arg>
        <constructor-arg type="java.lang.String" value="批"></constructor-arg>

    </bean>

</beans>

项目结构

UserDao接口和UserService接口

package com.teng.dao;
import com.teng.domain.User;
import java.util.List;
public interface UserDao {
    public void find();
    public void find(int id);
    public void find(User user);
    public void find(List list);
}
package com.teng.service;
import com.teng.domain.User;
import java.util.List;
public interface UserService {
    public void find();
    public void find(int id);
    public void find(User user);
    public void find(List list);
}

UserDaoImpl实现类和UserServiceImpl实现类

package com.teng.dao.impl;
import com.teng.dao.UserDao;
import com.teng.domain.User;
import java.util.List;
public class UserDaoImpl implements UserDao {
    @Override
    public void find() {
            System.out.println("====ig 牛逼======");
    }
    @Override
    public void find(int id) {
        System.out.println("====ig 牛逼======");
    }
    @Override
    public void find(User user) {
        System.out.println("====ig 牛逼======");
    }
    @Override
    public void find(List list) {
        System.out.println("====ig 牛逼======");
    }
}
package com.teng.service.impl;
import com.teng.dao.impl.UserDaoImpl;
import com.teng.domain.User;
import com.teng.service.UserService;
import java.util.List;
public class UserServiceImpl implements UserService {
    private UserDaoImpl userDao;
    private List list;
    @Override
    public void find() {
        userDao.find();
    }
    @Override
    public void find(int id) {
        userDao.find(id);
    }
    @Override
    public void find(User user) {
        userDao.find(user);
    }
    @Override
    public void find(List list) {
        userDao.find(list);
    }
    public void setUserDao(UserDaoImpl userDao) {
        this.userDao = userDao;
    }
    public List getList() {
        return list;
    }
    public void setList(List list) {
        this.list = list;
    }
}

实现的方法实行前代码和方法执行后代码

LogManager

package com.teng.util;

import org.springframework.aop.AfterReturningAdvice;
import org.springframework.aop.MethodBeforeAdvice;

import java.lang.reflect.Method;

public class LogManager implements MethodBeforeAdvice, AfterReturningAdvice {
    @Override
    public void before(Method method, Object[] objects, Object o) throws Throwable {
        System.out.println("方法执行前日志--------ig 牛逼");
    }

    @Override
    public void afterReturning(Object o, Method method, Object[] objects, Object o1) throws Throwable {
        System.out.println("方法执行后日志--------ig 牛逼");
    }
}

自定义日志切面类

package com.teng.util;

import org.aspectj.lang.ProceedingJoinPoint;

/*
* 自定义日志切面 不需要实现接口
* */
public class Log {
    public void before(){
        System.out.println("----before----");
    }
    public void after(){
        System.out.println("----after----");
    }
    public void around(ProceedingJoinPoint joinPoint){
        System.out.println("----around 前置-----");
        try {
            joinPoint.proceed();
        } catch (Throwable throwable) {
            throwable.printStackTrace();
        }
        System.out.println("----around 后置-----");
    }
    public void throwing1(){
        System.out.println("========throw=======");
    }
}

测试类

package com.teng;

import com.teng.domain.User;
import com.teng.service.UserService;
import com.teng.service.impl.UserServiceImpl;
import org.junit.Test;
import org.springframework.beans.factory.BeanFactory;
import org.springframework.context.support.ClassPathXmlApplicationContext;

import javax.activation.FileDataSource;
import java.util.List;
/*
* spring创建对象:代理模式
* 使用者  代理商                           厂家
* user    User uer = new User()         User
*           静态代理  提前生产对象
*           动态代理   使用的时候生产对象
* */
public class TestUser {
    @Test
    public void test1(){
        BeanFactory beanFactory = new ClassPathXmlApplicationContext("/spring.xml");
        UserService userService = (UserService) beanFactory.getBean("userService");
        userService.find();
    }
    @Test
    public void test2(){
        BeanFactory beanFactory = new ClassPathXmlApplicationContext("/spring.xml");
       //jdk代理
        UserService userService = (UserService) beanFactory.getBean("userService");
        //cglib  代理  配置文件中
        UserServiceImpl userServiceImpl = beanFactory.getBean(UserServiceImpl.class);
        userService.find();
        /*userService.find(11);
        User user = (User) beanFactory.getBean("user");
        userService.find(user);
        List list = userServiceImpl.getList();
        userService.find(list);*/
    }
}

执行结果

使用注解

在applicationContext.xml中加上

<!--开启注解扫描功能-->
<context:annotation-config></context:annotation-config>
<!--定义注解扫描的包-->
<context:component-scan base-package="com.teng"></context:component-scan>
<!--开启aop自动代理模式-->
    <aop:aspectj-autoproxy proxy-target-class="true" />

在User类上加上@Component(value=“user”)//注入beanfactory中

UserDaoImpl和UserServiceImpl代码

package com.teng.dao.impl;

import com.teng.dao.UserDao;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.ResultSetExtractor;
import org.springframework.stereotype.Repository;
import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
import javax.annotation.Resource;
import java.security.interfaces.RSAKey;
import java.sql.ResultSet;
import java.util.HashMap;
import java.util.List;

@Repository(value = "userDao")
public class UserDaoImpl implements UserDao {
    @PostConstruct//定义初始化是执行的方法
   public void init(){
       System.out.println("11111111111111");
   }
    @Override
    public void find() {
        System.out.println("=====ig  牛逼=======");
    }
    @PreDestroy//定义被销毁之前执行的方法
    public void destroy(){
        System.out.println("222222222222");
    }
}
package com.teng.service.impl;

import com.teng.dao.UserDao;
import com.teng.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
@Service(value = "userService")
public class UserServiceImpl implements UserService {
    /*
    @Resource  默认情况下通过属性名称查找 id= userDao 的bean
    如果通过名称找到,直接返回对应的bean
    如果通过名称没有找到,然后通过类型查找 UserDao UserDaoImplb
     @Resource(name = "userDao") 只通过name查找
    */
    /*@Resource(name = "userDao")
    private UserDao userDao;*/
    /*
    *  @Autowired 自动装配 先找class,如果一个接口只有一个实现类,直接找到对应实现类
    *  如果一个接口有多个实现类,再通过名称查找
    *
    *  @Autowired
    @Qualifier(value = "userDao")
    只能通过名称查找  byName
    * */
    @Autowired
    @Qualifier(value = "userDao")
    private UserDao userDao;
    @Override
    public void find() {
        userDao.find();
    }
    public void setUserDao(UserDao userDao) {
        this.userDao = userDao;
    }
}

自定义切面类的注解

package com.teng.util;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.stereotype.Component;

/**
 * Created by Administrator on 2018/11/22 0022.
 * 自定义日志切面 不需要实现接口
 */
@Aspect//标志是切面
@Component(value = "log")//注入beanfactory中
public class Log {
	// 定义在哪个层导入切面
    @Pointcut("execution(* com.teng.service.impl.*.*(..))")
     public void log(){
        System.out.println("++++++");
    }

    @Before(value = "log()")//方法执行前
    public void before(){
        System.out.println("-----before-----");
    }

    @AfterReturning(value = "log()")//方法执行后返回结果后执行
    public void after(){
        System.out.println("-----after-----");
    }
     @Around(value = "log()")//环绕
    public void around(ProceedingJoinPoint joinPoint){
        System.out.println("-------around 前置---------");
        try {
            joinPoint.proceed();
        } catch (Throwable throwable) {
            throwable.printStackTrace();
        }
        System.out.println("-------around 后置---------");
    }
}

测试结果是,在执行find方法时,执行这些方法。111111111是初始化userService时执行的。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

扫码关注云+社区

领取腾讯云代金券