聊聊注解@controller@service@component@repository的区别

网友投稿 548 2022-10-04


聊聊注解@controller@service@component@repository的区别

目录注解@controller@service@component@repository的区别命名不一样主要是为了区分类的作用和所属层级:Spring中的主要注解1. 组件类注解@Component、@Repository、@Service、@Controller【创建注解】1.@Component 标注为一个普通的spring Bean类2.@Repository 标注为一个DAO层的组件类3.@Service 标注为Service层(业务逻辑层)的组件类4.@Controller 标注一个控制器组件类2. 装配bean时常用注解 @Autowired、@Resource【获取注解】2.1 @Autowired【***常用】2.2 @Resource(不属于spring的注解,是javax.annotation注解)2.3 @Qualifier(不能单独使用)2.4 @Autowired和@Qualifier的混合使用

注解@controller@service@component@repository的区别

查了一些网上的其他博客,发现几个注解本质上没有什么区别,至少在spring2.5版本里,这几个注解本质是一样的(当然,新的版本有什么变化目前还没细查)

命名不一样主要是为了区分类的作用和所属层级:

@Repository:持久层,用于标注数据访问组件,即DAO组件。

@Servhttp://ice:业务层,用于标注业务逻辑层主键。

@Controller:控制层,用于标注控制层组件。

@Component:当你不确定是属于哪一层的时候使用。

之所以区分开几种类型,一是spring想在以后的版本中为它们添加特殊技能,二是这种分层的做法使web架构更清晰,易读性与维护性更好。

/**

* Indicates that an annotated class is a "Service", originally defined by Domain-Driven

* Design (Evans, 2003) as "an operation offered as an interface that stands alone in the

* model, with no encapsulated state."

*

*

May also indicate that a class is a "Business Service Facade" (in the Core J2EE

* patterns sense), or something similar. This annotation is a general-purpose stereotype

* and individual teams may narrow their semantics and use as appropriate.

*

*

This annotation serves as a specialization of {@link Component @Component},

* allowing for implementation classes to be autodetected through classpath scanning.

*

* @author Juergen Hoeller

* @since 2.5

* @see Component

* @see Repository

*/

@Target({ElementType.TYPE})

@Retention(RetentionPolicy.RUNTIME)

@Documented

@Component

public @interface Service {

/**

* The value may indicate a suggestion for a logical component name,

* to be turned into a Spring bean in case of an autodetected component.

* @return the suggested component name, if any

*/

String value() default "";

}

从@service的源码看,service仍然是使用了@Component注解(@Controller与@Repository与service一样,这里就不贴源码了)。

component即组件,相当于xml配置文件中的bean申明,通过spring的自动扫描机制,在规定的类路径中寻找标注了@Component,@Service,@Repository,@Controller注解的类,并把这些类纳入进容器中进行管理。

getBean的默认名称是类名(头字母小写),并且是单例的,如果想自定义,可以使用@Service(“beanName”)@Scope(“prototype”)来改变。

/**自动扫描base-package目录下的所有文件,包括子目录**/

Spring中的主要注解

Spring的一个核心功能是IOC,就是将Bean初始化加载到容器中, Bean加载到容器中可以使用 Spring注解方式或者 Spring XML配置方式。(通过注解将java中的一些类,加载到容器中)

1. 组件类注解@Component、@Repository、@Service、@Controller【创建注解】

@Repository、@Service、@Controller的功能和@Component相同,但为了使标注类的用途更加清晰(层次化),在实际开发中推荐使用:

@Repository标注数据访问层(DAO层)、使用@Service标注业务逻辑层(Service层)以及使用@Controller标注控制器层(控制层)。

1.@Component 标注为一个普通的spring Bean类

该注解是一个泛化的概念,仅仅表示一个组件对象(Bean),可以作用在任何层次上。

2.@Repository 标注为一个DAO层的组件类

该注解用于将数据访问层(DAO)的类标识为Bean,即注解数据访问层Bean,其功能与@Component()相同。

3.@Service 标注为Service层(业务逻辑层)的组件类

该注解用于标注一个业务逻辑组件类(Service层),其功能与@Component()相同。

4.@Controller 标注一个控制器组件类

该注解用于标注一个控制器组件类(Spring MVC的Controller),其功能与@Component()相同。

2. 装配bean时常用注解 @Autowired、@Resource【获取注解】

2.1 @Autowired【***常用】

该注解可以对类成员变量、方法及构造方法进行标注,完成自动装配的工作(按照Bean的类型进行装配)。 通过 @Autowired的使用来消除setter 和getter方法。默认按照Bean的类型进行装配。(属于Spring 的org.springframework.beans.factory.annotation包)

通过@Autowired注解,如果在容器中有对应的bean,就可以通过@Autowired自动装载,也就是赋值。装载之后自动的按照类型在spring容器中查找相同类型,然后为该字段其注入那个类型的bean实例。

其实就是一种依赖注入的方式,此方式必须确保加注解的类在spring中有对应的bean(怎样加进去不管),并且字段的类型需要在spring容器中有相同类型的bean,才能创建bean实例,为其注入。

@Autowired注解就相当于从Spring容器中通过类型,实例化了当前对象,可以直接调用它的方法。

@Autowired

private UserService userService;

// 相当于执行了实例化 private UserService userService = new UserServiceImpl();

2.2 @Resource(不属于spring的注解,是javax.annotation注解)

该注解与@Autowired功能一样。区别在于,该注解默认是按照名称来装配注入的,只有当找不到与名称匹配的Bean才会按照类型来装配注入;而@Autowired默认按照Bean的类型进行装配,如果想按照名称来装配注入,则需要结合@Qualifier注解一起使用。

@Resource注解有两个属性:name和type。name属性指定Bean实例名称,即按照名称来装配注入;type属性指定Bean类型,即按照Bean的类型进行装配。

2.3 @Qualifier(不能单独使用)

该注解与@Autowired注解配合使用。当@Autowired注解需要按照名称来装配注入,则需要结合该注解一起使用,Bean的实例名称由@Qualifier注解的参数指定。

2.4 @Autowired和@Qualifier的混合使用

@Autowired注解默认按照类型装配,如果容器中包含多个同一类型的Bean,那么启动容器时会报找不到指定类型bean的异常,解决办法是结合 @Qualifier 注解进行限定,指定注入的bean名称。

比如接口BaseInterface,它有两个实现类AClass和BClass,如果用@Autowired自动装载BaseInterface,会无法识别到底是哪一个实现类(AClass/BClass),所以就需要用@Qualifier来配合 @Autowired区分。

public class Demo{

@Autowired

@Qualifier("id值") //默认类名首字母小写 @Qualifier("aClass")

private BaseInterface base;

}


版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:初步探索yakit单兵作战工具
下一篇:Linux polkit本地权限提升漏洞(CVE-2021-4034)修复案例与POC复现方法(linux怎么读)
相关文章

 发表评论

暂时没有评论,来抢沙发吧~