Java-SSM-SpringBoot框架中的常用注解---学习中持续更新

注解知识回顾

第一:分类

(1)jdk自带的注解(5个):常用的就一个:@Override
(2)元注解(5个):常用的两个:@Target(指定注解使用的位置) @Retention(描述生命周期)
(3)自定义注解:(框架里大部分都是)

第二:元注解

 @Target 指定其他注解可以使用的位置(包上、类上、方法上、属性上)
    @Retention 指定其他注解的生命周期(源文件中、运行时、class文件中)
    @Documented 表示将该注解描述的注解内部的注释部分,也生成到相应的API中

第三:自定义注解

自定义注解需要配合元注解使用(常用@Target&@Retention )

第四:@Target注解(指定其他注解可以使用的位置)

(1)其他注解使用在单个位置(如何指定?)
    @Target(ElementType.Type)
(2)其他注解使用在多个位置(如何指定?)底层维护的是一个数组
    @Target({ElementType.Type,ElementType.Field}) 
 (3)@Target注解的取值{值被维护在ElementType中}
        ElementType.Type
        ElementType.Field
        ElementType.Method

第五:@Retention注解(指定其他注解的生命周期)

 @Retention注解的取值{值被维护在RetentionPolicy工具类中}
        RetentionPolicy.SOURCE
        RetentionPolicy.CLASS
        RetentionPolicy.RUNTIME

第六:自定义注解阐述

(1)定义:        
          @inteface 注解名{}
(2)配合元注解,指定自定义注解使用的位置,以及自定义注解的生命周期

第七:给注解添加功能---属性(也有人称为方法)

定义(1):

 @inteface Annotation{
        String name();  //没有设置默认值,使用该注解时,该属性必须添加值。
    //String name() default "lisi";//给name赋默认值lisi,设置了默认值后,使用该注解不需要手动设置name的属性值。
    }

使用(1):

 @Annotation(name="zhangsan")
        public void sayhello(){
    
    }

定义(2):

 @inteface Test{
        int value();
        //int value() default 10;//给value赋默认值10
    }

使用(2):

 @Test(value=100)
        public void sayhello(){    
     }
由于value的特殊性,在使用注解时,可以省略“value=”,例如@Test(100)
如果想直接使用@Test不写值100,可以在定义注解时,设置value的默认值为100
@inteface Test{
   int value() default 100;//给value赋默认值100
}

问题分析:

@inteface Test{
    String name() default "lisi";//给name赋默认值lisi
    int value() default 100;//给value赋默认值100
}

(1)可以直接使用这个注解,直接写@Test
(2)保留name的默认值,改value的值("value="可省略)

@Test(10)

(3)保留value的默认值,改name的值(“value=”可省略)

@Test(name="张三")

(4)同时改两个值时("value="不能省略)

@Test(name="张三",value=10)

第八:框架(framework)中常用的注解

(1)@SpringBootApplication

描述SpringBoot工程启动类的特定注解

(2)@SpringBootTest

描述SpringBoot工程测试类的特定注解
使用条件:如果需要在测试类中,引入spring容器机制,这是才是用该注解,否则没必要加。
引入spring容器机制:比如说,我们要在测试类中,通过spring容器来注入某个类的实例时,就需要使用该注解。

(3)@AutoWired

自动装配-由Spring框架为我们指定的属性类型注入值.我们常用接口类型的变量来接收spring框架注入的值(多态的思想,为了降低耦合,让程序更容易维护)
具体的注入(DI)过程:
 @AutoWired
                Student student;
                属性的类型 属性名

(1)第一:(Student为一个类)spring框架会基于属性的类型的首字母小写(student)作为key去bean池(单例)中(多例用的时候才创建)去寻找对应的value(这个value就是对象),在注入给这个属性名(注入的其实是一个地址而并非对象);
(2)第二:(Student为接口类型)若该实现类只有一个,则直接注入;
(3)第三:若该接口的实现类有多个,此时会根据属性名student,去查找对应的实现类创建的对象(这个对象存在map中的key为类名首字母小写),找到直接注入,找不到就直接抛异常:NoUniqueBeanDefinitionException
解决办法两种:(一般开发中都不推荐)

方法1:修改bean的名字(默认是类名首字母小写);@Component  (“指定的名字”),这个指定的名字必须与我们要注入的属性名一摸一样;
方法2:修改属性名(改成某个实现类的类名首字母小写);

