Java 如何要求 spring 对 new 出来的实例内的 @Autowired 成员变量注入?

2020-01-20 11:46:04 +08:00
 Newyorkcity
1971 次点击
所在节点    问与答
10 条回复
dddddddddd
2020-01-20 11:50:48 +08:00
为什么要手动 new, 可以直接从容器了取呀
Newyorkcity
2020-01-20 11:51:51 +08:00
@dddddddddd 没给那个类加 @Component 之类的注解。。。。。
nutting
2020-01-20 11:55:35 +08:00
不能,用 spring 最好就都让它管理
Newyorkcity
2020-01-20 12:00:58 +08:00
@nutting 那工厂模式咋整?工厂类我只调用它的静态方法,这把它 @Component 感觉有点得不偿失。。工厂类返回的实例按理来说应该是 new 出来的,给可能被工厂用来制造实例的类都给注解 @Component ?然后用 getBean 得到来返回?
可是 getBean 前面的 spring 上下文怎么得到呢。。。
dddddddddd
2020-01-20 12:01:56 +08:00
如何没有注册这个 bean,Autowired 是不管用的, 可以查一下 spring 如何动态注册 bean,应该是可以的
Newyorkcity
2020-01-20 12:02:49 +08:00
@Newyorkcity new 出来 --》 反射反出来
richard1122
2020-01-20 13:22:13 +08:00
```java
private @Autowired AutowireCapableBeanFactory beanFactory;

public void doStuff() {
MyBean obj = new MyBean();
beanFactory.autowireBean(obj);
// obj will now have its dependencies autowired.
}
```
https://stackoverflow.com/questions/3813588/how-to-inject-dependencies-into-a-self-instantiated-object-in-spring

把对象传进去帮你做 autowire
urzz
2020-01-20 15:22:53 +08:00
ApplicationContextAware
jaylee4869
2020-01-20 16:02:44 +08:00
给你工具类:

```java

package com.utils;

import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;

/**
* 以静态变量保存 Spring ApplicationContext, 可在任何代码任何地方任何时候中取出 ApplicaitonContext.
*
*/
public class SpringContextHolder implements ApplicationContextAware {
private static ApplicationContext applicationContext;

/**
* 实现 ApplicationContextAware 接口的 context 注入函数, 将其存入静态变量.
*/
@Override
public void setApplicationContext(ApplicationContext applicationContext) {
// NOSONAR
SpringContextHolder.applicationContext = applicationContext;
}

/**
* 取得存储在静态变量中的 ApplicationContext.
*/
public static ApplicationContext getApplicationContext() {
checkApplicationContext();
return applicationContext;
}

/**
* 从静态变量 ApplicationContext 中取得 Bean, 自动转型为所赋值对象的类型.
*/
public static <T> T getBean(String name) {
checkApplicationContext();
return (T) applicationContext.getBean(name);
}

/**
* 从静态变量 ApplicationContext 中取得 Bean, 自动转型为所赋值对象的类型.
*/
public static <T> T getBean(Class<T> clazz) {
checkApplicationContext();
return (T) applicationContext.getBean(clazz);
}

/**
* 清除 applicationContext 静态变量.
*/
public static void cleanApplicationContext() {
applicationContext = null;
}

private static void checkApplicationContext() {
if (applicationContext == null) {
throw new IllegalStateException(
"applicaitonContext 未注入,请在 applicationContext.xml 中定义 SpringContextHolder");
}
}
}
```
69partner
2020-01-20 16:03:50 +08:00
既然不想用 @Autowired 你都说了 new 那就 new 呀

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/639405

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX