Cara mencetak string kueri dengan nilai parameter saat menggunakan Hibernate


Jawaban:


428

Anda harus mengaktifkan pencatatan untuk kategori berikut:

  • org.hibernate.SQL   - atur untuk debugmencatat semua pernyataan SQL DML saat dieksekusi
  • org.hibernate.type- atur untuk tracemencatat semua parameter JDBC

Jadi konfigurasi log4j dapat terlihat seperti:

# logs the SQL statements
log4j.logger.org.hibernate.SQL=debug 

# Logs the JDBC parameters passed to a query
log4j.logger.org.hibernate.type=trace 

Yang pertama setara dengan propertihibernate.show_sql=true lawas , yang kedua mencetak parameter yang terikat di antara hal-hal lain.

Solusi lain (berbasis non hibernasi) adalah menggunakan driver proxy JDBC seperti P6Spy .


11
Ini bermanfaat. Tapi ini tidak menunjukkan pertanyaan SQL yang sebenarnya.
Nicolas Barbulesco

6
@ Nicolas itu benar, namun segera setelah permintaan itu membayar parameter yang diikat.
Xtreme Biker

2
Saya menggunakan grails 2.4.4 dan hibernate 4. Mengubah konfigurasi log4j tidak bekerja untuk saya tetapi p6spy bekerja!
Champ

11
Di Hibernate 5 kita bisa menggunakan org.hibernate.type.descriptor.sql.BasicBinderlogger. Mengaktifkan pencatatan pada org.hibernate.typeinfo terlalu banyak yang tidak berguna bagi saya ...
csharpfolk

5
org.hibernate.typedan org.hibernate.loader.hqltidak bekerja bagi saya untuk menunjukkan parameter
Dherik

75

Hanya untuk kenyamanan, berikut adalah contoh konfigurasi yang sama untuk Logback (SLF4J)

<appender name="SQLROLLINGFILE">
 <File>/tmp/sql.log</File>
 <rollingPolicy>
  <FileNamePattern>logFile.%d{yyyy-MM-dd}.log</FileNamePattern>
 </rollingPolicy>
 <layout>
  <Pattern>%-4date | %msg %n</Pattern>
 </layout>
</appender>

<logger name="org.hibernate.SQL" additivity="false" >   
 <level value="DEBUG" />    
 <appender-ref ref="SQLROLLINGFILE" />
</logger>

<logger name="org.hibernate.type" additivity="false" >
 <level value="TRACE" />
 <appender-ref ref="SQLROLLINGFILE" />
</logger>

Output di sql.log Anda (contoh) kemudian terlihat seperti ini:

2013-08-30 18:01:15,083 | update stepprovider set created_at=?, lastupdated_at=?, version=?, bundlelocation=?, category_id=?, customer_id=?, description=?, icon_file_id=?, name=?, shareStatus=?, spversion=?, status=?, title=?, type=?, num_used=? where id=?
2013-08-30 18:01:15,084 | binding parameter [1] as [TIMESTAMP] - 2012-07-11 09:57:32.0
2013-08-30 18:01:15,085 | binding parameter [2] as [TIMESTAMP] - Fri Aug 30 18:01:15 CEST 2013
2013-08-30 18:01:15,086 | binding parameter [3] as [INTEGER] -
2013-08-30 18:01:15,086 | binding parameter [4] as [VARCHAR] - com.mypackage.foo
2013-08-30 18:01:15,087 | binding parameter [5] as [VARCHAR] -
2013-08-30 18:01:15,087 | binding parameter [6] as [VARCHAR] -
2013-08-30 18:01:15,087 | binding parameter [7] as [VARCHAR] - TODO
2013-08-30 18:01:15,087 | binding parameter [8] as [VARCHAR] -
2013-08-30 18:01:15,088 | binding parameter [9] as [VARCHAR] - MatchingStep@com.mypackage.foo
2013-08-30 18:01:15,088 | binding parameter [10] as [VARCHAR] - PRIVATE
2013-08-30 18:01:15,088 | binding parameter [11] as [VARCHAR] - 1.0
2013-08-30 18:01:15,088 | binding parameter [12] as [VARCHAR] - 32
2013-08-30 18:01:15,088 | binding parameter [13] as [VARCHAR] - MatchingStep
2013-08-30 18:01:15,089 | binding parameter [14] as [VARCHAR] -
2013-08-30 18:01:15,089 | binding parameter [15] as [INTEGER] - 0
2013-08-30 18:01:15,089 | binding parameter [16] as [VARCHAR] - 053c2e65-5d51-4c09-85f3-2281a1024f64