常用方法就是指定用哪个实现类!使用( @Qualifier 注解)
@AutoWired(required=false)在项目启动的第一时间,可以不注入值(能注入则注入,不能注入则跳过)。
与@Resource注解装配过程区分,参见@Resource注解(位置:第47个注解)

(4)@Component

不明确这个类属于哪层时可以用该注解,将该类 的实 列交给spring容器创建

(5)@Controller

该注解用于描述控制层,将控制层的实例创建权限 交给spring容器
返回的是view

(6)@Service

该注解用于描述业务层,由spring来创建@Service 描述的类的实例

(7)@Lazy

该注解用于延迟对象的创建,在springboot项目中,对于 单例对象默认在项目启动时创建,这样会耗时耗资源-单例对象是要存 到bean池中的,通常配合[@Scope(singleton)]注解使用,对于 @Scope("prototype")描述的类的对象就是在需要时创建,按需加 载,故@Lazy注解对多利作用域对象不起作用

(8)@Scope

有两个取值@Scope("prototype")、 @Scope("singleton")

(9)@Test

(单元测试的注解)

满足以下条件
(1)访问修饰符不能为private
(2)返回值必须为void
(3)方法参数必须时无参
(4)测试方法允许抛出异常

扩展----测试的第二种方法(CommandLineRunner)
在启动类(@SpringBootApplicaton)中实现这个接口,重写 run()方法,在run()方法中写我们测试代码;当启动类启动时会自动执行run()方法

(10)@Bean

通常用于配置类中,与@Configuration配合使用
@Bean描述的方法的返回值(返回的是一个对象)交给spring去 管理。此时可以配合@Lazy注解使用

(11)@Mapper

添加在数据层的接口上,通知spring,该接口的实现类有mybatis负责实现,该实现类的对象有mybatis创建,但是交给spring管理

(12)@MapperScan("接口文件的包名")

添加在主启动类上,利用包扫描的方式,为指定包下的接口创建代理类以及代理对象并交给spring管理
优势:不用在每个映射的接口上使用@Mapper注解了
前提:要将所有的映射文件放在同一个包下。

(13)@Repository

添加在数据层接口的实现类上,将这个类交给Spring管理

(14)@Param

当mybatis版本相对较低时,在动态sql中想要使用方法中的参数变量来获取数据,就需要使用该注解对参数变量进行描述
也与jdk的版本有关(往下看~~~~)
原理:mybatis中规定,默认条件下可以进行单值传递 后端用任意的参数接收都可以。
有时候可能进行多值传递,需要将多值封装为map集合进行参数的传递(sql中通过key来取值)
旧版本时如果需要封装为单值,则必须添加@Param注解
新版本时可以自动添加@param,前提条件是多值传递
单值:数组 collection="array" (mapper层传的是数组,此时数组就是一个单值,此时xml中的collection="array")
单值:集合 collection="list" (mapper层传的是list集合,此时数组就是一个单值,此时xml中的collection="list")
多值:利用@param注解封装 collection="key"(mapper层传的是map,此时这个map就是一个单值,此时xml中的collection="key")

(15)@ReponseBody

1.描述的方法的返回值不是view(不是一个页面),
2.比如说可以是一个字符串String---直接返回该字符串
3.当方法的返回值是一个或多个pojo对象(也可以是map)时,springmvc去查看这个方法上是否有该注解,若有,就会pojo对象转成JSON格式的字符串(字符串数组)

(16)@RestController

@Controller+@ReponseBody
一般适用于ajax,不走视图解析器,并且返回json数据

(17)@PathVariable

当我们的方法参数要从url中获取参数时,就需要使用该注解--restful风格中常用!
如果url中的名字与方法参数名不一致,还可以指定
url="menu/menulist"

1.url中的名字与方法参数名一致,可以直接加上@PathVariable,不用指定别名
@RequestMapping("{do}/{dolist}")
public String domain(@PathVariable String dolist){
return dolist;
}

@RequestMapping("{do}/{dolist}")
public String domain(@PathVariable String do){
return do;
}

* * *

2.url中的名字与方法参数名不一致,还可以指定,表明方法参数中的变量时来自url中的哪一个
(一般不用这样的,直接写成一样就可以了(第一种))
@RequestMapping("{do}/{dolist}")
public String domain(@PathVariable("dolist")String name){
return name;
}
@RequestMapping("{do}/{dolist}")
public String domain(@PathVariable("do")String name){
return name;
}

