Como registrar instruções SQL no Spring Boot?

342

Eu quero registrar instruções SQL em um arquivo.
Eu tenho as seguintes propriedades emapplication.properties

spring.datasource.url=...
spring.datasource.username=user
spring.datasource.password=1234
spring.datasource.driver-class-name=net.sourceforge.jtds.jdbc.Driver

spring.jpa.show-sql=true
spring.jpa.properties.hibernate.format_sql=true

security.ignored=true
security.basic.enabled=false

logging.level.org.springframework.web=INFO
logging.level.org.hibernate=INFO
logging.file=c:/temp/my-log/app.log

Quando executo meu aplicativo

cmd>mvn spring-boot:run

Eu posso ver instruções sql no console, mas elas não aparecem em um arquivo app.log. O arquivo contém apenas logs básicos da primavera.

O que devo fazer para ver as instruções sql no arquivo de log?

Oleg Pavliv
fonte

Respostas:

458

tente usar isso no seu arquivo de propriedades:

logging.level.org.hibernate.SQL=DEBUG
logging.level.org.hibernate.type.descriptor.sql.BasicBinder=TRACE
Paul Woods
fonte
74
Se você também deseja registrar valores:logging.level.org.hibernate.type=TRACE
elysch
2
Mas isso registra apenas alguns valores de ligação. Como posso registrar valores da API de critérios? Se eu usar as Especificações, não receberei saída para os parâmetros vinculados criados com o CriteriaBuilder.
21716 Josh
204

Isso também funciona para o stdout:

spring.jpa.properties.hibernate.show_sql=true
spring.jpa.properties.hibernate.use_sql_comments=true
spring.jpa.properties.hibernate.format_sql=true

Para registrar valores:

logging.level.org.hibernate.type=trace

Basta adicionar isso a application.properties.

