JDBC Driver
clickhouse-jdbc implements the standard JDBC interface using the latest java client.
We recommend using the latest java client directly if performance/direct access is critical.
Environment requirements
- OpenJDK version >= 8
Setup
- Maven
- Gradle (Kotlin)
- Gradle
Configuration
Driver Class: com.clickhouse.jdbc.ClickHouseDriver
com.clickhouse.jdbc.ClickHouseDriver is a facade class for the new and old JDBC implementations. It uses the new JDBC implementation by default.
You can use the old JDBC implementation by setting the clickhouse.jdbc.v1 property to true in the connection properties.
com.clickhouse.jdbc.Driver is new JDBC implementation.
com.clickhouse.jdbc.DriverV1 is old JDBC implementation.
URL Syntax: jdbc:(ch|clickhouse)[:<protocol>]://endpoint[:port][/<database>][?param1=value1¶m2=value2][#tag1,tag2,...], for example:
jdbc:clickhouse:http://localhost:8123jdbc:clickhouse:https://localhost:8443?ssl=true
There are a few things to note about the URL syntax:
- only one endpoint is allowed in the URL
- protocol should be specified when it is not the default one - 'HTTP'
- port should be specified when it is not the default one '8123'
- driver do not guess the protocol from the port, you need to specify it explicitly
sslparameter is not required when protocol is specified.
Connection Properties
Main configuration parameters are defined in the java client. They should be passed as is to the driver. Driver has some own properties that are not part of the client configuration they are listed below.
Driver properties:
| Property | Default | Description |
|---|---|---|
disable_frameworks_detection | true | Disable frameworks detection for User-Agent |
jdbc_ignore_unsupported_values | false | Suppresses SQLFeatureNotSupportedException where is doesn't affect the driver work |
clickhouse.jdbc.v1 | false | Use older JDBC implementation instead of new JDBC |
default_query_settings | null | Allows passing of default query settings with query operations |
jdbc_resultset_auto_close | true | Automatically closes ResultSet when Statement is closed |
beta.row_binary_for_simple_insert | false | Use PreparedStatement implementation based on RowBinary writer. Works only for INSERT INTO ... VALUES queries. |
jdbc_resultset_auto_close | true | Automatically closes ResultSet when Statement is closed |
jdbc_use_max_result_rows | false | Enables using server property max_result_rows to limit number of rows returned by query. When enabled, overrides user-set overflow mode. See JavaDoc for details. |
jdbc_sql_parser | JAVACC | Configures which SQL parser to use. Choices: ANTLR4, ANTLR4_PARAMS_PARSER, JAVACC. |
All server settings should be prefixed with clickhouse_setting_ (same as for the client configuration).
Example configuration:
what will be equivalent to the following JDBC URL:
Note: no need to url encode JDBC URL or properties, they will be automatically encoded.
Supported data types
JDBC Driver supports the same data formats as the underlying java client.
Handling Dates, Times, and Timezones
java.sql.Date, java.sql.Time, and java.sql.Timestamp can complicate how Timezones are calculated - though they're of course supported,
you may want to consider using the java.time package. ZonedDateTime and
OffsetDateTime are both great replacements for java.sql.Timestamp, java.sql.Date, and java.sql.Time.
Date is stored without timezone, while DateTime is stored with timezone. This can lead to unexpected results if you're not careful.
Creating Connection
Supplying Credentials and Settings
Simple Statement
Insert
HikariCP
More Information
For more information, see our GitHub repository and Java Client documentation.
Troubleshooting
Logging
The driver uses slf4j for logging, and will use the first available implementation on the classpath.
Resolving JDBC Timeout on Large Inserts
When performing large inserts in ClickHouse with long execution times, you may encounter JDBC timeout errors like:
These errors can disrupt the data insertion process and affect system stability. To address this issue you may need to adjust a few timeout settings in the client's OS.
Mac OS
On Mac OS, the following settings can be adjusted to resolve the issue:
net.inet.tcp.keepidle: 60000net.inet.tcp.keepintvl: 45000net.inet.tcp.keepinit: 45000net.inet.tcp.keepcnt: 8net.inet.tcp.always_keepalive: 1
Linux
On Linux, the equivalent settings alone may not resolve the issue. Additional steps are required due to the differences in how Linux handles socket keep-alive settings. Follow these steps:
- Adjust the following Linux kernel parameters in
/etc/sysctl.confor a related configuration file:
net.inet.tcp.keepidle: 60000net.inet.tcp.keepintvl: 45000net.inet.tcp.keepinit: 45000net.inet.tcp.keepcnt: 8net.inet.tcp.always_keepalive: 1net.ipv4.tcp_keepalive_intvl: 75net.ipv4.tcp_keepalive_probes: 9net.ipv4.tcp_keepalive_time: 60 (You may consider lowering this value from the default 300 seconds)
- After modifying the kernel parameters, apply the changes by running the following command:
After Setting those settings, you need to ensure that your client enables the Keep Alive option on the socket:
Migration Guide
Key Changes
| Feature | V1 (Old) | V2 (New) |
|---|---|---|
| Transaction Support | Partially supported | Not supported |
| Response Column Renaming | Partially supported | Not supported |
| Multi-Statement SQL | Not supported | Not allowed |
| Named Parameters | Supported | Not supported (not in JDBC spec) |
Streaming Data With PreparedStatement | Supported | Not supported |
- JDBC V2 is implemented to be more lightweight and some features were removed.
- Streaming Data is not supported in JDBC V2 because it is not part of the JDBC spec and Java.
- JDBC V2 expects explicit configuration. No failover defaults.
- Protocol should be specified in the URL. No implicit protocol detection using port numbers.
Configuration Changes
There are only two enums:
com.clickhouse.jdbc.DriverProperties- the driver own configuration properties.com.clickhouse.client.api.ClientConfigProperties- the client configuration properties. Client configuration changes are described in the Java Client documentation.
Connection properties are parsed in the following way:
- URL is parsed first for properties. They override all other properties.
- Driver properties are not passed to the client.
- Endpoints (host, port, protocol) are parsed from the URL.
Example:
Data Types Changes
| ClickHouse Type | Changed | JDBC Type (V2) | Java Class (V2) | JDBC Type (V1) | Java Class (V1) |
|---|---|---|---|---|---|
| Int8 | No | TINYINT | java.lang.Byte | TINYINT | java.lang.Byte |
| Int16 | No | SMALLINT | java.lang.Short | SMALLINT | java.lang.Short |
| Int32 | No | INTEGER | java.lang.Integer | INTEGER | java.lang.Integer |
| Int64 | No | BIGINT | java.lang.Long | BIGINT | java.lang.Long |
| UInt8 | Yes | OTHER | java.lang.Short | OTHER | com.clickhouse.data.value.UnsignedByte |
| UInt16 | Yes | OTHER | java.lang.Integer | OTHER | com.clickhouse.data.value.UnsignedShort |
| UInt32 | Yes | OTHER | java.lang.Long | OTHER | com.clickhouse.data.value.UnsignedInteger |
| UInt64 | Yes | OTHER | java.math.BigInteger | OTHER | com.clickhouse.data.value.UnsignedLong |
| Int128 | No | OTHER | java.math.BigInteger | OTHER | java.math.BigInteger |
| UInt128 | No | OTHER | java.math.BigInteger | OTHER | java.math.BigInteger |
| Int256 | No | OTHER | java.math.BigInteger | OTHER | java.math.BigInteger |
| UInt256 | No | OTHER | java.math.BigInteger | OTHER | java.math.BigInteger |
| Float32 | No | REAL | java.lang.Float | REAL | java.lang.Float |
| Float64 | No | DOUBLE | java.lang.Double | DOUBLE | java.lang.Double |
| Decimal32 | No | DECIMAL | java.math.BigDecimal | DECIMAL | java.math.BigDecimal |
| Decimal64 | No | DECIMAL | java.math.BigDecimal | DECIMAL | java.math.BigDecimal |
| Decimal128 | No | DECIMAL | java.math.BigDecimal | DECIMAL | java.math.BigDecimal |
| Decimal256 | No | DECIMAL | java.math.BigDecimal | DECIMAL | java.math.BigDecimal |
| Bool | No | BOOLEAN | java.lang.Boolean | BOOLEAN | java.lang.Boolean |
| String | No | VARCHAR | java.lang.String | VARCHAR | java.lang.String |
| FixedString | No | CHAR | java.lang.String | CHAR | java.lang.String |
| Date | Yes | DATE | java.sql.Date | DATE | java.time.LocalDate |
| Date32 | Yes | DATE | java.sql.Date | DATE | java.time.LocalDate |
| DateTime | Yes | TIMESTAMP | java.sql.Timestamp | TIMESTAMP | java.time.OffsetDateTime |
| DateTime64 | Yes | TIMESTAMP | java.sql.Timestamp | TIMESTAMP | java.time.OffsetDateTime |
| UUID | No | OTHER | java.util.UUID | OTHER | java.util.UUID |
| IPv4 | No | OTHER | java.net.Inet4Address | OTHER | java.net.Inet4Address |
| IPv6 | No | OTHER | java.net.Inet6Address | OTHER | java.net.Inet6Address |
- Unsigned types are mapped to java types for better portability.
DateandDate32are mapped tojava.sql.Datefor better compatibility with JDBC. However gettingjava.time.LocalDateis possible by usingResultSet.getObject(int, Class<T>)withjava.time.LocalDate.classas the second argument.Arrayis mapped to anjava.sql.Arrayobject.Tupleis mapped to anjava.sql.Structobject. But can be used asArray.