(18)@RequestMapping

请求映射-提供映射路径-可以使用在类上、方法上

(19)@ControllerAdvice

该注解描述类为全局异常处理类
当Spring mvc(web)的控制层出现异常,首先会检查controller中是否有对应的异常处理方法,有则直接执行,若没有,就会检索是否有@ControllerAdvice描述的类,若有,则再去检索类中是否有对应的异常处理方法。。

(20)@ExceptionHandler

该注解描述的方法,为一个异常处理的方法,注解中需要指定能处理的异常类型(RuntimException.class-字节码对象),表示该方法能够处理该类型的异常以及子类异常。
在异常处理方法中,通常需要一个异常参数,用来接收异常对象。
方法的返回值通常是一个对象(json格式-满足响应式布局),通常与@ReponseBody注解结合使用

(21)@Aspect

该注解描述的类为一个切面(aop)

(22)@Around(环绕通知)优先级最高

执行目标方法之前Spring会检测是否有切面(@Aspect描述的类),然后检测是否有通知方法(@Around注解描述的方法),有该方法则执行该方法,在方法中调用通过ProceedingJoinPoint对象jp调用proceed()方法(该方法会执行目标方法)

(23)@Before

当@Around注解描述的方法中,要执行目标方法之前(proceed方法执行之前),执行该注解描述的方法

(24)@After

目标方法执行之后,执行此注解描述的方法(如果目标方法有异常该方法不执行)

(25)@AfterReturnning

@After注解描述的方法执行之后,(这个方法执行了,说明目标方法没有抛出异常)执行该注解描述的方法。

(26)@AfterThrowing

@Around注解描述的方法中的目标方法执行时抛出异常了,就直接执行该注解描述的方法。

(27)@Slf4j(lombok中)

应用在类上,此类中就可以使用log对象
就相当于在这个类中添加了一行如下代码

Logger log=LoggerFactory.getLogger(类名.class);

(28)@PointCut

该注解用来定义切入点方法

@Pointcut("bean(sysUserServiceImpl)")

 **public** **void** logPointCut() {}

切入点表示有四种:
bean execution within @annocation

(29)@Order(1)

该注解用于指定切面的优先级,数字越小,优先级越高,默认值是整数的最大值即默认值的优先级是最低的

(30)@Transactional

该注解可以描述类和方法,
当描述类时,表示类中的所有方法在执行之前开启事务,方法执行之后结束事务。
当描述方法时,表示该方法在执行之前开启事务,方法执行之后结束事务。
优先级问题:当类上和方法上都有该注解时,方法上的优先级高于类上的。
该注解中的属性也很重要:
timeout:设置超时时间
isolation:设置隔离级别
rollbackfor:当遇到什么异常以及子类异常时要执行回滚操作。
read-only:指定事务是否为只读事务,默认值为 false;为了忽略那些不需要事务的方法,比如读取数据,可以设置read-only为true。对添加,修改,删除业务read-only的值应该为false。
propagation:
Propagation.REQUIRED(如果没有事务创建新事务, 如果当前有事务参与当前事务, Spring 默认的事务传播行为是PROPAGATION_REQUIRED,它适合于绝大多数的情况。)
Propagation.REQUIRES_NEW
如果有当前事务, 挂起当前事务并且开启新事务

(31)@EnableAsync

注解应用到启动类上,表示开启异步,spring容器启动时会创建线程池
spring中线程池的配置:

spring:
    task:
        execution:
          pool:
            queue-capacity: 128
            core-size: 5
            max-size: 128
            keep-alive: 60000
            thread-name-prefix: db-service-task-

(32)@Async

在需要异步执行的业务方法上,使用@Async方法进行异步声明。

说明:AsyncResult对象可以对异步方法的执行结果进行封装,假如外界需要异步方法结果时,可以通过Future对象的get方法获取结果。
为了简便某些情况下,我们可以将方法的返回值写成void,这样就不要这么复杂的封装(前提时方法的返回值我们不使用)。

@Transactional(propagation = Propagation.REQUIRES_NEW) 
@Async
@Override
public Future saveObject(SysLog entity) {
System.out.println("SysLogServiceImpl.save:"+
Thread._currentThread_().getName());
int rows=sysLogDao.insertObject(entity);
//try{Thread._sleep_(5000);}catch(Exception e) {}
 return new AsyncResult(rows);

}