v.ladynev
fonte
11
Se você também deseja registrar valores:spring.jpa.properties.hibernate.type=trace
elysch
11
Isso não escrever no arquivo de log, este escreve para STDOUT
Muhammad Hewedy
4
Eu ainda vejo apenas em ?vez dos parâmetros. Essa solução deveria mostrar para mim?
21818 Adeynack
11
spring.jpa.properties.hibernate.type = trace não afeta meu arquivo de log; (
gstackoverflow 4/18
11
O "type = trace" não é uma propriedade spring, portanto não funciona. A solução apresentada abaixo stackoverflow.com/a/41594913/5107365 é a solução certa para isso.
Raj
97

Isso funciona para mim (YAML):

spring:
  jpa:
    properties:
      hibernate:
        show_sql: true
        format_sql: true
logging:
  level:
    org:
      hibernate:
        type: trace
Michel
fonte
18

Por favor, use:

logging.level.org.hibernate.SQL=DEBUG
logging.level.org.hibernate.type=TRACE
spring.jpa.show-sql=true
rahulnikhare
fonte
4
logging.level.org.hibernate.SQL=DEBUGfez funcionar para mim e estava faltando outras respostas. Obrigado!
27419 Vic
18

se você possui um logback-spring.xml ou algo parecido, adicione o seguinte código a ele

<logger name="org.hibernate.SQL" level="trace" additivity="false">
    <appender-ref ref="file" />
</logger>

funciona para mim.

Para obter variáveis ​​de ligação também:

<logger name="org.hibernate.type.descriptor.sql" level="trace">
    <appender-ref ref="file" />
</logger>
Edye Chan
fonte
11
Com Primavera Bota você tem que usar<appender-ref ref="FILE" />
Ortomala Lokni
appender ref é o nome do appender que você definiu no xml de logback. É apenas uma variável
Raja Anbazhagan
17

Como essa é uma pergunta muito comum, escrevi este artigo , no qual essa resposta se baseia.

Configurações a serem evitadas

Você não deve usar esta configuração:

spring.jpa.show-sql=true 

O problema show-sqlé que as instruções SQL são impressas no console, portanto não há como filtrá-las, como faria normalmente com uma estrutura de Log.

Usando o log do Hibernate

No seu arquivo de configuração de log, se você adicionar o seguinte criador de logs:

<logger name="org.hibernate.SQL" level="debug"/>

Em seguida, o Hibernate imprimirá as instruções SQL quando o JDBC PreparedStatementfor criado. É por isso que a instrução será registrada usando espaços reservados para parâmetros:

INSERT INTO post (title, version, id) VALUES (?, ?, ?)

Se você deseja registrar os valores dos parâmetros de ligação, adicione também o seguinte criador de logs:

<logger name="org.hibernate.type.descriptor.sql.BasicBinder" level="trace"/>

Depois de definir o BasicBindercriador de logs, você verá que os valores dos parâmetros de vinculação também são registrados:

DEBUG [main]: o.h.SQL - insert into post (title, version, id) values (?, ?, ?)
TRACE [main]: o.h.t.d.s.BasicBinder - binding parameter [1] as [VARCHAR] - [High-Performance Java Persistence, part 1]
TRACE [main]: o.h.t.d.s.BasicBinder - binding parameter [2] as [INTEGER] - [0]
TRACE [main]: o.h.t.d.s.BasicBinder - binding parameter [3] as [BIGINT] - [1]

Usando proxy de fonte de dados

O datasource-proxy permite proxy do JDBC real DataSource, conforme ilustrado pelo diagrama a seguir:

DataSource-Proxy

Você pode definir o dataSourcebean que será usado pelo Hibernate da seguinte maneira:

@Bean
public DataSource dataSource(DataSource actualDataSource) {
    SLF4JQueryLoggingListener loggingListener = new SLF4JQueryLoggingListener();
    loggingListener.setQueryLogEntryCreator(new InlineQueryLogEntryCreator());
    return ProxyDataSourceBuilder
        .create(actualDataSource)
        .name(DATA_SOURCE_PROXY_NAME)
        .listener(loggingListener)
        .build();
}

Observe que actualDataSourcedeve ser o DataSourcedefinido pelo pool de conexões que você está usando em seu aplicativo.

Depois de ativar datasource-proxy, a instrução SQl será registrada da seguinte maneira:

Name:DATA_SOURCE_PROXY, Time:6, Success:True,
Type:Prepared, Batch:True, QuerySize:1, BatchSize:3,
Query:["insert into post (title, version, id) values (?, ?, ?)"],
Params:[(Post no. 0, 0, 0), (Post no. 1, 0, 1), (Post no. 2, 0, 2)]
Vlad Mihalcea
fonte
11

Para o driver do servidor MS-SQL (Driver JDBC do Microsoft SQL Server).

tente usar:

logging.level.com.microsoft.sqlserver.jdbc=debug

no seu arquivo application.properties.

Minha preferência pessoal é definir:

logging.level.com.microsoft.sqlserver.jdbc=info
logging.level.com.microsoft.sqlserver.jdbc.internals=debug

Você pode consultar estes links para referência:

Javier Z.
fonte
8

De acordo com a documentação , é:

spring.jpa.show-sql=true # Enable logging of SQL statements.
Max Farsikov
fonte
Eu tenho problema inverso, definir este como falsa, e org.hibernate a erro nível e sua queda ainda impressão / criar / inserir / select
Kalpesh Soni
5

A resposta traduzida aceita para o YAML funciona para mim

logging:
  level:
    org:
      hibernate:
        SQL:
          TRACE
        type:
          descriptor:
            sql:
              BasicBinder:
                TRACE
Robert.Li
fonte
3
Você também pode usar propriedades simples no YAML se não desejar aninhar objetos de uso único, como: logging.level.org.hibernate.SQL: TRACE logging.level.org.hibernate.type.descriptor.sql.BasicBinder: TRACE
MarcinJ
4

Podemos usar qualquer um deles no arquivo application.properties :

spring.jpa.show-sql=true 

example :
//Hibernate: select country0_.id as id1_0_, country0_.name as name2_0_ from country country0_

ou

logging.level.org.hibernate.SQL=debug 

example :
2018-11-23 12:28:02.990 DEBUG 12972 --- [nio-8086-exec-2] org.hibernate.SQL   : select country0_.id as id1_0_, country0_.name as name2_0_ from country country0_
Lova Chittumuri
fonte
3

Se você deseja visualizar os parâmetros reais usados ​​para consultar, pode usar

logging.level.org.hibernate.SQL=DEBUG
logging.level.org.hibernate.type.descriptor.sql=TRACE

Observe que o valor real do parâmetro é mostrado como binding parameter......

   2018-08-07 14:14:36.079 DEBUG 44804 --- [           main] org.hibernate.SQL                        : select employee0_.id as id1_0_, employee0_.department as departme2_0_, employee0_.joining_date as joining_3_0_, employee0_.name as name4_0_ from employee employee0_ where employee0_.joining_date=?
    2018-08-07 14:14:36.079 TRACE 44804 --- [           main] o.h.type.descriptor.sql.BasicBinder      : binding parameter [1] as [TIMESTAMP] - [Tue Aug 07 00:00:00 SGT 2018]
Udara SS Liyanage
fonte
3

Efetue login na saída padrão

adicionar à application.properties

### to enable
spring.jpa.show-sql=true
### to make the printing SQL beautify
spring.jpa.properties.hibernate.format_sql=true

Essa é a maneira mais simples de imprimir as consultas SQL, embora não registre os parâmetros das instruções preparadas. E isso não é recomendado, pois não é como a estrutura de log otimizada.

Usando a estrutura de log

adicionar à application.properties

### logs the SQL queries
logging.level.org.hibernate.SQL=DEBUG
### logs the prepared statement parameters
logging.level.org.hibernate.type.descriptor.sql.BasicBinder=TRACE
### to make the printing SQL beautify
spring.jpa.properties.hibernate.format_sql=true

Ao especificar as propriedades acima, as entradas dos logs serão enviadas para o aplicativo de log configurado, como log-back ou log4j.

Saveendra Ekanayake
fonte
0

Se você está tendo problemas com essa configuração e ela parece funcionar algumas vezes e não outras - considere se os horários em que não funciona são durante testes de unidade.

Muitas pessoas declaram propriedades personalizadas de tempo de teste por meio da @TestPropertySourcesanotação declarada em algum lugar da hierarquia de herança de teste. Isso substituirá o que você colocar nas suas application.propertiesou em outras configurações de propriedades de produção, para que esses valores sejam efetivamente ignorados no momento do teste.

Shorn
fonte
0

Colocando spring.jpa.properties.hibernate.show_sql=true application.properties nem sempre ajudou.

Você pode tentar adicionar properties.put("hibernate.show_sql", "true");às propriedades da configuração do banco de dados.

public class DbConfig {

    @Primary
    @Bean(name = "entityManagerFactory")
    public LocalContainerEntityManagerFactoryBean
    entityManagerFactory(
            EntityManagerFactoryBuilder builder,
            @Qualifier("dataSource") DataSource dataSource
    ) {
        Map<String, Object> properties = new HashMap();
        properties.put("hibernate.hbm2ddl.auto", "validate");
        properties.put("hibernate.show_sql", "true");

        return builder
                .dataSource(dataSource)
                .packages("com.test.dbsource.domain")
                .persistenceUnit("dbsource").properties(properties)
                .build();
    }
SJX
fonte