注解英文称 Annotaion,是Java从1.5开始支持加入源码的特殊语法元数据,做为程序的元数据嵌入到程序当中。注解实现有一个重要的接口Annotation接口,利用@interface关键字,将全部使用该关键字的注解类都实现Annotation接口。Annontation像一种修饰符同样,应用于包、类型、构造方法、方法、成员变量、参数及本地变量的声明语句中。前端
使用注解的好处:java
一、帮助代码编译检查web
二、提升代码的识别度,好比 @override @Deprecated spring
三、减小重复代码,简化代码apache
四、根据注解生成帮助文档,如 @Decument 等app
基本语法:ide
@Target({ElementType.METHOD, ElementType.TYPE}) @Retention(RetentionPolicy.RUNTIME) @Documented public @interface AnnotationName{ }
import java.lang.annotation.*; /** * 打印出操做日志 * @author * @create 2019/11/4 */ //定义该注解的做用范围 @Target({ElementType.TYPE, ElementType.METHOD}) //定义该注解的生命周期 @Retention(RetentionPolicy.RUNTIME) //注解将生成到javadoc中 @Documented public @interface SystemLog { /** * 日志内容 * @return */ String message() default ""; }
注意:规定注解里面只能使用java基本数据类型和String、enum、Annotation、classspa
1> 定义注解接口日志
import java.lang.annotation.*; /** * 打印出操做日志 * @author * @create 2019/11/4 */ //定义该注解的做用范围 @Target({ElementType.TYPE, ElementType.METHOD}) //定义该注解的生命周期 @Retention(RetentionPolicy.RUNTIME) //注解将生成到javadoc中 @Documented public @interface SystemLog { /** * 日志内容 * @return */ String message() default ""; }
2>实现接口,code
import com.example.shiro.config.SystemLog; import lombok.extern.slf4j.Slf4j; import org.aspectj.lang.JoinPoint; import org.aspectj.lang.annotation.*; import org.aspectj.lang.reflect.MethodSignature; import org.springframework.core.annotation.Order; import org.springframework.stereotype.Component; import java.lang.reflect.Method; /** * 日志拦截 * @author * @create 2019/11/4 */ @Slf4j //使用order属性,设置该类在spring容器中的加载顺序 @Order(10) //做用是把当前类标识为一个切面供容器读取 @Aspect //把普通类实例化到spring容器中 @Component public class OuterServiceAop { @Pointcut("@annotation(com.example.shiro.config.SystemLog)") public void serviceAop(){} @Before("serviceAop()") public void doBefore(JoinPoint joinPoint) { log.info("前置通知"); } @After("serviceAop()") public void doAfter(JoinPoint joinPoint) { log.info("后置通知"); } @AfterReturning(pointcut = "serviceAop()", returning = "res") public void doAfterReturning(JoinPoint joinPoint, Object res) { log.info("日志返回通知"); //请求方法 String method = joinPoint.getSignature().getDeclaringTypeName() + "." + joinPoint.getSignature().getName(); log.info("method:"+ method); //日志描述 MethodSignature signature = (MethodSignature) joinPoint.getSignature(); Method method1 = signature.getMethod(); SystemLog annotation = method1.getAnnotation(SystemLog.class); String message = annotation.message(); log.info(message); } @AfterThrowing(pointcut = "serviceAop()", throwing = "e") public void doAfterThrowing(JoinPoint joinPoint, Throwable e) { log.info("异常通知"); log.info("异常信息:" + e.getMessage()); } }
3>在须要的类或方法中增长注解
import com.example.shiro.config.SystemLog; import com.example.shiro.entity.User; import org.apache.shiro.SecurityUtils; import org.apache.shiro.authc.AuthenticationException; import org.apache.shiro.authc.UsernamePasswordToken; import org.apache.shiro.subject.Subject; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; import com.example.shiro.common.BaseController; /** * <p> * 前端控制器 * </p> * * @author * @since 2019-11-01 */ @RestController @RequestMapping("/user") public class UserController extends BaseController { @PostMapping("/login") @SystemLog(message = "用户登陆") public String login(User user) { ... } }
4>效果