(33)@EnableCaching

在项目(SpringBoot项目)的启动类上添加@EnableCaching注解,以启动缓存配置。

在需要进行缓存的业务方法上通过@Cacheable注解对方法进行相关描述.表示方法的
返回值要存储到Cache中,假如在更新操作时需要将cache中的数据移除,可以在更新方法上使用@CacheEvict注解对方法进行描述。
@Cacheable(value = "menuCache")
@Transactional(readOnly = **true**)
**public** List> findObjects() {
....
}
value属性的值表示要使用的缓存对象,名字自己指定,其中底层为一个map对象,当向cache中添加数据时,key默认为方法实际参数的组合。

(34)@Value

说明:该注解单独使用(不配合@PropertySource注解)时,此时配置文件已经被加载到spring容器中,表示从spring容器(加载的配置文件)中取值。
该注解配合@PropertySource注解使用时,可以从指定的配置文件中取值,value属性指定配置文件的所在路径@PropertySource(value="classpath:/properties/image.properties",encoding="utf-8")
该注解用于描述属性的值,可以用来取出配置文件中的value值(根据key来取值)(properties、yml)、
properties配置文件的优先级高于yml配置文件的优先级
当这两个文件中都用同一个属性时,优先读取properties配置文件中的,然后读取yml配置文件中的,所有最后得到的是yml>中的(key相同值被覆盖)。
@value(“${server.port}”)
private String port;
说明:
因为配置文件中的value值都是字符串类型,所以这里需要用String类型接收。
该注解配合spel表达式取出配置文件中对应key的值。 

(35)@PropertySource(value="classpath:/properties/image.properties",encoding="utf-8")

当配置文件已经被加载到spring容器中了,就不要使用该注解指明加载的配置文件了,容器中有直接用@Value取值即可。
说明:该注解用于类上,作用:读取指定位置的配置文件信息,加载该文件到spring容器中
value属性用来指定配置文件的路径
classpath:/ 指定类目录下的路径(resource目录下)
encoding:用来指定配置文件的编码类型
@PropertySource(value="classpath:/properties/image.properties",encoding="utf-8")
public class ReadProperties{

}

(36)@Data(lombok)

该注解用在pojo类上,作用是生成对应的get/set/toString...方法
toString()方法只会重写自己的属性,不会添加父类的属性。

(37)@Setter(lombok)

该注解用在pojo类上,生成set方法

(38)@Getter(lombok)

该注解用在pojo类上,生成get方法

(39)@NoArgsConstructor(lombok)

该注解用在pojo类上,生成无参的构造方法

(40)@NoArgsConstructor(lombok)

该注解用在pojo类上,生成全参的构造方法

(41)@Accessors(chain=true)(lombok提供)

提供链式加载(对于set方法)
User user=new User();
user.setName("张三").setAge(26).setScore(98);

(42)@TableName(“表名”)(mybatisplus提供)

该注解用在pojo类上,用来指定该类的对象,与数据库中的哪张表映射
当pojo类名忽略大小写时,与数据库中要映射的表名一致时,可以不指定表名。如直接写@TableName注解即可。但不能省略这个注解。

(43)@TableId(type=IdType.Auto)(mybatisplus提供)

该注解用于pojo类中的属性上,用来指定表中的主键要映射到pojo类中的哪个属性。

(44)@TableField(value="字段名")(mybatisplus提供)

@TableField(fill = FieldFill.INSERT)指定哪个属性,在新增时有效,一般是创建时间
@TableField(fill = FieldFill.INSERT_UPDATE)指定哪个属性,在新增和修改时有效,一般是创建时间/修改时间
该注解用于pojo类中的属性上,用来指定表中的字段(除主键外的其他字段)映射到pojo类中的哪个属性。
当字段名与属性名一致时,或者,驼峰命名后字段名与属性名一致时,可以省略这个注解@TableField,即pojo中的属性上不写该注解。

(45)@GetMapping("/page/{moduleName}")

该注解用来处理查询请求,其他请求无效。
该注解相当于
@RequestMapping(value="/page/{moduleName}",method=RequestMethod.GET)
restful风格:可以根据请求的方式,来执行特定的业务功能。
TYPE=GET     处理查询业务
TYPE=POST    处理新增业务
TYPE=PUT     处理修改业务
TYPE=DELETE  处理删除业务
result风格总结:
1.可以获取url中的参数配合@PathVariable注解
2.根据请求方式,执行特定的业务功能