2
Ini tidak menjawab pertanyaan OP.
ShadowGames

33

Ubah hibernate.cfg.xmlke:

<property name="show_sql">true</property>
<property name="format_sql">true</property>
<property name="use_sql_comments">true</property>

Sertakan log4j dan entri di bawah ini di "log4j.properties":

log4j.logger.org.hibernate=INFO, hb
log4j.logger.org.hibernate.SQL=DEBUG
log4j.logger.org.hibernate.type=TRACE

log4j.appender.hb=org.apache.log4j.ConsoleAppender
log4j.appender.hb.layout=org.apache.log4j.PatternLayout

Terima kasih, telah bekerja dengan baik untuk saya. Pengaturan itu akan menambahkan di bawah sql query parameter seperti binding parameter [1] as [VARCHAR] - [1].
G. Ciardini

28

Jika spring boot digunakan, konfigurasikan ini:

aplication.yml

logging:
  level:
    org.hibernate.SQL: DEBUG
    org.hibernate.type: TRACE

aplication.properties

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

dan tidak ada lagi.

HTH


20

Log4JDBC adalah solusi bagus yang mencetak SQL yang tepat pergi ke database dengan parameter di tempat daripada jawaban paling populer di sini yang tidak melakukan ini. Satu kemudahan utama dari ini adalah Anda dapat menyalin SQL langsung ke front-end DB Anda dan mengeksekusi apa adanya.

http://log4jdbc.sourceforge.net/

https://code.google.com/p/log4jdbc-remix/

Yang terakhir juga menampilkan representasi tabular dari hasil kueri.

Contoh Output menunjukkan SQL yang dihasilkan dengan params di tempat bersama dengan tabel set hasil dari kueri:

5. insert into ENQUIRY_APPLICANT_DETAILS (ID, INCLUDED_IN_QUOTE, APPLICANT_ID, TERRITORY_ID, ENQUIRY_ID, ELIGIBLE_FOR_COVER) values (7, 1, 11, 1, 2, 0) 


10 Oct 2013 16:21:22 4953 [main] INFO  jdbc.resultsettable  - |---|--------|--------|-----------|----------|---------|-------|
10 Oct 2013 16:21:22 4953 [main] INFO  jdbc.resultsettable  - |ID |CREATED |DELETED |CODESET_ID |NAME      |POSITION |PREFIX |
10 Oct 2013 16:21:22 4953 [main] INFO  jdbc.resultsettable  - |---|--------|--------|-----------|----------|---------|-------|
10 Oct 2013 16:21:22 4953 [main] INFO  jdbc.resultsettable  - |2  |null    |null    |1          |Country 2 |1        |60     |
10 Oct 2013 16:21:22 4953 [main] INFO  jdbc.resultsettable  - |---|--------|--------|-----------|----------|---------|-------|

Perbarui 2016

Baru-baru ini saya sekarang menggunakan log4jdbc-log4j2 ( https://code.google.com/archive/p/log4jdbc-log4j2/ ) dengan SLF4j dan logback. Ketergantungan maven yang diperlukan untuk pengaturan saya adalah sebagai berikut:

<dependency>
    <groupId>org.bgee.log4jdbc-log4j2</groupId>
    <artifactId>log4jdbc-log4j2-jdbc4.1</artifactId>
    <version>1.16</version>
</dependency>
<dependency>
    <groupId>org.slf4j</groupId>
    <artifactId>slf4j-api</artifactId>
    <version>${slf4j.version}</version>
</dependency>
<dependency>
    <groupId>ch.qos.logback</groupId>
    <artifactId>logback-core</artifactId>
    <version>${logback.version}</version>
</dependency>
<dependency>
    <groupId>ch.qos.logback</groupId>
    <artifactId>logback-classic</artifactId>
    <version>$logback.version}</version>
</dependency>

Url Driver dan DB kemudian terlihat seperti:

database.driver.class=net.sf.log4jdbc.sql.jdbcapi.DriverSpy
database.url=jdbc:log4jdbc:hsqldb:mem:db_name #Hsql
#database.url=jdbc:log4jdbc:mysql://localhost:3306/db_name 

File konfigurasi logback.xml saya terlihat seperti di bawah ini: ini menampilkan semua pernyataan SQL dengan parameter plus tabel resultset untuk semua permintaan.

