Java 如何在自定义Wicket模型类中注入Springbean?
在一个定制Wicket类中,与下面的不同,我使用的是一个服务bean,它应该由Spring注入,正如SpringBean注释(来自Wicket-Spring项目)所定义的那样Java 如何在自定义Wicket模型类中注入Springbean?,java,spring,dependency-injection,wicket,Java,Spring,Dependency Injection,Wicket,在一个定制Wicket类中,与下面的不同,我使用的是一个服务bean,它应该由Spring注入,正如SpringBean注释(来自Wicket-Spring项目)所定义的那样 公共类ReportExportFileModel扩展了AbstractReadOnlyModel{ @SpringBean(name=“reportService”) 报告服务报告服务; 报告到报告到; ReportExportFileModel(ReportDto ReportDto){ this.reportDto=r
公共类ReportExportFileModel扩展了AbstractReadOnlyModel{
@SpringBean(name=“reportService”)
报告服务报告服务;
报告到报告到;
ReportExportFileModel(ReportDto ReportDto){
this.reportDto=reportDto;
}
@凌驾
公共文件getObject(){
试一试{
return reportService.generatePentahoReport(reportDto);
}捕获(ReportGenerationException e){
// ...
}
}
}
但是,这不起作用:reportService.generatePentahoReport()
因NullPointerException而失败,因为由于某种原因Spring没有注入bean
奇怪的是,我在Wicket页面上使用了与匿名内部类完全相同的模型代码,并且没有出现任何问题
如何解决这个问题?显然,Springbeans不会自动注入到页面以外的其他类中。我的自定义WebRequestCycle类也实现了这一点 一个简单的解决方案是使用
InjectorHolder.getInjector().inject(this)
手动触发注入
因此,这样编写构造函数可以使模型按预期工作:
ReportExportFileModel(ReportDto reportDto) {
this.reportDto = reportDto;
InjectorHolder.getInjector().inject(this);
}
编辑:啊,在发布这篇文章之后,我发现了另一个关于发生了什么的问题:
@SpringBean只在组件的任何子类中工作
wicket依赖项注入与实现IComponentInstanceListener的类一起工作。只要实例化组件,就会调用这些应用程序级侦听器。这是用于组件依赖项注入的钩子 模型类没有这样的机制。任何模型都可以直接实现IModel,因此与组件不同,没有抽象基类可以调用侦听器 我为我的注入模型(Wicket 1.5)使用以下基类: 及 Wicket 1.5: 及
如果有人知道更好的解决方案,或者可以解释为什么wicket-spring集成是这样工作的,请随意发布其他答案!伯尼解释了它的工作原理。我只能补充一点,在Wicket 1.5.3+中,行为也会像o.a.w.组件一样自动注入。很抱歉像旧黑手党战争一样讨论;),请记住我为什么模型不能被注入,这个决定有深刻的哲学背景,还是只有实现特性?而正统wicket解决方案是如何形成模型、资源等的呢?答案是:因为它是基于接口的,而不是基于类的这是Wicket 1.5,而Jonik仍然使用1.4。是的,@martin-g是对的;我忘了在问题中提到它,但我在1.4.17。如果您将答案编辑为涵盖1.4和1.5,我将接受:)
ReportExportFileModel(ReportDto reportDto) {
this.reportDto = reportDto;
InjectorHolder.getInjector().inject(this);
}
public abstract class InjectedDetachableModel<T> extends LoadableDetachableModel<T> {
public InjectedDetachableModel() {
Injector.get().inject(this);
}
public InjectedDetachableModel(T a_entity) {
super(a_entity);
Injector.get().inject(this);
}
}
@Override
protected void init()
{
// initialize Spring
addComponentInstantiationListener(new SpringComponentInjector(this, applicationContext));
}
InjectorHolder.getInjector().inject(Object object)
@Override
protected void init()
{
// initialize Spring
getComponentInstantiationListeners().add(new SpringComponentInjector(this, applicationContext))
}
Injector.get().inject(Object object)