(46)@RestControllerAdvice

@RestControllerAdvide=@ResponseBody+@ControllerAdvide
说明:
该注解应用于类上,表示为通知方法。类中的方法的返回值都不是view,返回的是JSON格式的数据。
该注解描述的类为全局异常处理类,处理Controller层出现的异常。

(47)@Resource

@Resource的作用相当于@Autowired,只不过@Autowired按byType自动注入,而@Resource默认按 byName自动注入罢了。@Resource有两个属性是比较重要的,分是name和type,Spring将@Resource注解的name属性解析为bean的名字,而type属性则解析为bean的类型。所以如果使用name属性,则使用byName的自动注入策略,而使用type属性时则使用byType自动注入策略。如果既不指定name也不指定type属性,这时将通过反射机制使用byName自动注入策略。
@Resource装配顺序
  1. 如果同时指定了name和type,则从Spring上下文中找到唯一匹配的bean进行装配,找不到则抛出异常
  2. 如果指定了name,则从上下文中查找名称(id)匹配的bean进行装配,找不到则抛出异常
  3. 如果指定了type,则从上下文中找到类型匹配的唯一bean进行装配,找不到或者找到多个,都会抛出异常
  4. 如果既没有指定name,又没有指定type,则自动按照byName方式进行装配;如果没有匹配,则回退为一个原始类型进行匹配,如果匹配则自动装配;

(48)@ComponentScan(basePackages={"包的路径"})

扫描指定路径下的类,看是否有类上@Component、@Controller、@Service、@Mapper等,若有则指明该类的实例由Spring容器创建。

(49)@RequestBody

1、@requestBody注解常用来处理content-type不是默认的application/x-www-form-urlcoded编码的内容,比如说:application/json或者是application/xml等。一般情况下来说常用其来处理application/json类型。

2、通过@requestBody可以将请求体中的JSON字符串绑定到相应的bean上,当然,也可以将其分别绑定到对应的字符串上。

@RequestBody和@RequestParam区别

@RequestParam
注解@RequestParam接收的参数是来自HTTP请求体或请求url的QueryString中。
RequestParam可以接受简单类型的属性,也可以接受对象类型。
@RequestParam有三个配置参数:

required 表示是否必须,默认为 true,必须。
defaultValue 可设置请求参数的默认值。
value 为接收url的参数名(相当于key值)。 
@RequestParam
用来处理Content-Type为application/x-www-form-urlencoded编码的内容,Content-Type默认为该属性,也可以接收​​​​​​​application/json。@RequestParam也可用于其它类型的请求,例如:POST、DELETE等请求.所以在postman中,要选择body的类型为 x-www-form-urlencoded,这样在headers中就自动变为了 Content-Type : application/x-www-form-urlencoded 编码格式。

@RequestBody
注解@RequestBody接收的参数是来自requestBody中,即请求体。一般用于处理非 Content-Type: application/x-www-form-urlencoded编码格式的数据,比如:application/json、application/xml等类型的数据。就application/json类型的数据而言,使用注解@RequestBody可以将body里面所有的json数据传到后端,后端再进行解析。

GET请求中,因为没有HttpEntity,所以@RequestBody并不适用。
POST请求中,通过HttpEntity传递的参数,必须要在请求头中声明数据的类型Content-Type,SpringMVC通过使用
HandlerAdapter 配置的HttpMessageConverters来解析HttpEntity中的数据,然后绑定到相应的bean上。由于@RequestBody可用来处理 Content-Type 为 application/json 编码的内容,所以在postman中,选择body的类型为rowJSON(application/json),这样在 Headers 中也会自动变为 Content-Type : application/json 编码格式。

(50)@JsonFormat

在你需要查询出来的时间的数据库字段对应的实体类的属性上添加@JsonFormat
可以很好的解决:后台到前台时间格式保持一致的问题

(51)@DateTimeFormat

在你需要查询出来的时间的数据库字段对应的实体类的属性上添加@DataTimeFormat
可以很好的解决:前台到后台时间格式保持一致的问题
@DateTimeFormat(pattern ="yyyy-MM-dd")
@JsonFormat(pattern ="yyyy-MM-dd HH:mm:ss",timezone="GMT+8")
private Date symstarttime;

你可能感兴趣的:(springboot,java,spring)