草庐IT

【Spring boot 普通类调用 Bean】

God Zhang 2023-04-21 原文
Spring boot 普通类调用 Bean
我们知道如果我们要在一个类使用 spring 提供的 bean 对象,我们需要把这个类注入到 spring 容器中,
交给 spring
容器进行管理,但是在实际当中,我们往往会碰到在一个普通的 Java 类中,想直接使用 spring 提供的其他对象
或者说有一些不需要交给 spring 管理,但是需要用到 spring 里的一些对象。如果这是 spring 框架的独立应用程
序,我们通过:
ApplicationContext ac = new FileSystemXmlApplicationContext("applicationContext.xml");
ac.getBean("beanId");
这样的方式就可以很轻易的获取我们所需要的对象。
但是往往我们所做的都是 Web Application,这时我们启动 spring 容器是通过在 web.xml 文件中配置,这样就不
适合使用上面的方式在普通类去获取对象了,因为这样做就相当于加载了两次 spring 容器,而我们想是否可以
通过在启动 web 服务器的时候,就把 Application 放在某一个类中,我们通过这个类在获取,这样就可以在普通
类获取 spring bean 对象了,让我们接着往下看。
普通类调用 Spring bean 对象:
可以参考:http://412887952-qq-com.iteye.com/blog/1479445
这里有更多这方面的介绍,比较详细,在这里只是抛装引玉说明在 Spring Boot 是如何进行调用的。
在 Spring Boot 可以扫描的包下
假设我们编写的工具类为 SpringUtil。
如果我们编写的 SpringUtil 在 Spring Boot 可以扫描的包下或者使用@ComponentScan 引入自定义的包了,那
么原理很简单,只需要使得 SpringUtil 实现接口:ApplicationContextAware,然后加上@Component 注解即可,
具体编码如下:
package com.hpit.springboot01.util;
import org.apache.log4j.Logger;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.stereotype.Component;
/**
* spring工具类,为了更方便的获取spring的applicationContext 直接实现接口ApplicationContextAware
*
*
*/
@Component
public class SpringUtil implements ApplicationContextAware {
private Logger logger = Logger. getLogger (getClass());
private static ApplicationContext applicationContext ;
@Override
public void setApplicationContext(ApplicationContext applicationContext ) throws BeansException {
if (SpringUtil. applicationContext == null ) {
SpringUtil. applicationContext = applicationContext ;
}
logger .info(
"========ApplicationContext配置成功,在普通类可以通过调用
SpringUtils.getApplicationContext()获取applicationContext对象,applicationContext="
+ SpringUtil. applicationContext + "========" );
}
/**
* 获取spring上下wen
*
* @return
*/
public static ApplicationContext getApplicationContext() {
return applicationContext ;
}
public static Object getBean(String beanName ) {
return applicationContext .getBean( beanName );
}
public static <T> Object getBean(Class<T> class1 ) {
return applicationContext .getBean( class1 );
}
public static <T> Object getBean(Class<T> class1 , String beanName ) {
return applicationContext .getBean( class1 , beanName );
}
}
不在 Spring Boot 的扫描包下方式一
这种情况处理起来也很简单,先编写 SpringUtil 类,同样需要实现接口:ApplicationContextAware,具体编
码如下:
simple.plugin.spring.SpringUtil
package simple.plugin.spring;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
public class SpringUtil implements ApplicationContextAware{
private static ApplicationContext applicationContext = null ;
@Override
public void setApplicationContext(ApplicationContext applicationContext ) throws BeansException
{
if (SpringUtil. applicationContext == null ){
SpringUtil. applicationContext = applicationContext ;
}
System. out .println( "---------------------------------------------------------------------" );
System. out .println( "---------------------------------------------------------------------" );
System. out .println( "---------------simple.plugin.spring.SpringUtil--------------------------------------
----------------" );
System. out .println( "========ApplicationContext 配置成功 , 在普通类可以通过调用
SpringUtils.getAppContext()
获 取
applicationContext
象,applicationContext=" +SpringUtil. applicationContext + "========" );
System. out .println( "---------------------------------------------------------------------" );
}
//获取 applicationContext
public static ApplicationContext getApplicationContext() {
return applicationContext ;
}
//通过 name 获取 Bean.
public static Object getBean(String name ){
return getApplicationContext ().getBean( name );
}
//通过 class 获取 Bean.
public static <T> T getBean(Class<T> clazz ){
return getApplicationContext ().getBean( clazz );
}
//通过 name,以及 Clazz 返回指定的 Bean
public static <T> T getBean(String name ,Class<T> clazz ){
return getApplicationContext ().getBean( name , clazz );
}
}
之后这一步才是关键,使用@Bean 注解,在 App.java 类中将 SpringUtil 注解进来,代码如下:
package com.hpit;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.web.servlet.ServletComponentScan;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Import;
import simple.plugin.spring.SpringUtil;
/**
* Hello world!
*
*/
// 其中 @SpringBootApplication 申明让 spring boot 自动给程序进行必要的配置,等价于以默认属性使用
@Configuration @EnableAutoConfiguration @ComponentScan
@SpringBootApplication
@ServletComponentScan
public class App {
/** 注册 Spring Util
* 这里为了和上一个冲突,所以方面名为: springUtil2
* 实际中使用 springUtil
*/
@Bean
public SpringUtil springUtil2(){return new SpringUtil();}
/**
*
参数里 VM 参数设置为:
-javaagent:.\lib\springloaded-1.2.4.RELEASE.jar -noverify
* @param args
*/
public static void main(String[] args) {
SpringApplication.run(App.class, args);
}
}
不在 Spring Boot 的扫描包下方式二
代码基本和上面都是相同的,主要是在 App.java 中使用@Import 进行导入。
而且在 SpringUtil 是不需要添加@Component 注解
@SpringBootApplication
@ServletComponentScan
@Import (value={SpringUtil. class })
publicclass App {
//省略其它代码.
}
说明以上 3 中方式都生效了,这 3 中方式根据实际情况选择一种方式就可以了。
那么这样子在普通类既可以使用:
SpringUtil.getBean() 获取到 Spring IOC 容器中的 bean。
当然也可以在 Spring 管理的类中使用:
@Resouce 或者@Autowired 进行注入使用,当然我们这个类的核心是普通类可以调用 spring 的 bean 进行使用
了,是不是很神奇呢。

有关【Spring boot 普通类调用 Bean】的更多相关文章

  1. 使用 ACL 调用 upload_file 时出现 Ruby S3 "Access Denied"错误 - 2

    我正在尝试编写一个将文件上传到AWS并公开该文件的Ruby脚本。我做了以下事情:s3=Aws::S3::Resource.new(credentials:Aws::Credentials.new(KEY,SECRET),region:'us-west-2')obj=s3.bucket('stg-db').object('key')obj.upload_file(filename)这似乎工作正常,除了该文件不是公开可用的,而且我无法获得它的公共(public)URL。但是当我登录到S3时,我可以正常查看我的文件。为了使其公开可用,我将最后一行更改为obj.upload_file(file

  2. c# - 如何在 ruby​​ 中调用 C# dll? - 2

    如何在ruby​​中调用C#dll? 最佳答案 我能想到几种可能性:为您的DLL编写(或找人编写)一个COM包装器,如果它还没有,则使用Ruby的WIN32OLE库来调用它;看看RubyCLR,其中一位作者是JohnLam,他继续在Microsoft从事IronRuby方面的工作。(估计不会再维护了,可能不支持.Net2.0以上的版本);正如其他地方已经提到的,看看使用IronRuby,如果这是您的技术选择。有一个主题是here.请注意,最后一篇文章实际上来自JohnLam(看起来像是2009年3月),他似乎很自在地断言RubyCL

  3. java - 从 JRuby 调用 Java 类的问题 - 2

    我正在尝试使用boilerpipe来自JRuby。我看过guide从JRuby调用Java,并成功地将它与另一个Java包一起使用,但无法弄清楚为什么同样的东西不能用于boilerpipe。我正在尝试基本上从JRuby中执行与此Java等效的操作:URLurl=newURL("http://www.example.com/some-location/index.html");Stringtext=ArticleExtractor.INSTANCE.getText(url);在JRuby中试过这个:require'java'url=java.net.URL.new("http://www

  4. ruby - 调用其他方法的 TDD 方法的正确方法 - 2

    我需要一些关于TDD概念的帮助。假设我有以下代码defexecute(command)casecommandwhen"c"create_new_characterwhen"i"display_inventoryendenddefcreate_new_character#dostufftocreatenewcharacterenddefdisplay_inventory#dostufftodisplayinventoryend现在我不确定要为什么编写单元测试。如果我为execute方法编写单元测试,那不是几乎涵盖了我对create_new_character和display_invent

  5. 【鸿蒙应用开发系列】- 获取系统设备信息以及版本API兼容调用方式 - 2

    在应用开发中,有时候我们需要获取系统的设备信息,用于数据上报和行为分析。那在鸿蒙系统中,我们应该怎么去获取设备的系统信息呢,比如说获取手机的系统版本号、手机的制造商、手机型号等数据。1、获取方式这里分为两种情况,一种是设备信息的获取,一种是系统信息的获取。1.1、获取设备信息获取设备信息,鸿蒙的SDK包为我们提供了DeviceInfo类,通过该类的一些静态方法,可以获取设备信息,DeviceInfo类的包路径为:ohos.system.DeviceInfo.具体的方法如下:ModifierandTypeMethodDescriptionstatic StringgetAbiList​()Obt

  6. C51单片机——实现用独立按键控制LED亮灭(调用函数篇) - 2

    说在前面这部分我本来是合为一篇来写的,因为目的是一样的,都是通过独立按键来控制LED闪灭本质上是起到开关的作用,即调用函数和中断函数。但是写一篇太累了,我还是决定分为两篇写,这篇是调用函数篇。在本篇中你主要看到这些东西!!!1.调用函数的方法(主要讲语法和格式)2.独立按键如何控制LED亮灭3.程序中的一些细节(软件消抖等)1.调用函数的方法思路还是比较清晰地,就是通过按下按键来控制LED闪灭,即每按下一次,LED取反一次。重要的是,把按键与LED联系在一起。我打算用K1来作为开关,看了一下开发板原理图,K1连接的是单片机的P31口,当按下K1时,P31是与GND相连的,也就是说,当我按下去时

  7. ruby - 如何找到调用当前方法的方法 - 2

    如何找到调用此方法的位置?defto_xml(options={})binding.pryoptions=options.to_hifoptions&&options.respond_to?(:to_h)serializable_hash(options).to_xml(options)end 最佳答案 键入caller。这将返回当前调用堆栈。文档:Kernel#caller.例子[0]%rspecspec10/16|===================================================62=====

  8. ruby-on-rails - 使用 HTTParty 的非常基本的 Rails 4.1 API 调用 - 2

    Rails相对较新。我正在尝试调用一个API,它应该向我返回一个唯一的URL。我的应用程序中捆绑了HTTParty。我已经创建了一个UniqueNumberController,并且我已经阅读了几个HTTParty指南,直到我想要什么,但也许我只是有点迷路,真的不知道该怎么做。基本上,我需要做的就是调用API,获取它返回的URL,然后将该URL插入到用户的数据库中。谁能给我指出正确的方向或与我分享一些代码? 最佳答案 假设API为JSON格式并返回如下数据:{"url":"http://example.com/unique-url"

  9. ruby - 为什么当我调用类的实例方法时,初始化不显示为方法? - 2

    我正在写一篇关于在Ruby中几乎一切都是对象的博客文章,我试图通过以下示例来展示这一点:classCoolBeansattr_accessor:beansdefinitialize@bean=[]enddefcount_beans@beans.countendend所以从类中我们可以看出它有4个方法(当然,除非我错了):它可以在创建新实例时初始化一个默认的空bean数组它可以计算它有多少个bean它可以读取它有多少个bean(通过attr_accessor)它可以向空数组写入(或添加)更多bean(也通过attr_accessor)但是,当我询问类本身它有哪些实例方法时,我没有看到默认

  10. ruby-on-rails - Rake 任务仅调用一次时执行两次 - 2

    我写了一个非常简单的rake任务来尝试找到这个问题的根源。namespace:foodotaskbar::environmentdoputs'RUNNING'endend当在控制台中执行rakefoo:bar时,输出为:RUNNINGRUNNING当我执行任何rake任务时会发生这种情况。有没有人遇到过这样的事情?编辑上面的rake任务就是写在那个.rake文件中的所有内容。这是当前正在使用的Rakefile。requireFile.expand_path('../config/application',__FILE__)OurApp::Application.load_tasks这里

随机推荐