<?xml version="1.0" encoding="UTF-8"?>
<configuration>

    <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
        <encoder>
            <pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
            </pattern>
        </encoder>
    </appender>

    <logger name="jdbc.audit" level="ERROR" />
    <logger name="jdbc.connection" level="ERROR" />
    <logger name="jdbc.sqltiming" level="ERROR" />
    <logger name="jdbc.resultset" level="ERROR" />

    <!-- UNCOMMENT THE BELOW TO HIDE THE RESULT SET TABLE OUTPUT -->
    <!--<logger name="jdbc.resultsettable" level="ERROR" /> -->

    <root level="debug">
        <appender-ref ref="STDOUT" />
    </root>
</configuration>

Akhirnya, saya harus membuat file bernama log4jdbc.log4j2.properties di root classpath misalnya src / test / resources atau src / main / resources dalam proyek Mevn. File ini memiliki satu baris yaitu di bawah ini:

log4jdbc.spylogdelegator.name=net.sf.log4jdbc.log.slf4j.Slf4jSpyLogDelegator

Di atas akan tergantung pada perpustakaan logging Anda. Lihat dokumen di https://code.google.com/archive/p/log4jdbc-log4j2 untuk info lebih lanjut

Output sampel:

10:44:29.400 [main] DEBUG jdbc.sqlonly -  org.hibernate.engine.jdbc.internal.ResultSetReturnImpl.extract(ResultSetReturnImpl.java:70)
5. select memberrole0_.member_id as member_i2_12_0_, memberrole0_.id as id1_12_0_, memberrole0_.id 
as id1_12_1_, memberrole0_.member_id as member_i2_12_1_, memberrole0_.role_id as role_id3_12_1_, 
role1_.id as id1_17_2_, role1_.name as name2_17_2_ from member_roles memberrole0_ left outer 
join roles role1_ on memberrole0_.role_id=role1_.id where memberrole0_.member_id=104 

10:44:29.402 [main] INFO  jdbc.resultsettable - 
|----------|---|---|----------|--------|---|-----|
|member_id |id |id |member_id |role_id |id |name |
|----------|---|---|----------|--------|---|-----|
|----------|---|---|----------|--------|---|-----|

1
Hei .... Ini sepertinya keren .... hanya apa yang diperintahkan dokter untukku :) ... tetapi apakah itu juga mendukung CLOB / BLOB ?? Juga, apakah mungkin untuk hanya menampilkan kueri dan bukan hasil yang ditetapkan. - Terima kasih :)
dev ray

1
dapatkah Anda memberi saya contoh konfigurasi bagaimana melakukan itu?
grep

Sebenarnya, yang terakhir menampilkan representasi tabluar dari hasil permintaan ... yaitu kita perlu log4jdbc-remix untuk fitur yang bagus itu.
meriton

Solusi ini terbaik untuk situasi saya di mana saya perlu melihat nilai-nilai nomor baris yang dihasilkan Hibernate untuk kumpulan hasil paging. Pencatatan jejak hanya menunjukkan nilai parameter kueri.
Oliver Hernandez

@ Alan Hay, apakah ini mencatat pertanyaan asli juga?
Sayantan

9

Anda dapat menambahkan baris kategori ke log4j.xml:

<category name="org.hibernate.type">
    <priority value="TRACE"/>
</category>

dan tambahkan properti hibernasi:

<property name="show_sql">true</property>
<property name="format_sql">true</property>
<property name="use_sql_comments">true</property>

7

tambahkan properti dan nilai berikut ke konfigurasi log4j atau logback Anda:

org.hibernate.sql=DEBUG
org.hibernate.type.descriptor.sql.BasicBinder=TRACE

5
The org.hibernate.type.descriptor.sql.BasicBinderkategori tidak mencakup semua parameter, misalnya jenis enum. Jadi, jika Anda menginginkan semuanya, Anda benar-benar perlu TRACEuntuk seluruh org.hibernate.typekelompok.
seanf

Bagi saya ini berfungsi di Hibernate 4.3! Plus, saya tidak akan MELAKUKAN org.hibernate.type penuh, karena itu terlalu banyak output. Dalam kebanyakan kasus, solusi ini akan berhasil.
cslotty

Perhatikan bahwa org.hibernate.type.descriptor.sql.BasicExtractor mencatat set hasil. Jadi memiliki entri ukuran besar bahkan dapat menghentikan aplikasi saat masuk ke konsol di Eclipse, dan saya kira itu juga tidak ideal untuk masuk ke file. Itu sebabnya saya lebih suka solusi ini, ini juga berfungsi di Hibernate 3. Bagi mereka yang tertarik pada tipe enum, silakan coba kelas yang tepat yang mencatatnya ketika org.hibernate.type = TRACE. Kemudian atur org.hibernate.type.xyz.TheClassThatLogsEnumParams = TRACE.
Géza

