Search code examples
javaspring-bootjdbcfirebirdjaybird

FBDriver reporting warnings I can't figure out how to fix


I'm developing a RESTful application and whenever I make a request, it works fine, but also outputs these warnings:

o.h.engine.jdbc.spi.SqlExceptionHelper   : SQL Warning Code: 0, SQLState: null
o.h.engine.jdbc.spi.SqlExceptionHelper   : Connection.isValid does not support non-zero timeouts, timeout value 5 has been ignored

Using Spring Boot framework with Hibernate, HikariCP, QueryDSL and a Firebird database using the Jaybird 4.0.5.java11 version.

Here is my application.yml file where I setup the connection with my database:

spring:
  datasource:
    driver-class-name: org.firebirdsql.jdbc.FBDriver
    url: jdbc:firebirdsql://localhost:3050/C:\\path\\to\\my\\database.fdb?encoding=win1252
    username: myuser
    password: mypassword
    hikari:
      connection-timeout: 1000
      login-timeout: 1000
      minimum-idle: 10

  jpa:
    database-platform: org.hibernate.dialect.FirebirdDialect
    hibernate:
      ddl-auto: validate

I've tried all options I could to setup a timeout but none of them made the timeout warning go away.

Also, I can't figure out that SQL Warning Code: 0, from what I've gathered so far, it means it worked, but why is it outputting a warning?

I should mention that I've altered some sensitive information and they were replaced with path\\to\\my\\database.fdb, myuser and mypassword, but these settings work just fine.


Solution

  • The reason for this is that Jaybird currently doesn't support a timeout for Connection.isValid(int) and ignores it, and thus - if the specified timeout is non-zero - it registers a SQLWarning on the connection (instead of throwing an exception). Although registering a warning here isn't specified in the JDBC specification, this is similar to what JDBC requires a driver to do when it replaces/ignores user-specified values when configuring the result set type, concurrency and holdability.

    When Hibernate notices there is a warning registered on the connection, it will log that warning in org.hibernate.engine.jdbc.spi.SqlExceptionHelper. This logging of warnings can be disabled by setting the property hibernate.jdbc.log.warnings=false (see Query Settings in the Hibernate documentation). In case of Spring Boot, I guess you can set this as property spring.jpa.properties.hibernate.jdbc.log.warnings (but I haven't verified this).

    The timeout is configurable through the HikariCP property validationTimeout, but - by default - this doesn't accept a value lower than 250 milliseconds (you can change that with system property com.zaxxer.hikari.timeoutMs.floor). Alternatively, you can configure HikariCP property connectionTestQuery with - for example - select 1 from rdb$database, so HikariCP uses the test query instead of Connection.isValid(int). Be aware that a test query has more overhead.

    The warning code printed is the SQLWarning.getErrorCode() (technically, SQLException.getErrorCode(), a.k.a the vendor code). And given this warning doesn't have an error/warning code, its value is 0, which simply means "there is no specific vendor code associated with this warning".

    I have created this issue to see if actual timeout support can be added in Jaybird 4.0.6 or Jaybird 5.

    Since Jaybird 6, it is also possible to disable reporting of warnings entirely, using the connection property reportSQLWarnings=NONE.

    Disclosure: I am one of the maintainers of Jaybird.