在Grails中自动安装定制的Spring组件

时间:2014-10-15 03:46:52

标签: spring grails spring-annotations

我有一个定制的Spring,它捆绑在一个jar中,然后设置为我的Grails应用程序的依赖项。我使用resoueces.groovy中的importBeans语句加载bean的app-context,如

beans = {
  importBeans('classpath:app-context-my-component.xml')
}

app-context-my-component.xml有一些bean定义和以下行

<context:annotation-config />
<context:property-placeholder location="classpath:my-component.properties" />

我正在尝试使用Grails的组件使用@Component("myComponent")进行注释。

Grails正在加载外部应用程序上下文。我知道这是因为我首先在classpath上没有.properties文件,并且在我的@Value声明中我们没有丢失属性的回退机制。

在Grails控制器中,组件用作

class MyController {

  def myComponent

  def someaction() {
    myComponent.doSomething()
  }
}

结果是NullPointerException,即组件的自动装配在所有之后都不起作用。我试图在控制器中使用@Autowired,但这给了我一些奇怪的问题,我认为这不是我想要的道路。

正在使用的Grails版本为2.3.6 Spring组件也设置为使用 Spring版本3.2.7 以避免不兼容。

更新

现在再次掌握这个问题的时间,我设置了Spring日志记录,以便找出发生了什么。好吧,Spring上下文加载产生了大量的日志,但是这是我设法从全部中获取的内容

INFO xml.XmlBeanDefinitionReader Loading XML bean definitions from class path resource [app-context-my-component.xml]
INFO support.PropertySourcesPlaceholderConfigurer Loading properties file from class path resource [my-component.properties]
DEBUG framework.CglibAopProxy Unable to apply any optimisations to advised method: public myapp.external.MyComponent myapp.MyService.getMyComponentClient()
DEBUG framework.CglibAopProxy Unable to apply any optimisations to advised method: public myapp.external.MyComponent myapp.MyService.getMyComponentClient()
DEBUG framework.CglibAopProxy Unable to apply any optimisations to advised method: public myapp.external.MyComponent myapp.MyService.getMyComponentClient()
DEBUG framework.CglibAopProxy Unable to apply any optimisations to advised method: public void myapp.MyService.setMyComponentClient(myapp.external.MyComponent)
DEBUG framework.CglibAopProxy Unable to apply any optimisations to advised method: public void myapp.MyService.setMyComponentClient(myapp.external.MyComponent)
DEBUG framework.CglibAopProxy Unable to apply any optimisations to advised method: public void myapp.MyService.setMyComponentClient(myapp.external.MyComponent)

我更改了日志的命名空间,但 myapp.external 命名空间引用了外部jar包, myapp 命名空间引用了Grails应用程序命名空间。我已经更改了用法,因此外部组件是从服务而不是直接从Controller使用的,但该细节的行为没有变化。

根据我的理解,Spring上下文加载进展顺利。

更新2

根据 @ th3morg 的回答,我有一个想法,只尝试使用基于XML的配置,从bean中跳过所有@Component和这样的注释。它奏效了!现在,Grails设法导入bean,不再使用NPE。

虽然这至少部分地解决了我的问题。我仍然对可以使用Spring注释的解决方案感兴趣。

1 个答案:

答案 0 :(得分:6)

您应该确保在jar中设置了组件扫描。查看标题为&#34;使用Spring命名空间&#34;这里http://grails.org/doc/latest/guide/spring.html#theBeanBuilderDSLExplained。如果您无法修改jar,也可以使用resources.xml并将组件扫描添加到该文件中。

或者,您也可以逐个连接bean,尽管这很麻烦且乏味:

beans = {
  myComponent(com.my.MyComponent){
    someOtherService = ref('someOtherService') //if there are other beans to wire by name
    propertyOne = "x"
    propertyTwo = 2
  }
}