我们有一个grails应用程序,该应用程序在grails数据库中存储了各种域对象。该应用程序连接到第二个数据库,运行一些原始sql,并在表中显示结果。它基本上是一个报告服务器。

我们通过在DataSource.groovy中指定第二个数据源来连接第二个db,例如:

dataSource_target { 
dialect = org.hibernate.dialect.MySQLInnoDBDialect 
pooled = true 
jmxExport = true 
driverClassName = "com.mysql.jdbc.Driver" 
username = "bla" 
password = "bla" 
} 

然后在 Controller 中,我们有
static mapping = { 
    datasource 'ALL' 
 } 

然后在服务中,我们有:
         con = new Sql(dataSource_target) 
         rows = con.rows(sql) 

它可以工作,但是有两个大问题:
  • 如果在运行gra-app时报表应用程序无法连接到第二个“目标”数据源,则它将无法启动。
  • 一旦运行,如果应用程序失去与目标数据库的连接,它将不会尝试重新连接,您必须停止并重新启动整个grails应用程序。

  • 我们需要更强大的功能-仅在用户决定运行报告时才调用目标数据库-在应用启动时不运行目标数据库,当我们调用con = new Sql(datasource)时应尝试连接(或重新连接)。

    有什么想法可以实现吗?就是一种在运行时连接到aribtrary数据库的方法,向后拉一些行,如果到目标数据库的连接丢失,则重新建立,下次运行报表时它仍然可以工作。另外,如果在没有目标数据库的情况下启动了该应用程序,则该应用程序仍应启动,因为它在启动时不依赖它。

    谢谢,

    请您参考如下方法:

    您可能会考虑添加一些其他属性,以使其尝试重新连接。例如:

    dataSource_target { 
      dialect = org.hibernate.dialect.MySQLInnoDBDialect 
      pooled = true 
      jmxExport = true 
      driverClassName = "com.mysql.jdbc.Driver" 
      username = "bla" 
      password = "bla" 
      properties { 
        maxActive = -1 
        minEvictableIdleTimeMillis=1800000 
        timeBetweenEvictionRunsMillis=1800000 
        numTestsPerEvictionRun=3 
        testOnBorrow=true 
        testWhileIdle=true 
        testOnReturn=true 
        validationQuery="SELECT 1" 
      } 
    } 
    

    我建议您更改属性以适合您的需求。但是,这将无法解决启动应用程序时数据库不可用的问题。

    为了避免这种情况,您必须避免使用Grails数据源。在这种情况下,您需要在对数据库进行调用的服务中定义数据源。
    def db = [ 
      url:'jdbc:hsqldb:mem:testDB',  
      user:'sa',  
      password:'',  
      driver:'org.hsqldb.jdbc.JDBCDriver' 
    ] 
    def sql = Sql.newInstance(db.url, db.user, db.password, db.driver) 
    

    当然,请修改此设置以适合您的需求。您甚至可以从Config.groovy中提取这些设置,而不是对其进行硬编码(强烈建议)。


    评论关闭
    IT序号网

    微信公众号号:IT虾米 (左侧二维码扫一扫)欢迎添加!