@mapperscan注解_Spring的@Import注解详解

首先看下@Import的javadoc文档:

Provides functionality equivalent to the <import/> element in Spring XML. Allows for importing @Configuration classes, ImportSelector and ImportBeanDefinitionRegistrar implementations, as well as regular component classes (as of 4.2; analogous to AnnotationConfigApplicationContext.register).
@Bean definitions declared in imported @Configuration classes should be accessed by using @Autowired injection. Either the bean itself can be autowired, or the configuration class instance declaring the bean can be autowired. The latter approach allows for explicit, IDE-friendly navigation between @Configuration class methods.
May be declared at the class level or as a meta-annotation.

简单翻译一下,这里面说了3个点:

(1)@Import就是用来向容器中导入bean的,导入的方式有三种:导入@Configuration、导入ImportSelector、导入ImportBeanDefinitionRegistrar。

(2)被@Import的类是被加载到了Spring容器当中,因此无论是类本身还是类里面用@Bean注解定义的bean都可以被@Autowired注入。

(3)@Import可以加在类上面,也可以作为元注解加在注解上面

下面就来分别举例说明下。

1.导入@Configuration举例

//这是个普通的类
public class Service1 {public Service1(){System.out.println("Service1");}
}
//这是个配置类
@Configuration
public class DemoConfig {@Beanpublic Service2 service2(){return new Service2();}
}
@SpringBootApplication
//这样可以导入Service1和Service2这两个Bean
@Import({Service1.class, DemoConfig.class})
public class ImportDemoApplication {public static void main(String[] args) {SpringApplication.run(ImportDemoApplication.class, args);}
}

2.导入ImportSelector举例

public class DemoImportSelector implements ImportSelector {@Overridepublic String[] selectImports(AnnotationMetadata importingClassMetadata) {//这里返回bean的完整的名字return new String[]{"com.github.xjs.importdemo.service.Service3"};}
}
@SpringBootApplication
//这样就可以导入Service3这个bean
@Import({DemoImportSelector.class})
public class ImportDemoApplication {public static void main(String[] args) {SpringApplication.run(ImportDemoApplication.class, args);}
}

3.导入ImportBeanDefinitionRegistrar举例

public class DemoRegistrar implements ImportBeanDefinitionRegistrar {@Overridepublic void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) {//可以直接向容器注册beanGenericBeanDefinition bd = new GenericBeanDefinition();bd.setBeanClass(Service4.class);registry.registerBeanDefinition("service4", bd);}
}
@SpringBootApplication
//这样就可以导入Service4这个bean
@Import({DemoRegistrar.class})
public class ImportDemoApplication {public static void main(String[] args) {SpringApplication.run(ImportDemoApplication.class, args);}
}

4.@Import作为元注解使用举例

因为@Import可以作为元注解使用,因此可以用这个特性来做组件扫描,比如:

//首先定义一个用于扫描的注解,上面添加@Import元注解:
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE})
@Import({DemoImportSelector.class})
public @interface DemoScan {/*** 要扫描的根路径* */String basePackage() default "";
}

然后在启动类或者配置类上添加这个注解:

@SpringBootApplication
//首先添加这个注解
@DemoScan(basePackage="com.github.xjs")
@Import({DemoImportSelector.class, DemoRegistrar.class})
public class ImportDemoApplication {public static void main(String[] args) {SpringApplication.run(ImportDemoApplication.class, args);}
}

无论是ImportSelector还是ImportBeanDefinitionRegistrar在回调中都可以使用AnnotationMetadata获取@DemoScan里面的属性:

public class DemoImportSelector implements ImportSelector {@Overridepublic String[] selectImports(AnnotationMetadata importingClassMetadata) {//读取DemoScan的属性AnnotationAttributes annoAttrs = AnnotationAttributes.fromMap(importingClassMetadata.getAnnotationAttributes(DemoScan.class.getName()));String basePackage = annoAttrs.getString("basePackage");System.out.println("basePackage:"+basePackage);return new String[]{"com.github.xjs.importdemo.service.Service3"};}
}

拿到了要扫描的路径如何去扫描可以参考上一篇如何去扫描Mapper接口的,在Spring的源码中有大量的这种用法,比如:ServletComponentScan与ServletComponentScanRegistrar、MapperScan与MapperScannerRegistrar等等。

5.@Import解析的源码

// org.springframework.context.annotation.ConfigurationClassParser:
private void processImports(ConfigurationClass configClass, SourceClass currentSourceClass,Collection<SourceClass> importCandidates, boolean checkForCircularImports) {...for (SourceClass candidate : importCandidates) {if (candidate.isAssignable(ImportSelector.class)) {// Candidate class is an ImportSelector -> delegate to it to determine importsClass<?> candidateClass = candidate.loadClass();ImportSelector selector = BeanUtils.instantiateClass(candidateClass, ImportSelector.class);ParserStrategyUtils.invokeAwareMethods(selector, this.environment, this.resourceLoader, this.registry);if (selector instanceof DeferredImportSelector) {this.deferredImportSelectorHandler.handle(configClass, (DeferredImportSelector) selector);}else {String[] importClassNames = selector.selectImports(currentSourceClass.getMetadata());Collection<SourceClass> importSourceClasses = asSourceClasses(importClassNames);processImports(configClass, currentSourceClass, importSourceClasses, false);}}else if (candidate.isAssignable(ImportBeanDefinitionRegistrar.class)) {// Candidate class is an ImportBeanDefinitionRegistrar ->// delegate to it to register additional bean definitionsClass<?> candidateClass = candidate.loadClass();ImportBeanDefinitionRegistrar registrar = BeanUtils.instantiateClass(candidateClass, ImportBeanDefinitionRegistrar.class);ParserStrategyUtils.invokeAwareMethods(registrar, this.environment, this.resourceLoader, this.registry);configClass.addImportBeanDefinitionRegistrar(registrar, currentSourceClass.getMetadata());}else {// Candidate class not an ImportSelector or ImportBeanDefinitionRegistrar ->// process it as an @Configuration classthis.importStack.registerImport(currentSourceClass.getMetadata(), candidate.getMetadata().getClassName());processConfigurationClass(candidate.asConfigClass(configClass));}}...
}
}

完整的源码下载:

https://github.com/xjs1919/enumdemo 下的 import-demo

欢迎扫码加关注:

ae540b540f6e97d615170f7519965810.png

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/502066.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

百合数c语言360问答,《百合花》

满意答案fadess1d2013.02.26采纳率&#xff1a;51% 等级&#xff1a;12已帮助&#xff1a;7212人作者茹志娟&#xff0c;于1958年3月在《延安》上面发表。这篇小说具有清新俊逸的艺术风格。是她前期的代表作。她写这篇小说时&#xff0c;中那个是反右斗争扩大化&#xff0c;…

python 实现显著性检测_使用python轻松实现高大上的YOLOV4对象检测算法

YOLO系列对象检测算法&#xff0c;算是人工智能技术领域的一匹黑马&#xff0c;当开发者宣布不再为YOLO系列检测算法更新时&#xff0c;很多开发者瞬间失去了”精神食粮“。突然&#xff0c;当YOLOV4检测算法发布的时候&#xff0c;让很多开发者喜出望外。YOLOV4对象检测YOLOV4…

android source镜像源_【转载】Celadon快速上路指南Part2:编译Celadon镜像

Celadon快速上路指南Part2&#xff1a;编译Celadon镜像From: 孙晓璐 AndroidIA Celadon 9/20一目了然 | Celadon 新手上路快速通道隆重揭晓 | 打开Celadon 的正确姿势上一期我们向您介绍了如何安装Celadon预编译镜像&#xff08;Celadon快速上路指南 Part1&#xff1a;安装Cela…

python中os模块_Python的武器库11:os模块

说到编程语言python&#xff0c;有一个著名的格言"余生太短&#xff0c;只用python"。如果要分析为什么会存在这么一句格言&#xff1f;python的语法并不简单&#xff0c;有复杂难懂的部分&#xff0c;之所以有这样一句格言&#xff0c;是因为python中有很多强大的模…

java 同步锁_死磕 java同步系列之自己动手写一个锁Lock

问题&#xff08;1&#xff09;自己动手写一个锁需要哪些知识&#xff1f;&#xff08;2&#xff09;自己动手写一个锁到底有多简单&#xff1f;&#xff08;3&#xff09;自己能不能写出来一个完美的锁&#xff1f;简介本篇文章的目标一是自己动手写一个锁&#xff0c;这个锁的…

android里canvas视频帧,移动端用canvas截取视频封面,如何不截取第一帧,而是截取其它的帧?...

我在微信开发工具里截的图是可以的&#xff0c;但是在手机上截的图缺变成全透明的了。我猜是视频的第一帧的问题微信开发工具的截图手机的截图我的代码&#xff1a;JS&#xff1a;function captureImage(video) {var scale1var canvas document.createElement("canvas&qu…

python画正方形内切圆_python画出三角形外接圆和内切圆的方法

刚看了《最强大脑》中英对决&#xff0c;其中难度最大的项目需要选手先脑补泰森多边形&#xff0c;再找出完全相同的两个泰森多边形。在惊呆且感叹自身头脑愚笨的同时&#xff0c;不免手痒想要借助电脑弄个图出来看看&#xff0c;闲来无事吹吹牛也是极好的。 今天先来画画外接圆…

查看地区的ip段_「教程」CloudFlare 自选 IP优化网站速度

前言CloudFlare 官网虽然不提供 CNAME / AAAA / A 记录接入 CloudFlare 的 CDN &#xff0c;但是我们可以通过 CloudFlare Partner 免费使用 CNAME / A 记录接入 CloudFlare 。而我们正好利用 CloudFlare 使用 A 记录接入 CDN 的方式&#xff0c;自定义节点 IP &#xff0c;例如…

android手机可以设置屏幕锁定,安卓手机屏幕锁设置方法(九个点图案)

这里以三星S5368手机屏幕锁为例随着三星S5368手机系统功能愈来愈完善&#xff0c;性能愈来愈强劲&#xff0c;越来越多的三星S5368用户们都喜欢把一些重要的信息甚至隐私放在三星S5368手机里面&#xff0c;但是这就有可能会让别人看到&#xff0c;这样一来你的三星S5368里面的信…

python win10 连接hive_使用win10+python3.5+impyla 连接大数据平台hive表的步骤与问题解决...

环境硬件配置及Hadoop&#xff0c;Hive版本一、安装步骤pip install pure-saslDownloading https://pypi.tuna.tsinghua.edu.cn/packages/16/83/30eaf3765de898083 75a8358f9c15d45a3dd44ed26be991471abc0b4480b/pure_sasl-0.5.1-py2.py3-none-any.whlpip install thrift_sasl0…

python将excel表按地方拆分_Python将一个Excel拆分为多个Excel

本文实例为大家分享了Python将一个Excel拆分为多个Excel的具体代码&#xff0c;供大家参考&#xff0c;具体内容如下 原始文档如下图所示将销售部门一、二、三科分别存为三个Excel 代码如下 # -*- coding: utf-8 -*- """ Created on Mon Jul 9 20:25:31 2018 au…

华为申请注册鸿蒙商标,华为申请“鸿蒙商标”,企业注册商标有什么价值?

原标题&#xff1a;华为申请“鸿蒙商标”&#xff0c;企业注册商标有什么价值&#xff1f;国家知识产权局商标局网站显示&#xff0c;华为已申请“华为鸿蒙”商标。申请日期为2018年8月24日&#xff0c;注册公告日期为2019年5月14日&#xff0c;专用权限期是从2019年5月14日到2…

html5音乐播放器设计论文,基于微信小程序的音乐播放器设计和毕业论文

摘 要随着通信技术的发展和智能设备的普及&#xff0c;移动互联网在近两年发展迅猛&#xff0c;新兴的移动社交软件“微信”逐渐走进了手机用户的生活&#xff0c;深受全国数亿用户的欢迎。随着微信版本的不断更新&#xff0c;微信也从单纯的聊天应用逐变成媒体信息、游戏娱乐…

python后端开发学什么_零基础学Python,这是阿里Python8年开发经验写给你的学习路线图...

今天给大家分享一位前辈整理的一个Python web学习路线。这位前辈由于有编程基础&#xff0c;所以采用了自学Python的方式。学完后主要做后端开发。希望对你有所启发。 整理的一个 python web 学习路线&#xff0c;这基本就是笔者自学后做后端的学习路线。入门基础 编程语言: Py…

如何把meshlab中的圆环去掉_如何设计一座太空城?

整整半个世纪前的今天&#xff0c;1969年7月20日&#xff0c;执行阿波罗11号计划的美国宇航员阿姆斯特朗和奥尔德林登上月球。而同一年&#xff0c;伍德斯托克音乐节的舞台前聚集了几十万名追求和平与爱的青年。在神奇的1969年&#xff0c;人类文明向着更为广袤与深邃的境地突飞…

axure html 360安装扩展,win10系统360浏览器添加Axure扩展的操作方法

win10系统360浏览器添加Axure扩展的操作方法?很多win10用户在使用电脑的时候&#xff0c;会发现win10系统360浏览器添加Axure扩展的的现象&#xff0c;根据小编的调查并不是所有的朋友都知道win10系统360浏览器添加Axure扩展的的问题怎么解决&#xff0c;不会的朋友也不用担心…

电信计算机知识考试,2020中国电信考试试题——专业知识一

1、我国对独立型STP设备要求其信令链路数不得小于( )A、7000MSU/s&#xff1b;B、10000MSU/s&#xff1b;C、14000MSU/s&#xff1b;D、20000MSU/s2、GSM的多址方式为( )A、FDMA&#xff1b; B、TDMA&#xff1b; C、CDMA&#xff1b; D、FDMA-TDMA混合技术3、以下属于被叫控制…

full outer join 与full join的区别_sleep、yield、join都是干啥的? sleep与wait有啥区别?中篇[十五]...

点击上方 “ 布衣码农 ” &#xff0c;免费订阅~选择“ 设为星标 ”&#xff0c;第一时间免费获得更新~「布衣码农」用不到却又不得不学习了解的底层方法1。Object中的wait、notify、notifyAll&#xff0c;可以用于线程间的通信&#xff0c;核心原理为借助于监视器的入口集与等…

npu算力如何计算_异构计算神器来了,它能带来性能革命吗

前言&#xff1a;优化差有多要命&#xff1f;3A大作告诉您说到最近游戏圈子里的热门话题&#xff0c;刚刚在全平台上线的某“国产3A大作”显然绝对值得一提。一方面来说&#xff0c;靠着“抽卡化单机游戏”的设计&#xff0c;以及投入几十万元都难以实现全角色满状态的高氪金程…

画股票图csdn_这个股票今天是要弄啥?

点击上方蓝色字体&#xff0c;关注我们作者 | 四叶草编辑 | 易小投大盘点评今天市场上午走势相对弱势&#xff0c;盘中只有杀出一点点急跌的恐慌盘&#xff0c;有一些盘中的做T机会&#xff0c;但是确定性不是特别高&#xff0c;毕竟盘中的急跌相对幅度有限。下午指数随着一些概…