在Grails中定义可选(多个)数据源

在Grails中定义可选(多个)数据源,grails,datasource,multiple-databases,Grails,Datasource,Multiple Databases,我目前正在使用Grails2.3.11开发一个Grails插件,并且熟悉使用多个数据源。但现在我希望该插件提供的域对象可以使用不同的数据源(因为性能原因,所有数据都可以存储在不同的数据库中) 问题是,第二个数据源是可选的,这意味着用户可以在tomcat中定义第二个数据源(可通过JNDI访问),但不必这样做。这一点很重要:用户可以在servlet容器中定义第二个数据源,Grails应用程序必须检查是否有第二个可用的数据源 更具体地说:我有一个域类: class MyDomain { st

我目前正在使用Grails2.3.11开发一个Grails插件,并且熟悉使用多个数据源。但现在我希望该插件提供的域对象可以使用不同的数据源(因为性能原因,所有数据都可以存储在不同的数据库中)

问题是,第二个数据源是可选的,这意味着用户可以在tomcat中定义第二个数据源(可通过JNDI访问),但不必这样做。这一点很重要:用户可以在servlet容器中定义第二个数据源,Grails应用程序必须检查是否有第二个可用的数据源

更具体地说:我有一个域类:

class MyDomain {

    static mapping = {
        datasource('optionalDS')
    }
}
My DataSource.groovy:

dataSource {
    jndiName = "..."
}

dataSource_optionalDS {
    jndiName = "..."
}
问题是,如果用户没有为该可选数据源配置JNDI名称(因为它是可选的,他不必这样做),那么这将失败

我尝试创建一个委派数据源:

class OptionalDataSource extends DelegatingDataSource {

    ...
    // the main purpose is to check, if the optional DS
    // can be created using JNDI. If this fails, the default
    // DS is used
    setTagetDataSource(dataSource)
    ...

}
在我的插件描述符中:

def doWithSpring = {
    dataSource_optionalDS(OptionalDataSource) {
        // set default DS in case optional can not be created
        dataSource = ref('dataSource')
    }
}
此解决方案的问题是,数据源选项DS不可用。如果我尝试读取数据,即MyDomain.findAll(),则会出现以下错误:

MyDomain类上的Method在Grails应用程序之外使用。 如果在使用模拟API的测试上下文中运行,或 引导Grails正确

我不明白为什么,因为我可以这样定义默认数据源


所以,我的问题是:如何在Grails中定义可选的数据源

dataSource.groovy
中查找
JNDI数据源
,然后如果它存在,则声明可选的
数据源
。像下面这样的

    //default dataSource
    dataSource {
        jndiName = "..."
    } 

    //optional dataSource
    //let's first lookup the JNDI dataSource
    def jndiDataSource

    try {
        jndiDataSource = InitialContext.doLookup("...")
    } 
    catch(NamingException ne) {}

    //now if jndiDataSource exists we can declare the optional dataSource
    if(jndiDataSource) {
        dataSource_optionalDS {
            jndiName = "..."
        }
    }

我正在寻找另一种lightwight方法,只检查
JNDI数据源是否存在,而不是查找它。但是没有运气

这是个好主意。我稍微修改了您的代码,因为我必须在域类中声明可选的数据源。而且,如果jndi查找失败,我将使用默认数据源的jndi名称来创建可选数据源。