代码之家  ›  专栏  ›  技术社区  ›  user2427

如何在Grails中记录SQL语句

  •  78
  • user2427  · 技术社区  · 15 年前

    我想登录控制台或文件,Grails做的所有查询,以检查性能。

    我已经配置了 this 没有成功。

    任何想法都会有帮助。

    10 回复  |  直到 6 年前
        1
  •  125
  •   Tomislav Nakic-Alfirevic    7 年前

    设置

    datasource {
    ...
    logSql = true
    }
    

    在datasource.groovy中(根据 these 说明)足以让它在我的环境中工作。FAQ的某些部分似乎已经过时了(例如,“多到多栏向后”的问题),因此这也可能是同时发生变化的问题。

        2
  •  89
  •   aldrin    9 年前

    我发现执行以下操作更有用,即启用Hibernate的日志记录SQL和绑定变量(这样您就可以看到传递到调用中的值,并且可以在编辑器中轻松地复制SQL或其他)。

    在你的 Config.groovy ,将以下内容添加到您的log4j块中:

    log4j = {
    
        // Enable Hibernate SQL logging with param values
        trace 'org.hibernate.type'
        debug 'org.hibernate.SQL'
        //the rest of your logging config
        // ...
        }
    
        3
  •  31
  •   Robert Hutto    10 年前

    对于GRASES 3

    选项1将以下内容添加到logback.groovy

    logger("org.hibernate.SQL", DEBUG, ["STDOUT"], false)
    logger("org.hibernate.type.descriptor.sql.BasicBinder", TRACE, ["STDOUT"], false)
    

    选项2将以下内容添加到application.yml中的数据源。但是,此方法不记录参数值

    environments:
      local:
        dataSource:
            logSql: true
            formatSql: true
    
        4
  •  17
  •   Jason    11 年前

    试试这个:

    log4j = {
       ...
       debug 'org.hibernate.SQL'
       trace 'org.hibernate.type.descriptor.sql.BasicBinder'
    }
    

    它避免了跟踪记录休眠的性能问题 type 包裹。适用于Hibernate 3.6及更高版本。我是从以下地方得到的: https://burtbeckwith.com/blog/?p=1604

        5
  •  5
  •   Wuestenfuchs    11 年前

    解决方案只用于开发,而不是生产。

    以上答案都是正确的。但它们并没有以一种人类可读的方式显示完整的查询。如果想看决赛(没有??)查询您有两个选项。

    a)使用log4jdbc或p6spy代理JDBC连接。

    b)在数据库级别查看它。例如,使用MySQL非常容易。

    找出您的常规日志文件在哪里。如果没有激活,则激活常规日志。

    mysql command line> show variables like "%general_log%";
    mysql command line> set global general_log = true;
    

    现在一切都记录到日志文件中。mac/linux示例显示了您的查询流。

    tail -f path_to_log_file 
    
        6
  •  3
  •   Dennie de Lange    8 年前

    仅供参考,但我使用p6spy记录SQL查询。它是一个小型的中间JDBC驱动程序。准确的查询会被记录下来,因为它将被发送到服务器(包括参数)。

    将其包含在项目中:

    runtime 'p6spy:p6spy:3.0.0'
    

    更改数据源驱动程序:

    driverClassName: com.p6spy.engine.spy.P6SpyDriver
    

    您的JDBC URL:

    url: jdbc:p6spy:mysql://
    

    使用spy.properties配置它(在grails app/conf中)。

    driverlist=org.h2.Driver,com.mysql.jdbc.Driver
    autoflush=true
    appender=com.p6spy.engine.spy.appender.StdoutLogger
    databaseDialectDateFormat=yyyy-MM-dd
    logMessageFormat=com.p6spy.engine.spy.appender.MultiLineFormat
    

    别忘了在生产中禁用它!

        7
  •  1
  •   Madhu Bose    10 年前

    我知道这是很久以前被问过和回答过的,但我恰好看到了这个问题,我无法停止自己在我们的项目中回答或共享我们的SQL日志实现方法。 希望能有所帮助。

    目前处于开发环境中。 我们使用“log4jdbc driver spy”来记录SQL。

    配置:

    在buildconfig.groovy中: 添加以下依赖项:

    dependencies {
    .....
    runtime 'org.lazyluke:log4jdbc-remix:0.2.7'
    }
    

    以及在与数据源或其他配置相关的[无论您在何处定义了与数据源相关的配置], 添加:

    datasources{
    .....
    driverClassName: "net.sf.log4jdbc.DriverSpy",
    url: "jdbc:log4jdbc:oracle:thin:@(DESCRIPTION =(ADDRESS_LIST = (ADDRESS = (PROTOCOL = TCP)(HOST = XXXXX.XX>XXX)(PORT = 1521))) (CONNECT_DATA = (SID = XXXX)(SERVER =DEDICATED)))",
    ....
    }
    log4j = {
    
        info 'jdbc.sqlonly' //, 'jdbc.resultsettable'
    
    }
    

    根据我的个人经验,我发现它在调试时非常有用和有用。 您还可以在此网站中找到更多信息。 https://code.google.com/p/log4jdbc-remix/

    国王的问候

        8
  •  0
  •   user3180264    9 年前

    对于特定的代码块,我们还可以创建一个接受闭包的方法。如。

     static def executeBlockAndGenerateSqlLogs(Closure closure) {
        Logger sqlLogger = Logger.getLogger("org.hibernate.SQL");
        Level currentLevel = sqlLogger.level
        sqlLogger.setLevel(Level.TRACE)
        def result = closure.call()
        sqlLogger.setLevel(currentLevel)
        result }
    
    executeBlockAndGenerateSqlLogs{DomainClazz.findByPropertyName("property value")}
    
        9
  •  0
  •   burns    6 年前

    如果你有 console 插件已安装,您可以使用这个小代码段获取SQL日志记录。

    // grails 2.3
    def logger=ctx.sessionFactory.settings.sqlStatementLogger
    
    // grails 3.3  
    def logger = ctx.sessionFactory.currentSession.jdbcCoordinator.statementPreparer.jdbcService.sqlStatementLogger
    
    logger.logToStdout=true    
    try {
       <code that will log sql queries>
    }
    finally {
        logToStdout = false
    }
    

    这是上面许多解决方案的变体,但允许您在运行时调整值。就像其他解决方案一样 logToStdout 它只显示查询,不显示绑定值。

    这个想法是从几年前我读到的一篇博贝克的文章中偷来的,现在我找不到。它已经被编辑为与Grails3.3一起工作。

    可以使用类似的技术打开特定集成测试的日志记录:

    class SomeIntegrationSpec extends IntegrationSpec {
    
        def sessionFactory
    
        def setup() {
            sessionFactory.settings.sqlStatementLogger.logToStdout = true
        }
    
        def cleanup() {
            sessionFactory.settings.sqlStatementLogger.logToStdout = false
        }
    
        void "some test"() {
               ...
        }
    

    这将只为这个文件中的测试打开SQL日志记录。

        10
  •  0
  •   Eduardo Cuomo Sajjad Ali Khan    6 年前

    下一个适合我:

    Grails应用程序/conf/application.yml

    # ...
    hibernate:
        format_sql: true # <<<<<<< ADD THIS <<<<<<<
        cache:
            queries: false
            use_second_level_cache: true
    # ...
    environments:
        development:
            dataSource:
                logSql: true // <<<<<<< ADD THIS <<<<<<<
                dbCreate: create-drop
                url: jdbc:h2:mem:...
    # ...
    

    grails应用程序/conf/logback.groovy

    // ...
    appender('STDOUT', ConsoleAppender) {
        encoder(PatternLayoutEncoder) {
            pattern = "%level %logger - %msg%n"
        }
    }
    
    // >>>>>>> ADD IT >>>>>>>
    logger 'org.hibernate.type.descriptor.sql.BasicBinder', TRACE, ['STDOUT']
    logger 'org.hibernate.SQL', TRACE, ['STDOUT']
    // <<<<<<< ADD IT <<<<<<<
    
    root(ERROR, ['STDOUT'])
    
    def targetDir = BuildSettings.TARGET_DIR
    // ...
    

    来源: http://sergiodelamo.es/log-sql-grails-3-app/