Come registrare le istruzioni SQL in Grails

Voglio accedere alla console o in un file, tutte le query che Grails fa, per verificare le prestazioni.

L’avevo configurato senza successo.

Qualsiasi idea potrebbe aiutare.

Ambientazione

datasource { ... logSql = true } 

in DataSource.groovy (come da queste istruzioni) è stato sufficiente per farlo funzionare nel mio ambiente. Sembra che parti delle FAQ non siano aggiornate (ad es. “La domanda molte colonne all’indietro”) quindi questo potrebbe anche essere qualcosa che è cambiato nel frattempo.

Trovo più utile eseguire quanto segue, ovvero abilitare la registrazione di Hibernate per registrare l’SQL insieme alle variabili di binding (in modo da poter vedere i valori passati nelle chiamate e replicare facilmente l’SQL nel proprio editor o in altro modo).

Nel tuo Config.groovy , aggiungi quanto segue al tuo blocco log4j:

 log4j = { // Enable Hibernate SQL logging with param values trace 'org.hibernate.type' debug 'org.hibernate.SQL' //the rest of your logging config // ... } 

Per i graal 3. *

Opzione # 1 aggiungere quanto segue a logback.groovy

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

o

L’opzione n. 2 aggiunge quanto segue a dataSource nel file application.yml. Tuttavia questo approccio non registra i valori dei parametri

 environments: local: dataSource: logSql: true formatSql: true 

Prova questo:

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

Evita i problemi di prestazioni della traccia di registrazione del pacchetto di type Hibernate. Funziona con Hibernate 3.6 e versioni successive. L’ho preso da: https://burtbeckwith.com/blog/?p=1604

La soluzione è solo per lo sviluppo, non per la produzione.

Tutte le risposte sopra funzionano e sono corrette. Ma non mostrano la query completa in un modo umano leggibile. Se vuoi vedere la query finale (senza nessuna?,?) Hai due opzioni.

A) proxy la tua connessione jdbc con log4jdbc o p6Spy.

B) guardalo a livello di database. Ad esempio, davvero facile da fare con mysql.

Scopri dove si trova general_log_file. Registro generale attivo se non è già stato triggersto.

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

Ora tutto è registrato nel tuo log file. Esempio di Mac / Linux per mostrare un bel stream di query.

 tail -f path_to_log_file 

Pure solo per riferimento, ma io uso p6spy per registrare le query SQL. È un piccolo driver jdbc intermedio. La query esatta viene registrata come verrebbe inviata al server (con i parametri inclusi).

includilo nel tuo progetto:

 runtime 'p6spy:p6spy:3.0.0' 

Cambia il tuo driver di origine dati:

 driverClassName: com.p6spy.engine.spy.P6SpyDriver 

E il tuo jdbc url:

 url: jdbc:p6spy:mysql:// 

Configuralo usando spy.properties (in 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 

Non dimenticare di disabilitare questo per la produzione!

So che questo è stato chiesto e ho risposto a lungo. Ma mi è capitato di vedere questa domanda e non potevo impedirmi di rispondere o condividere il nostro approccio di implementazione del logging sql nel nostro progetto. Spero che sia di qualche aiuto.

Attualmente è in ambiente di sviluppo. Stiamo usando “log4jdbc Driver Spy” per registrare sql.

Configurazione:

In BuildConfig.groovy: aggiungi dipendenze sottostanti:

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

E nella tua DataSource o altra configurazione correlata: [ovunque tu abbia definito la configurazione relativa all’origine dati], Aggiungi:

 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' } 

Dalla mia esperienza personale l’ho trovato abbastanza utile e utile durante il debug. Inoltre ulteriori informazioni che puoi trovare in questo sito. https://code.google.com/p/log4jdbc-remix/

Re saluti

Per un particolare blocco di codice possiamo anche creare un metodo che accetta una chiusura. per esempio.

  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")} 

Se hai installato il plugin per la console , puoi ottenere la registrazione di sql con questo piccolo frammento di codice.

 ctx.sessionFactory.settings.sqlStatementLogger.logToStdout = true try {  } finally { ctx.sessionFactory.settings.sqlStatementLogger.logToStdout = false } 

Questa è una variazione su molte delle soluzioni precedenti, ma consente di modificare il valore in fase di esecuzione. E proprio come le altre soluzioni che si occupano di logToStdout mostra solo le query e non i valori di bind.

L'idea è stata rubata da un burtbeckwith post che ho letto alcuni anni fa e che non riesco a trovare in questo momento.

Una tecnica simile può essere utilizzata per triggersre la registrazione per test di integrazione specifici:

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

Ciò accenderà la registrazione sql solo per i test in questo unico file.