Spring常⽤的⼀些注解说明
@Configuration
从Spring3.0,@Configuration⽤于定义配置类,可替换xml配置⽂件,被注解的类内部包含有⼀个或多个被@Bean注解的⽅法。
这些⽅法将会被AnnotationConfigApplicationContext或AnnotationConfigWebApplicationContext类进⾏扫描,并⽤于构建bean定义。
@Bean
@Bean注解⽤于告诉⽅法,产⽣⼀个Bean对象,然后这个Bean对象交给Spring管理。产⽣这个Bean对象的⽅法Spring只会调⽤⼀次,随后这个Spring将会将这个Bean对象放在⾃⼰的IOC容器中。
SpringIOC 容器管理⼀个或者多个bean,这些bean都需要在@Configuration注解下进⾏创建,在⼀个⽅法上使⽤@Bean注解就表明这个⽅法需要交给Spring进⾏管理。
@Autowired、@Resource
@Resource和@Autowired注解都是⽤来实现依赖注⼊的。只是@AutoWried按by type⾃动注⼊,⽽@Resource默认按byName⾃动注⼊。
♣ @Autowired
@Autowired具有强契约特征,其所标注的属性或参数必须是可装配的。如果没有Bean可以装配到@Autowired所标注的属性或参数中,⾃动装配就会失败,抛出NoSuchBeanDefinitionException.
@Autowired可以对类成员变量、⽅法及构造函数进⾏标注,让 spring 完成 bean ⾃动装配的⼯作。
@Autowired 默认是按照类去匹配,配合 @Qualifier 指定按照名称去装配 bean。
♣ @Resource
@Resource是JDK提供的注解,有两个重要属性,分别是name和type。
@Resource依赖注⼊时查bean的规则
既不指定name属性,也不指定type属性,则⾃动按byName⽅式进⾏查。如果没有到符合的bean,则回退为⼀个原始类型进⾏查,如果到就注⼊。
只是指定了@Resource注解的name,则按name后的名字去bean元素⾥查有与之相等的name属性的bean。
只指定@Resource注解的type属性,则从上下⽂中到类型匹配的唯⼀bean进⾏装配,不到或者到多个,都会抛出异常。
既指定了@Resource的name属性⼜指定了type,则从Spring上下⽂中到唯⼀匹配的bean进⾏装配,不到则抛出异常。
@Primary、@Qualifier
问题:当⼀个接⼝有2个不同实现时,使⽤@Autowired注解时会报org.springframework.beans.factory.NoUniqueBeanDefinitionException异常信息。
@Primary为默认优先选择,同时不可以同时设置多个,内部实质是设置BeanDefinition的primary属性。
@Qualifier注解,选择⼀个对象的名称,通常⽐较常⽤。
@PostConstruct、@PreDestroy
@PostConstruct是Java的注解,该注解被⽤来修饰⼀个⾮静态的void()⽅法。被@PostConstruct修饰的⽅法会在服务器加载Servlet的时候运⾏,并且只会被服务器执⾏⼀次。PostConstruct在构造函数之后执⾏,init()⽅法之前执⾏。
该注解的⽅法在整个Bean初始化中的执⾏顺序:Constructor(构造⽅法) -> @Autowired(依赖注⼊) -> @PostConstruct(注释的⽅法)。
被@PreDestroy修饰的⽅法会在服务器卸载Servlet的时候运⾏,并且只会被服务器调⽤⼀次,类似于Servlet的destroy()⽅法。被
@PreDestroy修饰的⽅法会在destroy()⽅法之后运⾏,在Servlet被彻底卸载之前。
注意:@PostConstruct和@PreDestroy 标注不属于 Spring,它是在J2EE库- common-annotations.jar。
@Service
@Service⽤于标注业务层组件。
@service("service") 指定Bean的id,相当于 <bean id="service">,如果不指定的话,默认是类的全限定名称。
@Scope
@Scope 就是⽤来指定bean的作⽤域。即⽤来声明IOC容器中的对象应该处的限定场景或者说该对象的存活空间,即IOC容器在对象进⼊相应的scope之前,⽣成并装配这些对象,在该对象不再处于这些scope的限定之后,容器通常会销毁这些对象。
默认是单例模式,@Scope("singleton")。
singleton:全局有且仅有⼀个实例
prototype:每次获取Bean的时候会有⼀个新的实例
request:表⽰该针对每⼀次HTTP请求都会产⽣⼀个新的bean,同时该bean仅在当前HTTP request内有效。
session:表⽰该针对每⼀次HTTP请求都会产⽣⼀个新的bean,同时该bean仅在当前HTTP session内有效。
application:将单个bean定义限定为ServletContext的⽣命周期。仅在⽀持web的Spring应⽤程序上下⽂中有效。
websocket:将单个bean定义限定为WebSocket的⽣命周期。仅在⽀持web的Spring应⽤程序上下⽂中有效。
@Repository
@Repository⽤于标注数据访问组件,即DAO组件。
@Component
@Component泛指组件,当组件不好归类的时候,我们可以使⽤这个注解进⾏标注。
@ComponentScan、@ComponentScans
@ComponentScan: 指定包路径扫描,把@Controller、@Service、@Repository,@Component标注的类,实例化到spring容器中。@Filter:是@ComponentScan注解类中的⼦注解(内部注解),可以指定⼀些过滤规则
FilterType.ANNOTATION:按照注解注⼊
FilterType.ASSIGNABLE_TYPE:按照给定的类型注⼊
FilterType.ASPECTJ:使⽤ASPECTJ表达式
FilterType.REGEX:使⽤正则指定
FilterType.CUSTOM:使⽤⾃定义规则
@ComponentScans:是@ComponentScan注解的集合,⾥⾯可以指定多个@ComponentScan注解,扫描多个包路径。
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
@Documented
@Repeatable(ComponentScans.class)
public @interface ComponentScan {
//字符串形式指定扫描的包路径
@AliasFor("basePackages")
String[] value() default {};
//字符串形式指定扫描的包路径
@AliasFor("value")
String[] basePackages() default {};
//这个英⽂翻译,⼤概就是指定类或者接⼝的类型,会按照指定的类所在的包,扫描包下的类
Class<?>[] basePackageClasses() default {};
//为bean⽣成名称的规则的类,需要实现BeanNameGenerator接⼝,后⾯指定了默认的⽣成规则
Class<? extends BeanNameGenerator> nameGenerator() default BeanNameGenerator.class;
//⽤于解析bean定义范围的策略接⼝。(单例,多例等
Class<? extends ScopeMetadataResolver> scopeResolver() default AnnotationScopeMetadataResolver.class;
//各种作⽤域代理选项
ScopedProxyMode scopedProxy() default ScopedProxyMode.DEFAULT;
//看解释,以及默认值(static final String DEFAULT_RESOURCE_PATTERN = "**/*.class";),是扫描的⽂件类型
String resourcePattern() default ClassPathScanningCandidateComponentProvider.DEFAULT_RESOURCE_PATTERN;
//是否启动⾃动扫描所有标注了 @Controller、@Service、@Repository,@Component的类
boolean useDefaultFilters() default true;
//扫描只包含Filter规则的类
//扫描只包含Filter规则的类
Filter[] includeFilters() default {};
//排除规则Filter的类
Filter[] excludeFilters() default {};
//懒加载
boolean lazyInit() default false;
@Retention(RetentionPolicy.RUNTIME)
@Target({})
@interface Filter {
//Filter的定义策略
FilterType type() default FilterType.ANNOTATION;
//跟type()配合使⽤
@AliasFor("classes")
Class<?>[] value() default {};
//跟type()配合使⽤
@AliasFor("value")
Class<?>[] classes() default {};
/**
跟type()配合使⽤,⼤概就是,如果指定的类型是ASPECTJ,那么就是ASPECTJ的表达式,是REGEX,就是REGEX的表达式,不常⽤ * The pattern (or patterns) to use for the filter, as an alternative
* to specifying a Class {@link #value}.
* <p>If {@link #type} is set to {@link FilterType#ASPECTJ ASPECTJ},
* this is an AspectJ type pattern expression. If {@link #type} is
* set to {@link FilterType#REGEX REGEX}, this is a regex pattern
* for the fully-qualified class names to match.
* @see #type
* @see #classes
*/
String[] pattern() default {};
}
}
如何使⽤?
//配置类==配置⽂件
@Configuration // 告诉Spring这是⼀个配置类
@ComponentScan(value = "com.bader", includeFilters = {
//只扫描有@Controller注解的类
@Filter(type = FilterType.ANNOTATION, classes = { Controller.class }),
/
/只扫描类型是BookService的类
@Filter(type = FilterType.ASSIGNABLE_TYPE, classes = { BookService.class }),
//⾃定义过滤规则
@Filter(type = FilterType.CUSTOM, classes = { MyTypeFilter.class }) },
json值的类型有哪些useDefaultFilters = false)
// @ComponentScan value:指定要扫描的包
// excludeFilters = Filter[] :指定扫描的时候按照什么规则排除那些组件
// includeFilters = Filter[] :指定扫描的时候只需要包含哪些组件
// FilterType.ANNOTATION:按照注解
// FilterType.ASSIGNABLE_TYPE:按照给定的类型;
// FilterType.ASPECTJ:使⽤ASPECTJ表达式
/
/ FilterType.REGEX:使⽤正则指定
// FilterType.CUSTOM:使⽤⾃定义规则
public class MyConfig {
}
⾃定义的Filter,最后的CUSTOM,也说了,需要实现ype.filter.TypeFilter接⼝。
public class MyTypeFilter implements TypeFilter {
/**
* metadataReader:读取到的当前正在扫描的类的信息
* metadataReaderFactory:可以获取到其他任何类信息的
*/
@Override
public boolean match(MetadataReader metadataReader, MetadataReaderFactory metadataReaderFactory) throws IOException {
// 获取当前类注解的信息
AnnotationMetadata annotationMetadata = AnnotationMetadata();
// 获取当前正在扫描的类的类信息
ClassMetadata classMetadata = ClassMetadata();
// 获取当前类资源(类的路径)
Resource resource = Resource();
String className = ClassName();
System.out.println("--->" + className);
//根据扫描的className,包含service的,扫描成功
if (ains("service")) {
return true;
}
return false;
}
}
@Controller、@RestController
⽤于标注控制层组件。
@RestController注解,相当于@Controller+@ResponseBody两个注解的结合,返回json数据不需要在⽅法前⾯加@ResponseBody注解了,但使⽤@RestController这个注解,就不能返回jsp,html页⾯,视图解析器⽆法解析jsp,html页⾯。
@ControllerAdvice、@RestControllerAdvice
@ControllerAdvice是⼀个增强的 Controller。使⽤这个 Controller ,可以实现三个⽅⾯的功能:
全局异常处理:结合@ExceptionHandler
全局数据绑定:结合@ModelAttribute
全局数据预处理:结合@InitBinder
@RequestBody、@ResponseBody
@ResponseBody注解将HttpRequest的请求体映射为Java的POJO对象。⼀般Get⽅法是没有body的,在post数据的时候可以指定json数据。
注意:对于想要转换的格式,记得要添加对应的依赖包。⽐如json的,添加Gson。或者jackson,必要时还要配置⼀下converter的bean。
@RequestBody主要⽤来接收前端传递给后端的json字符串中的数据的(请求体中的数据的);GET⽅式⽆请求体,所以使⽤@RequestBody 接收数据时,前端不能使⽤GET⽅式提交数据,⽽是⽤POST⽅式进⾏提交。在后端的同⼀个接收⽅法⾥,@RequestBody与
@RequestParam()可以同时使⽤,@RequestBody最多只能有⼀个,⽽@RequestParam()可以有多个。
@Value、@Validated
@Valid是javax.validation⾥的。
@Validated是@Valid 的⼀次封装,是Spring提供的校验机制使⽤。@Valid不提供分组功能。
@ExceptionHandler
@ExceptionHandler只有⼀个参数,可以是⼀个数组,表⽰要捕获的异常。@ExceptionHandler遵循就近原则,当异常发⽣时,Spring会选择最接近抛出异常的处理⽅法。⽐如上⾯ArithmeticException,这个异常有⽗类RuntimeException,RuntimeException还有⽗类Exception,但是我们通过debug,可以知道,它只会被pointException⽅法处理。
@RequestMapping
RequestMapping是⼀个⽤来处理请求地址映射的注解,可⽤于类或⽅法上。⽤于类上,表⽰类中的所有响应请求的⽅法都是以该地址作为⽗路径。
@RequestMapping 除了修饰⽅法, 还可来修饰类:
类定义处: 提供初步的请求映射信息。相对于 WEB 应⽤的根⽬录;
⽅法处: 提供进⼀步的细分映射信息。相对于类定义处的 URL。
若类定义处未标注 @RequestMapping,则⽅法处标记的 URL相对于 WEB 应⽤的根⽬录
返回ModelAndView时的url会根据你的 @RequestMapping实际情况组成。
对应项⽬jsp位置则是⼀级路径对应⼀级⽂件⽬录:如url为/default/index对应项⽬中webapp/default/index.jsp
如果类上没有映射,那么url直接就是⽅法的映射;否则url为类上+⽅法上映射路径组合。
@RequestMapping注解有六个属性,下⾯我们把它分成三类进⾏说明:
value:指定请求的实际地址,指定的地址可以是URI Template 模式;
method:指定请求的method类型, GET、POST、PUT、DELETE等,在RequestMethod定义;
consumes:指定处理请求的提交内容类型(Content-Type),例如application/json, text/html;
produces: 指定返回的内容类型,仅当request请求头中的(Accept)类型中包含该指定类型才返回;
params:指定request中必须包含某些参数值时,才让该⽅法处理;
headers:指定request中必须包含某些指定的header值,才能让该⽅法处理请求;
@RequestMapping ⼀共有五种映射⽅式:
(1) 标准URL 映射是最简单的⼀种映射
@RequestMapping("/hello") 或 @RequestMapping({"/hello","/world"})
(2) Ant风格的 URL 映射
Ant 通配符有三种:
?:匹配任何单字符
*:匹配任意数量的字符(含 0 个)
**:匹配任意数量的⽬录(含 0 个)
@RequestMapping("/?/hello/")
@RequestMapping("/*/hello")
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论