7

Anda dapat melakukannya dengan menggunakan sumber data-proxy , seperti yang saya jelaskan di posting ini .

Dengan asumsi aplikasi Anda mengharapkan dataSourcekacang (mis. Via @Resource), ini adalah bagaimana Anda dapat mengonfigurasi datasource-proxy:

<bean id="actualDataSource" class="bitronix.tm.resource.jdbc.PoolingDataSource" init-method="init"
  destroy-method="close">
    <property name="className" value="bitronix.tm.resource.jdbc.lrc.LrcXADataSource"/>
    <property name="uniqueName" value="actualDataSource"/>
    <property name="minPoolSize" value="0"/>
    <property name="maxPoolSize" value="5"/>
    <property name="allowLocalTransactions" value="false" />
    <property name="driverProperties">
        <props>
            <prop key="user">${jdbc.username}</prop>
            <prop key="password">${jdbc.password}</prop>
            <prop key="url">${jdbc.url}</prop>
            <prop key="driverClassName">${jdbc.driverClassName}</prop>
        </props>
    </property>
</bean>

<bean id="proxyDataSource" class="net.ttddyy.dsproxy.support.ProxyDataSource">
    <property name="dataSource" ref="testDataSource"/>
    <property name="listener">
        <bean class="net.ttddyy.dsproxy.listener.ChainListener">
            <property name="listeners">
                <list>
                    <bean class="net.ttddyy.dsproxy.listener.CommonsQueryLoggingListener">
                        <property name="logLevel" value="INFO"/>
                    </bean>
                    <bean class="net.ttddyy.dsproxy.listener.DataSourceQueryCountListener"/>
                </list>
            </property>
        </bean>
    </property>
</bean>

<alias name="proxyDataSource" alias="dataSource"/>

Sekarang output Hibernate vs dataource-proxy:

INFO  [main]: n.t.d.l.CommonsQueryLoggingListener - Name:, Time:1, Num:1, Query:{[select company0_.id as id1_6_, company0_.name as name2_6_ from Company company0_][]}
INFO  [main]: n.t.d.l.CommonsQueryLoggingListener - Name:, Time:0, Num:1, Query:{[insert into WarehouseProductInfo (id, quantity) values (default, ?)][19]}
INFO  [main]: n.t.d.l.CommonsQueryLoggingListener - Name:, Time:0, Num:1, Query:{[insert into Product (id, code, company_id, importer_id, name, version) values (default, ?, ?, ?, ?, ?)][phoneCode,1,-5,Phone,0]}

The datasource-proxyquery mengandung nilai-nilai parameter dan Anda bahkan dapat menambahkan pencegat kustom pernyataan JDBC sehingga Anda dapat menangkap N + 1 masalah permintaan langsung dari tes integrasi Anda .


5

nyalakan org.hibernate.typeLogger untuk melihat bagaimana parameter aktual mengikat tanda tanya.


4

<!-- A time/date based rolling appender -->
<appender name="FILE" class="org.apache.log4j.RollingFileAppender">
    <param name="File" value="logs/system.log" />
    <param name="Append" value="true" />
    <param name="ImmediateFlush" value="true" />
    <param name="MaxFileSize" value="200MB" />
    <param name="MaxBackupIndex" value="100" />

    <layout class="org.apache.log4j.PatternLayout">
        <param name="ConversionPattern" value="%d %d{Z} [%t] %-5p (%F:%L) - %m%n" />
    </layout>
</appender>

<appender name="journaldev-hibernate" class="org.apache.log4j.RollingFileAppender">
    <param name="File" value="logs/project.log" />
    <param name="Append" value="true" />
    <param name="ImmediateFlush" value="true" />
    <param name="MaxFileSize" value="200MB" />
    <param name="MaxBackupIndex" value="50" />

    <layout class="org.apache.log4j.PatternLayout">
        <param name="ConversionPattern" value="%d %d{Z} [%t] %-5p (%F:%L) - %m%n" />
    </layout>
</appender>

<logger name="com.journaldev.hibernate" additivity="false">
    <level value="DEBUG" />
    <appender-ref ref="journaldev-hibernate" />
</logger>

<logger name="org.hibernate" additivity="false">
    <level value="INFO" />
    <appender-ref ref="FILE" />
</logger>

<logger name="org.hibernate.type" additivity="false">
    <level value="TRACE" />
    <appender-ref ref="FILE" />
</logger>

<root>
    <priority value="INFO"></priority>
    <appender-ref ref="FILE" />
</root>


3

