java 使用 Guice 注入特定实例
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/16748126/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Injecting specific instance with Guice
提问by halfwarp
I'm having a few problems injecting a specific field instance with Guice.
我在使用 Guice 注入特定字段实例时遇到了一些问题。
Here's what I currently have:
这是我目前拥有的:
class Driver {
private ThreadLocal<Database> db;
...
}
I'd usually just pass the db instance in a constructor. But this class will be intercepted, using guice.
我通常只是在构造函数中传递 db 实例。但是这个类会被拦截,使用guice。
Here's the module:
这是模块:
class MyGuiceModule extends AbstractModule {
private ThreadLocal<Database> dbToInject;
public MyGuiceModule(ThreadLocal<Database> dbToInject) {
this.dbToInject = dbToInject;
}
@Override
protected void configure() {
// Binds the interceptor.
bindInterceptor(....);
bind(ThreadLocal.class).toInstance(this.dbToInject);
}
}
And here's how I'm instantiating all the stuff:
这是我实例化所有东西的方式:
Injector injector = new Injector(new MyGuiceModule(db));
Driver driver = injector.getInstance(Driver.class);
I bet it's pretty obvious, but what am I doing wrong here?
我敢打赌这很明显,但我在这里做错了什么?
EDIT:
编辑:
Sorry if I wasn't clear. My problem is that this is not working. The instance is not being injected. I've annotated the field with @Inject and still doesn't work.
对不起,如果我不清楚。我的问题是这不起作用。未注入该实例。我已经用@Inject 注释了该字段,但仍然不起作用。
回答by Mingyu
I think you need to use Guice.createInjectorto create an injector instance.
Here's how I would create an injector:
Injector injector = Guice.createInjector(new MyGuiceModule(db));
Another thing is you used the following code to perform binding:
bind(ThreadLocal.class).toInstance(this.dbToInject);
Usually, it would be something like:
bind(MyInterface.class).toInstance(MyImplementation.class);
Your ThreadLocal.class is not an interface class, and this.dbToInject is not your implementation class.
我认为您需要使用Guice.createInjector来创建一个注入器实例。
下面是我将如何创建一个注入器:
Injector injector = Guice.createInjector(new MyGuiceModule(db));
另一件事是您使用以下代码执行绑定:
bind(ThreadLocal.class).toInstance(this.dbToInject);
通常,它会是这样的:
bind(MyInterface.class).toInstance(MyImplementation.class);
您的 ThreadLocal.class 不是接口类,而 this.dbToInject 也不是您的实现类。
Here's the documentation:
这是文档:
http://code.google.com/p/google-guice/wiki/Motivation
http://code.google.com/p/google-guice/wiki/Motivation
Hope this helps.
希望这可以帮助。
回答by condit
It would probably be better not to inject the ThreadLocal
directly but to inject the Database into the constructor (as @Tobias suggested). And do you really want to use the same Database for all the instance of the Driver that are created (note the optional singleton in the comment)?
最好不要ThreadLocal
直接注入,而是将数据库注入构造函数(如@Tobias 建议的那样)。并且您真的想对创建的所有驱动程序实例使用相同的数据库(注意注释中的可选单例)?
public class GuiceExample {
public static class MyGuiceModule extends AbstractModule {
@Override
protected void configure() {
bind(Driver.class);
}
@Provides
//Uncomment this to use the same Database for each Driver
//@Singleton
Database getDatabase() {
return new Database();
}
}
@Test
public void testInjection() {
Injector i = Guice.createInjector(new MyGuiceModule());
i.getInstance(Driver.class);
}
public static class Database {}
public static class Driver {
ThreadLocal<Database> db = new ThreadLocal<Database>();
@Inject
Driver(Database db) {
this.db.set(db);
}
}
}