在*.java文件中搜索 bind方法可以发现在JPAPlanetModule.java、JPAWebloggerModule.java、RollerPlanetModule.java文件中使用了google的guice框架的bind方法。
也就是把java 接口和实现类绑定起来。
如:
binder.bind(WeblogManager.class).to( JPAWeblogManagerImpl.class);
这样在使用时只需要这样做:
@com.google.inject.Inject
protected JPAWeblogEntryManagerImpl(Weblogger roller, JPAPersistenceStrategy strategy) {
log.debug("Instantiating JPA Weblog Manager");
this.roller = roller;
this.strategy = strategy;
}
看来是按照类型,以参数的形式注入的。 这样用起来还是简单。
但是注入的入口方法在哪里呢? 搜索JPAWebloggerModule 在roller.properties中发现这样的配置
# Backend Guice module
guice.backend.module=org.apache.roller.weblogger.business.jpa.JPAWebloggerModule
然后搜索guice.backend.module 可以发现
/**
* Instantiate a new GuicePlanetProvider using default guice module
* configured in PlanetConfig via 'guice.backend.module' property.
*/
public GuicePlanetProvider() {
String moduleClassname = PlanetConfig.getProperty("guice.backend.module");
if(moduleClassname == null) {
throw new NullPointerException("unable to lookup default guice module via property 'guice.backend.module'");
}
try {
Class moduleClass = Class.forName(moduleClassname);
Module module = (Module)moduleClass.newInstance();
injector = Guice.createInjector(module);
} catch (Throwable e) {
// Fatal misconfiguration, cannot recover
throw new RuntimeException("Error instantiating backend module " + moduleClassname, e);
}
}
这个就是guice的入口方法。
但是这个方法是哪里调用的呢?搜索发现 在roller.properties中定义了这个配置
# Backend Provider
weblogger.provider.class=org.apache.roller.weblogger.business.GuiceWebloggerProvider
发现在 WebloggerFactory.java文件中有
public static final void bootstrap() throws BootstrapException {
// if the app hasn't been properly started so far then bail
if (!WebloggerStartup.isPrepared()) {
throw new IllegalStateException("Cannot bootstrap until application has been properly prepared");
}
// lookup our default provider and instantiate it
WebloggerProvider defaultProvider;
String providerClassname = WebloggerConfig.getProperty("weblogger.provider.class");
if(providerClassname != null) {
try {
Class providerClass = Class.forName(providerClassname);
defaultProvider = (WebloggerProvider) providerClass.newInstance();
} catch (Exception ex) {
throw new BootstrapException("Error instantiating default provider: "+providerClassname, ex);
}
} else {
throw new NullPointerException("No provider specified in config property 'weblogger.provider.class'");
}
// now just bootstrap using our default provider
bootstrap(defaultProvider);
}
反射调用。
在rollerContextd.java 这个类实现了如下接口
public class RollerContext extends ContextLoaderListener implements ServletContextListener
在 public void contextInitialized(ServletContextEvent sce) 方法中有调用
// trigger bootstrapping process
WebloggerFactory.bootstrap();
而org.apache.roller.weblogger.ui.core.RollerContext 定义在web.xml 中
这样就能够使容器启动时,就执行完成相应的初始化方法。