Solusinya benar tetapi mencatat juga semua binding untuk objek hasil. Untuk mencegahnya, mungkin membuat append terpisah dan mengaktifkan penyaringan, misalnya:

<!-- A time/date based rolling appender -->
<appender name="FILE_HIBERNATE" class="org.jboss.logging.appender.DailyRollingFileAppender">
    <errorHandler class="org.jboss.logging.util.OnlyOnceErrorHandler"/>
    <param name="File" value="${jboss.server.log.dir}/hiber.log"/>
    <param name="Append" value="false"/>
    <param name="Threshold" value="TRACE"/>
    <!-- Rollover at midnight each day -->
    <param name="DatePattern" value="'.'yyyy-MM-dd"/>

    <layout class="org.apache.log4j.PatternLayout">
        <!-- The default pattern: Date Priority [Category] Message\n -->
        <param name="ConversionPattern" value="%d %-5p [%c] %m%n"/>
    </layout>

    <filter class="org.apache.log4j.varia.StringMatchFilter">
        <param name="StringToMatch" value="bind" />
        <param name="AcceptOnMatch" value="true" />
    </filter>
    <filter class="org.apache.log4j.varia.StringMatchFilter">
        <param name="StringToMatch" value="select" />
        <param name="AcceptOnMatch" value="true" />
    </filter>  
    <filter class="org.apache.log4j.varia.DenyAllFilter"/>
</appender> 

<category name="org.hibernate.type">
  <priority value="TRACE"/>
</category>

<logger name="org.hibernate.type">
   <level value="TRACE"/> 
   <appender-ref ref="FILE_HIBERNATE"/>
</logger>

<logger name="org.hibernate.SQL">
   <level value="TRACE"/> 
   <appender-ref ref="FILE_HIBERNATE"/>
</logger>

3
**If you want hibernate to print generated sql queries with real values instead of question marks.**
**add following entry in hibernate.cfg.xml/hibernate.properties:**
show_sql=true
format_sql=true
use_sql_comments=true

**And add following entry in log4j.properties :**
log4j.logger.org.hibernate=INFO, hb
log4j.logger.org.hibernate.SQL=DEBUG
log4j.logger.org.hibernate.type=TRACE
log4j.appender.hb=org.apache.log4j.ConsoleAppender
log4j.appender.hb.layout=org.apache.log4j.PatternLayout

Hai single31 baris di atas harus ditambahkan dalam file konfigurasi hibernate Anda maka pasti akan berfungsi. Saya selalu memposting hal yang telah saya lakukan secara praktis.
Vijay Bhatt

3

Jawaban ini sedikit berbeda untuk pertanyaan itu. Terkadang, kita hanya perlu sql hanya untuk keperluan debug di runtime. Dalam hal ini, ada cara yang lebih mudah, menggunakan debug pada editor.

  • Letakkan breakpoint di org.hibernate.loader.Loader.loadEntityBatch (atau navigasikan di tumpukan sampai di sana);
  • Ketika eksekusi ditangguhkan, lihat nilai variabel this.sql;

Ini untuk hibernasi 3. Saya tidak yakin ini berfungsi pada versi lain.


3

mysql jdbc driver telah memberikan kenyamanan untuk memenuhi persyaratan ini, Anda setidaknya harus memiliki versi jar> = mysql-connect-jar-5.1.6.jar

langkah 1: [konfigurasikan jdbc.url Anda untuk menambahkan logger dan custom logging]

    jdbc.url=jdbc:mysql://host:port/your_db?logger=com.mysql.jdbc.log.Slf4JLogger&profileSQL=true&profilerEventHandler=com.xxx.CustomLoggingProfilerEventHandler

sekarang, ia menggunakan logging slf4j, jika logging default Anda adalah log4j, Anda harus menambahkan slf4j-api, dependensi slf4j-log4j12 untuk menggunakan logging slf4j

langkah 2: [tulis log kustom Anda]

package com.xxx;
import java.sql.SQLException;
import java.util.Properties;

import com.mysql.jdbc.Connection;
import com.mysql.jdbc.log.Log;

public class CustomLoggingProfilerEventHandler implements ProfilerEventHandler {
    private Log log;

    public LoggingProfilerEventHandler() {
    }

    public void consumeEvent(ProfilerEvent evt) {
            /**
             * you can only print the sql as        this.log.logInfo(evt.getMessage())
             * you can adjust your sql print log level with: DEBUG,INFO
             * you can also handle the message to meet your requirement
             */ 
            this.log.logInfo(evt);
    }

    public void destroy() {
        this.log = null;
    }

    public void init(Connection conn, Properties props) throws SQLException {
        this.log = conn.getLog();
    }

}

2

Saya suka ini untuk log4j:

log4j.logger.org.hibernate.SQL=trace
log4j.logger.org.hibernate.engine.query=trace
log4j.logger.org.hibernate.type=trace
log4j.logger.org.hibernate.jdbc=trace
log4j.logger.org.hibernate.type.descriptor.sql.BasicExtractor=error 
log4j.logger.org.hibernate.type.CollectionType=error 

Hei - ini bagus. Tapi saya pikir di sini pertanyaan dicetak dengan? diikuti dengan nilai parameter. Karena saya punya banyak sekali pertanyaan, saya butuh sesuatu yang bisa saya salin-tempel pada editor sql dan itu akan dieksekusi. Apakah ada cara saya bisa melakukan itu dengan menggunakan pendekatan ini. Saya tidak begitu tertarik untuk pergi ke perpustakaan pihak ke-3. Terima kasih :)
dev ray

Terima kasih. Saya berharap tidak harus menggunakan solusi pihak ke-3 dan hibernasi secara langsung, tapi saya rasa saya tidak punya pilihan lain.
dev ray

2

Logging berfungsi tetapi tidak persis seperti yang Anda inginkan atau saya inginkan beberapa waktu lalu, tetapi P6Spy berfungsi dengan baik ,

di sini adalah tutorial sederhana untuk menerapkan juga tutorial MKYONG untuk P6Spy .

bagi saya itu bekerja seperti pesona.

  1. Unduh pustaka P6Spy

Dapatkan "p6spy-install.jar"

  1. Ekstrak itu

Ekstrak p6spy-install.jarfile, cari p6spy.jardanspy.properties

  1. Tambahkan ketergantungan perpustakaan

Tambahkan p6spy.jarke dalam ketergantungan pustaka proyek Anda

  1. Ubah file properti P6Spy

Ubah file konfigurasi basis data Anda. Anda perlu mengganti driver JDBC yang ada dengan driver P6Spy JDBC -com.p6spy.engine.spy.P6SpyDriver

Asli adalah driver MySQL JDBC - com.mysql.jdbc.Driver

<session-factory>
  <property name="hibernate.bytecode.use_reflection_optimizer">false</property>
  <property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
  <property name="hibernate.connection.password">password</property>
  <property name="hibernate.connection.url">jdbc:mysql://localhost:3306/mkyong</property>
  <property name="hibernate.connection.username">root</property>
  <property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
  <property name="show_sql">true</property>
</session-factory>

Mengubahnya menjadi driver P6Spy JDBC - com.p6spy.engine.spy.P6SpyDriver

<session-factory>
  <property name="hibernate.bytecode.use_reflection_optimizer">false</property>
  <property name="hibernate.connection.driver_class">com.p6spy.engine.spy.P6SpyDriver
  </property>
  <property name="hibernate.connection.password">password</property>
  <property name="hibernate.connection.url">jdbc:mysql://localhost:3306/mkyong</property>
  <property name="hibernate.connection.username">root</property>
  <property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
  <property name="show_sql">true</property>
</session-factory>
  1. Ubah file properti P6Spy. Ubah file properti P6Spy -spy.properties

Ganti real driverdengan driver MySQL JDBC yang ada

realdriver=com.mysql.jdbc.Driver

#specifies another driver to use
realdriver2=
#specifies a third driver to use
realdriver3=

Ubah lokasi file Log. Ubah lokasi file log di properti logfile, semua pernyataan SQL akan masuk ke file ini.

Windows

logfile     = c:/spy.log

* nix

logfile     = /srv/log/spy.log
  1. Salin “spy.properties”ke classpath proyek

Salin “spy.properties”ke folder root proyek Anda, pastikan proyek Anda dapat menemukan "spy.properties", jika tidak maka akan meminta “spy.properties”file tidak ditemukan pengecualian.


Ini adalah jalur termudah bagi saya dalam aplikasi Boot Spring saya, di mana saya mencoba untuk log SQL yang dihasilkan dari tes unit. Saya menambahkan dependensi tes ke Gradle (testCompile 'p6spy: p6spy: 3.8.5'), app.yml yang disesuaikan untuk mengatur spring.datasource.url = jdbc: p6spy: h2: mem: testdb dan spring.datasource.driver-class- name = com.p6spy.engine.spy.P6SpyDriver, dan kemudian menambahkan properti spy.prop dengan realdriver = org.h2.Driver dan logfile diatur ke jalur yang saya pilih. Mudah untuk mengekstrak SQL lengkap dari file log yang dihasilkan. Satu-satunya masalah adalah H2 tidak suka format cap waktu yang dibuat.
Ken Pronovici

2

<appender name="console" class="org.apache.log4j.ConsoleAppender">
    <layout class="org.apache.log4j.PatternLayout">
    <param name="ConversionPattern" 
      value="%d{yyyy-MM-dd HH:mm:ss} %-5p %c{1}:%L - %m%n" />
    </layout>
</appender>

<logger name="org.hibernate" additivity="false">
    <level value="INFO" />
    <appender-ref ref="console" />
</logger>

<logger name="org.hibernate.type" additivity="false">
    <level value="TRACE" />
    <appender-ref ref="console" />
</logger>


Bagaimana ini berhubungan dengan pertanyaan?
hotzst

2

Menggunakan Hibernate 4 dan slf4j / log4j2, saya mencoba menambahkan yang berikut ini di konfigurasi log4j2.xml saya:

<Logger name="org.hibernate.type.descriptor.sql.BasicBinder" level="trace" additivity="false"> 
    <AppenderRef ref="Console"/> 
</Logger> 
<Logger name="org.hibernate.type.EnumType" level="trace" additivity="false"> 
    <AppenderRef ref="Console"/>
</Logger>

Tetapi tanpa hasil.

Saya menemukan melalui utas ini bahwa kerangka jboss-logging yang digunakan oleh hibernate perlu dikonfigurasikan untuk dapat login melalui slf4j. Saya menambahkan argumen berikut ke argumen VM aplikasi:

-Dorg.jboss.logging.provider=slf4j

Dan itu bekerja seperti pesona.


2

Inilah yang bekerja untuk saya, set properti di bawah ini di log4j.file:

log4j.logger.org.hibernate.type.descriptor.sql.BasicBinder=TRACE

Pengaturan properti hibernasi:

hibernate.show_sql=true

2

untuk pengembangan dengan Wildfly (standalone.xml), tambahkan penebang tersebut:

<logger category="org.hibernate.SQL">
   <level name="DEBUG"/>
</logger>
<logger category="org.hibernate.type.descriptor.sql">
   <level name="TRACE"/>
</logger>

1

jika Anda menggunakan hibernate 3.2.xx gunakan

log4j.logger.org.hibernate.SQL=trace

dari pada

log4j.logger.org.hibernate.SQL=debug 

1

Anda dapat mencatat ini:

net.sf.hibernate.hql.QueryTranslator

Contoh keluaran:

2013-10-31 14:56:19,029 DEBUG [net.sf.hibernate.hql.QueryTranslator] HQL: select noti.id, noti.idmicrosite, noti.fcaducidad, noti.fpublicacion, noti.tipo, noti.imagen, noti.visible, trad.titulo, trad.subtitulo, trad.laurl, trad.urlnom, trad.fuente, trad.texto  from org.ibit.rol.sac.micromodel.Noticia noti join noti.traducciones trad where index(trad)='ca' and noti.visible='S' and noti.idmicrosite=985 and noti.tipo=3446

2013-10-31 14:56:19,029 DEBUG [net.sf.hibernate.hql.QueryTranslator] SQL: select noticia0_.NOT_CODI as x0_0_, noticia0_.NOT_MICCOD as x1_0_, noticia0_.NOT_CADUCA as x2_0_, noticia0_.NOT_PUBLIC as x3_0_, noticia0_.NOT_TIPO as x4_0_, noticia0_.NOT_IMAGEN as x5_0_, noticia0_.NOT_VISIB as x6_0_, traduccion1_.NID_TITULO as x7_0_, traduccion1_.NID_SUBTIT as x8_0_, traduccion1_.NID_URL as x9_0_, traduccion1_.NID_URLNOM as x10_0_, traduccion1_.NID_FUENTE as x11_0_, traduccion1_.NID_TEXTO as x12_0_ from GUS_NOTICS noticia0_ inner join GUS_NOTIDI traduccion1_ on noticia0_.NOT_CODI=traduccion1_.NID_NOTCOD where (traduccion1_.NID_CODIDI='ca' )and(noticia0_.NOT_VISIB='S' )and(noticia0_.NOT_MICCOD=985 )and(noticia0_.NOT_TIPO=3446 )

Hei ... Saya tidak dapat menemukan contoh pendekatan ini. Bisakah Anda memberikan referensi / contoh / tutorial. Dan apakah masih sama dengan versi terbaru atau hibernate / log4j atau telah menjadi beberapa org.hibernate.QueryTranslator atau sesuatu. Terima kasih
dev ray

Hai ... Saya sudah mencoba ini, tetapi ini sepertinya tidak berfungsi dengan menyimpan atau memperbarui. Saya kira itu hanya berfungsi untuk kueri pemilihan, di mana terjemahan dari hql ke sql mulai dimainkan
dev ray

1

Plugin Log4Jdbc akan menjadi yang terbaik untuk kebutuhan Anda. Ini menunjukkan berikut-

1. Complete SQL query being hit to the db
2. Parameter values being passed to the query
3. Execution time taken by each query

Lihat tautan di bawah ini untuk mengonfigurasi Log4Jdbc-

https://code.google.com/p/log4jdbc/

1

Gunakan Wireshark atau yang serupa:

Tak satu pun dari jawaban yang disebutkan di atas akan mencetak sql dengan parameter dengan benar atau merepotkan. Saya mencapai ini dengan menggunakan WireShark , yang menangkap semua sql / perintah yang dikirim dari aplikasi ke Oracle / Mysql dll dengan permintaan.


2
Log4JDBC akan. Lihat di atas.
Alan Hay

1

Semua jawaban di sini sangat membantu, tetapi jika Anda menggunakan konteks aplikasi Spring XML untuk mengatur pabrik sesi Anda, mengatur variabel level log4j SQL hanya membuat Anda menjadi bagian dari perjalanan ke sana, Anda juga harus mengatur variabel hibernate.show_sql dalam konteks aplikasi itu sendiri untuk mendapatkan Hibernate untuk mulai benar-benar menunjukkan nilai-nilai.

ApplicationContext.xml memiliki:

<property name="hibernateProperties">
            <value>
            hibernate.jdbc.batch_size=25
            ... <!-- Other parameter values here -->
            hibernate.show_sql=true
            </value>
 </property>

Dan file log4j Anda perlu

log4j.logger.org.hibernate.SQL=DEBUG

1

Di Jawa:

Ubah kueri Anda di TypedQuery jika itu adalah KriteriaQuery (javax.persistence).

Kemudian:

query.unwrap (org.hibernate.Query.class) .getQueryString ();


1
Terima kasih, Ini mencetak kueri, tetapi bukan parameter yang digunakan, ada cara untuk mencetak parameter juga?
Liz Lamperouge

0

Hibernate menampilkan kueri dan nilai parameternya di baris yang berbeda.

Jika Anda menggunakan application.properties di spring boot dan Anda dapat menggunakan parameter yang disorot di bawah ini di application.properties.

  1. org.hibernate.SQL akan menampilkan kueri

    logging.level.org.hibernate.SQL = DEBUG

  2. org.hibernate.type akan menampilkan semua nilai parameter, yang akan dipetakan dengan pilih, masukkan dan perbarui kueri. logging.level.org.hibernate.type = TRACE

    • org.hibernate.type.EnumType akan menampilkan nilai parameter tipe enum

      logging.level.org.hibernate.type.EnumType = TRACE

      contoh ::

      2018-06-14 11:06:28,217 TRACE [main] [EnumType.java : 321] Binding [active] to parameter: [1]
    • sql.BasicBinder akan menampilkan nilai parameter tipe integer, varchar, tipe boolean

      logging.level.org.hibernate.type.descriptor.sql.BasicBinder = TRACE

      contoh ::

      • 2018-06-14 11: 28: 29.750 TRACE [http-nio-9891-exec-2] [BasicBinder.java: 65] parameter pengikat [1] sebagai [BOOLEAN] - [benar]
      • 2018-06-14 11: 28: 29.751 TRACE [http-nio-9891-exec-2] [BasicBinder.java: 65] parameter pengikat [2] sebagai [INTEGER] - [1]
      • 2018-06-14 11: 28: 29.752 TRACE [http-nio-9891-exec-2] [BasicBinder.java: 65] parameter pengikat [3] sebagai [VARCHAR] - [publik]

1
Bahkan ini tidak menunjukkan nilai untuk batas dan offset dalam kueri.
T3rm1

0

Solusi paling sederhana bagi saya adalah menerapkan stringReplace biasa untuk mengganti input parameter dengan nilai parameter (memperlakukan semua parameter sebagai string, untuk kesederhanaan):

 String debugedSql = sql;
 //then, for each named parameter
     debugedSql = debugedSql.replaceAll(":"+key, "'"+value.toString()+"'");
 //and finnaly
 println(debugedSql);

atau sesuatu yang serupa untuk parameter posisi (?).
Jaga nilai null dan tipe nilai spesifik seperti tanggal, jika Anda ingin menjalankan sql yang siap untuk dicatat.

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.