J'essaie de configurer HikariCP dans mon application Spring Boot (1.2.0.M1) afin de pouvoir l'utiliser à la place de Tomcat DBCP. J'aimerais configurer le pool de connexions dans mon fichier application.properties comme je le faisais avec Tomcat, mais je ne vois pas comment je devrais le faire. Tous les exemples que j'ai trouvés montrent le style JavaConfig ou l'utilisation d'un fichier de propriétés HikariCP distinct. Quelqu'un peut-il m'aider à comprendre les noms de propriété pour le configurer dans application.properties? J'aimerais également passer de l'approche driverClassName à l'approche DataSourceClassName, car elle a l'air plus propre et est recommandée. Est-ce également possible dans mes fichiers application.properties?
Voici ce que j'ai eu pour Tomcat DBCP (juste une configuration de base, pas complètement vidé)
spring.datasource.validation-query=SELECT 1
spring.datasource.max-active=10
spring.datasource.max-idle=8
spring.datasource.min-idle=8
spring.datasource.initial-size=5
spring.datasource.test-on-borrow=true
spring.datasource.test-on-return=true
Et j'utilise actuellement driverClassName et l'URL jdbc pour configurer la connexion:
spring.datasource.url=jdbc:mysql://localhost:3306/myDb
spring.datasource.driverClassName=com.mysql.jdbc.Driver
@Configuration
@ConfigurationProperties(prefix = "params.datasource")
public class JpaConfig extends HikariConfig {
@Bean
public DataSource dataSource() throws SQLException {
return new HikariDataSource(this);
}
}
application.yml
params:
datasource:
driverClassName: com.mysql.jdbc.Driver
jdbcUrl: jdbc:mysql://localhost:3306/myDb
username: login
password: password
maximumPoolSize: 5
MIS À JOUR! Depuis la version Spring Boot 1.3.0 :
application.yml
spring:
datasource:
type: com.zaxxer.hikari.HikariDataSource
url: jdbc:h2:mem:TEST
driver-class-name: org.h2.Driver
username: username
password: password
hikari:
idle-timeout: 10000
MIS À JOUR! Depuis la version Spring Boot 2.0.0 :
Le pool de connexions par défaut est passé de Tomcat à Hikari :)
Vous pouvez simplement utiliser uniquement application.yml/application.properties. Il n'est pas nécessaire de créer explicitement un bean DataSource
Vous devez exclure Tomcat-jdbc comme mentionné par ydemartino
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
<exclusions>
<exclusion>
<groupId>org.Apache.Tomcat</groupId>
<artifactId>Tomcat-jdbc</artifactId>
</exclusion>
</exclusions>
</dependency>
Comme vous ne créez pas de bean DataSource
, vous devez spécifier explicitement l'utilisation de Hikari via spring.datasource.type
avec la valeur com.zaxxer.hikari.HikariDataSource
dans application.yml/application.properties
spring:
datasource:
hikari:
connection-test-query: SELECT 1 FROM DUAL
minimum-idle: 1
maximum-pool-size: 5
pool-name: yourPoolName
auto-commit: false
driver-class-name: com.mysql.jdbc.Driver
url: jdbc:mysql://localhost:3306/myDb
username: login
password: password
type: com.zaxxer.hikari.HikariDataSource
Dans votre application.yml/application.properties, vous pouvez configurer des paramètres spécifiques à Hikari tels que la taille du pool, etc. dans spring.datasource.hikari.*
Je suis tombé sur HikariCP
et les tests de performance m'ont émerveillé. Je voulais l'essayer plutôt que mon choix par défaut C3P0
et à ma grande surprise, j'ai eu du mal à obtenir le configurations
probablement parce que les configurations diffèrent en fonction de la combinaison de pile technologique que vous utilisez.
J'ai configuré le projet Spring Boot
avec les démarreurs JPA, Web, Security
(à l'aide de Spring Initializer ) pour utiliser PostgreSQL
en tant que base de données avec HikariCP
en tant que pool de connexions.
J'ai utilisé Gradle
comme outil de génération et j'aimerais partager ce qui a fonctionné pour moi pour les hypothèses suivantes:
Vous avez besoin du build.gradle
suivant si vous utilisez Gradle
ou l'équivalent pom.xml
si vous utilisez maven
buildscript {
ext {
springBootVersion = '1.5.8.RELEASE'
}
repositories {
mavenCentral()
}
dependencies {
classpath("org.springframework.boot:spring-boot-gradle-plugin:${springBootVersion}")
}
}
apply plugin: 'Java'
apply plugin: 'Eclipse'
apply plugin: 'org.springframework.boot'
apply plugin: 'war'
group = 'com'
version = '1.0'
sourceCompatibility = 1.8
repositories {
mavenCentral()
}
dependencies {
compile('org.springframework.boot:spring-boot-starter-aop')
// Exclude the Tomcat-jdbc since it's used as default for connection pooling
// This can also be achieved by setting the spring.datasource.type to HikariCP
// datasource see application.properties below
compile('org.springframework.boot:spring-boot-starter-data-jpa') {
exclude group: 'org.Apache.Tomcat', module: 'Tomcat-jdbc'
}
compile('org.springframework.boot:spring-boot-starter-security')
compile('org.springframework.boot:spring-boot-starter-web')
runtime('org.postgresql:postgresql')
testCompile('org.springframework.boot:spring-boot-starter-test')
testCompile('org.springframework.security:spring-security-test')
// Download HikariCP but, exclude hibernate-core to avoid version conflicts
compile('com.zaxxer:HikariCP:2.5.1') {
exclude group: 'org.hibernate', module: 'hibernate-core'
}
// Need this in order to get the HikariCPConnectionProvider
compile('org.hibernate:hibernate-hikaricp:5.2.11.Final') {
exclude group: 'com.zaxxer', module: 'HikariCP'
exclude group: 'org.hibernate', module: 'hibernate-core'
}
}
Il y a un tas d'excludes dans le build.gradle
ci-dessus et c'est parce que
jdbc-Tomcat
lors du téléchargement des dépendances spring-boot-starter-data-jpa
. Ceci peut être réalisé en configurant également le spring.datasource.type=com.zaxxer.hikari.HikariDataSource
mais je ne veux pas de dépendance supplémentaire si je n'en ai pas besoin hibernate-core
lors du téléchargement de la dépendance com.zaxxer
et c’est parce que hibernate-core
est déjà téléchargé par Spring Boot
et que nous ne voulons pas nous retrouver avec des versions différentes. hibernate-core
lors du téléchargement du module hibernate-hikaricp
, nécessaire pour que HikariCP utilise org.hibernate.hikaricp.internal.HikariCPConnectionProvider
en tant que fournisseur de connexion au lieu de obsolète com.zaxxer.hikari.hibernate.HikariConnectionProvider
Une fois que j’ai compris le build.gradle
et ce qu’il fallait garder et ce qu’il ne fallait pas, j’étais prêt à copier/coller une configuration datasource
dans mon application.properties
et je pensais que tout fonctionnerait bien, mais pas vraiment et j’ai trébuché sur les problèmes suivants
com.zaxxer.hikari.hibernate.HikariConnectionProvider
key/value
dans le application.properties
et se plaignait de dataSource, dataSourceClassName, jdbcUrl
. J'ai dû déboguer dans HikariConfig, HikariConfigurationUtil, HikariCPConnectionProvider
et découvert que HikariCP
ne pouvait pas trouver les propriétés de application.properties
car le nom était différent. Quoi qu’il en soit, c’est là que j’ai dû miser sur des essais et des erreurs pour s’assurer que HikariCP
est en mesure de choisir les propriétés (c’est-à-dire que la source de données contient des détails de base de données, ainsi que des propriétés de mise en pool), ainsi que Sping Boot se comporte comme prévu et que je me suis retrouvé avec le fichier application.properties
suivant.
server.contextPath=/
debug=true
# Spring data source needed for Spring boot to behave
# Pre Spring Boot v2.0.0.M6 without below Spring Boot defaults to Tomcat-jdbc connection pool included
# in spring-boot-starter-jdbc and as compiled dependency under spring-boot-starter-data-jpa
spring.datasource.type=com.zaxxer.hikari.HikariDataSource
spring.datasource.url=jdbc:postgresql://localhost:5432/somedb
spring.datasource.username=dbuser
spring.datasource.password=dbpassword
# Hikari will use the above plus the following to setup connection pooling
spring.datasource.hikari.minimumIdle=5
spring.datasource.hikari.maximumPoolSize=20
spring.datasource.hikari.idleTimeout=30000
spring.datasource.hikari.poolName=SpringBootJPAHikariCP
spring.datasource.hikari.maxLifetime=2000000
spring.datasource.hikari.connectionTimeout=30000
# Without below HikariCP uses deprecated com.zaxxer.hikari.hibernate.HikariConnectionProvider
# Surprisingly enough below ConnectionProvider is in hibernate-hikaricp dependency and not hibernate-core
# So you need to pull that dependency but, make sure to exclude it's transitive dependencies or you will end up
# with different versions of hibernate-core
spring.jpa.hibernate.connection.provider_class=org.hibernate.hikaricp.internal.HikariCPConnectionProvider
# JPA specific configs
spring.jpa.properties.hibernate.show_sql=true
spring.jpa.properties.hibernate.format_sql=true
spring.jpa.properties.hibernate.use_sql=true
spring.jpa.properties.hibernate.id.new_generator_mappings=false
spring.jpa.properties.hibernate.default_schema=dbschema
spring.jpa.properties.hibernate.search.autoregister_listeners=false
spring.jpa.properties.hibernate.bytecode.use_reflection_optimizer=false
# Enable logging to verify that HikariCP is used, the second entry is specific to HikariCP
logging.level.org.hibernate.SQL=DEBUG
logging.level.com.zaxxer.hikari.HikariConfig=DEBUG
logging.level.org.hibernate.type.descriptor.sql.BasicBinder=TRACE
Comme indiqué ci-dessus, les configurations sont divisées en catégories en fonction des modèles de dénomination suivants
Il est difficile de trouver un tutoriel, un message ou une ressource qui montre comment le fichier de propriétés ci-dessus est utilisé et comment les propriétés doivent être nommées. Bien, tu l'as maintenant.
Le fait d'insérer le application.properties
ci-dessus avec build.gradle
(ou au moins similaire) dans une version de projet Spring Boot JPA (1.5.8) devrait fonctionner comme un charme et se connecter à votre base de données préconfigurée (c'est-à-dire dans mon cas, c'est PostgreSQL que HikariCP & Spring
détermine à partir le spring.datasource.url
sur le pilote de base de données à utiliser).
Je ne voyais pas la nécessité de créer un bean DataSource
et c’est parce que Spring Boot est capable de tout faire pour moi simplement en regardant dans application.properties
et c’est génial.
Le article du github de HikariCP wiki montre comment configurer Spring Boot avec JPA, mais manque d'explications et de détails.
Les deux fichiers ci-dessus sont également disponibles publiquement. Gist https://Gist.github.com/rhamedy/b3cb936061cc03acdfe21358b86a5bc6
Vous n'avez pas besoin de code redondant pour mettre des valeurs de propriété dans des variables. Vous pouvez définir les propriétés avec un fichier de propriétés directement.
Placez le fichier hikari.properties
dans le chemin de classe.
driverClassName=com.mysql.jdbc.Driver
jdbcUrl=jdbc:mysql://localhost:3306/myDb
connectionTestQuery=SELECT 1
maximumPoolSize=20
username=...
password=...
Et créez un bean source de données comme celui-ci.
@Bean(destroyMethod = "close")
public DataSource dataSource() throws SQLException {
HikariConfig config = new HikariConfig("/hikari.properties");
HikariDataSource dataSource = new HikariDataSource(config);
return dataSource;
}
Cela fonctionne pour mon application de démarrage au cas où cela aiderait. Cette classe vous indique les propriétés recherchées par l'objet config:
Je pense que plusieurs sources de données pourraient être supportées en ajoutant datasource_whatever
aux clés de propriété dans le fichier de configuration source. À votre santé!
@Configuration
class DataSourceConfig {
@Value('${spring.datasource.username}')
private String user;
@Value('${spring.datasource.password}')
private String password;
@Value('${spring.datasource.url}')
private String dataSourceUrl;
@Value('${spring.datasource.dataSourceClassName}')
private String dataSourceClassName;
@Value('${spring.datasource.connectionTimeout}')
private int connectionTimeout;
@Value('${spring.datasource.maxLifetime}')
private int maxLifetime;
@Bean
public DataSource primaryDataSource() {
Properties dsProps = [url: dataSourceUrl, user: user, password: password]
Properties configProps = [
connectionTestQuery: 'select 1 from dual',
connectionTimeout: connectionTimeout,
dataSourceClassName: dataSourceClassName,
dataSourceProperties: dsProps,
maxLifetime: maxLifetime
]
// A default max pool size of 10 seems reasonable for now, so no need to configure for now.
HikariConfig hc = new HikariConfig(configProps)
HikariDataSource ds = new HikariDataSource(hc)
ds
}
}
vous ne pouvez pas utiliser l'approche dataSourceClassName dans les configurations application.properties comme l'a dit @Andy Wilkinson. si vous voulez quand même avoir dataSourceClassName, vous pouvez utiliser Java Config en tant que:
@Configuration
@ComponentScan
class DataSourceConfig {
@Value("${spring.datasource.username}")
private String user;
@Value("${spring.datasource.password}")
private String password;
@Value("${spring.datasource.url}")
private String dataSourceUrl;
@Value("${spring.datasource.dataSourceClassName}")
private String dataSourceClassName;
@Value("${spring.datasource.poolName}")
private String poolName;
@Value("${spring.datasource.connectionTimeout}")
private int connectionTimeout;
@Value("${spring.datasource.maxLifetime}")
private int maxLifetime;
@Value("${spring.datasource.maximumPoolSize}")
private int maximumPoolSize;
@Value("${spring.datasource.minimumIdle}")
private int minimumIdle;
@Value("${spring.datasource.idleTimeout}")
private int idleTimeout;
@Bean
public DataSource primaryDataSource() {
Properties dsProps = new Properties();
dsProps.put("url", dataSourceUrl);
dsProps.put("user", user);
dsProps.put("password", password);
dsProps.put("prepStmtCacheSize",250);
dsProps.put("prepStmtCacheSqlLimit",2048);
dsProps.put("cachePrepStmts",Boolean.TRUE);
dsProps.put("useServerPrepStmts",Boolean.TRUE);
Properties configProps = new Properties();
configProps.put("dataSourceClassName", dataSourceClassName);
configProps.put("poolName",poolName);
configProps.put("maximumPoolSize",maximumPoolSize);
configProps.put("minimumIdle",minimumIdle);
configProps.put("minimumIdle",minimumIdle);
configProps.put("connectionTimeout", connectionTimeout);
configProps.put("idleTimeout", idleTimeout);
configProps.put("dataSourceProperties", dsProps);
HikariConfig hc = new HikariConfig(configProps);
HikariDataSource ds = new HikariDataSource(hc);
return ds;
}
}
raison pour laquelle vous ne pouvez pas utiliser dataSourceClassName, car il lancera et exception
Caused by: Java.lang.IllegalStateException: both driverClassName and dataSourceClassName are specified, one or the other should be used.
ce qui signifie que spring boot déduit de la propriété spring.datasource.url le pilote et que, en même temps, le paramètre dataSourceClassName crée cette exception. Pour que cela fonctionne correctement, votre application.properties devrait ressembler à ceci pour la source de données HikariCP:
# hikariCP
spring.jpa.databasePlatform=org.hibernate.dialect.MySQLDialect
spring.datasource.url=jdbc:mysql://localhost:3306/exampledb
spring.datasource.username=root
spring.datasource.password=
spring.datasource.poolName=SpringBootHikariCP
spring.datasource.maximumPoolSize=5
spring.datasource.minimumIdle=3
spring.datasource.maxLifetime=2000000
spring.datasource.connectionTimeout=30000
spring.datasource.idleTimeout=30000
spring.datasource.pool-prepared-statements=true
spring.datasource.max-open-prepared-statements=250
Remarque: Veuillez vérifier s'il existe des fichiers Tomcat-jdbc.jar ou commons-dbcp.jar dans votre chemin de classe ajoutés la plupart du temps par dépendance transitive. Si ceux-ci sont présents dans le chemin de classe, Spring Boot configurera la source de données à l'aide du pool de connexions par défaut qui est Tomcat. HikariCP ne sera utilisé pour créer la source de données que s'il n'y a pas d'autre fournisseur dans classpath. il y a une séquence de repli de Tomcat -> vers HikariCP -> vers Commons DBCP.
Vous pouvez utiliser l'approche dataSourceClassName, voici un exemple avec MySQL . (Testé avec spring boot 1.3 et 1.4)
Vous devez d’abord exclure Tomcat-jdbc du classpath, qui sera choisi en faveur de hikaricp.
pom.xml
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
<exclusions>
<exclusion>
<groupId>org.Apache.Tomcat</groupId>
<artifactId>Tomcat-jdbc</artifactId>
</exclusion>
</exclusions>
</dependency>
application.properties
spring.datasource.dataSourceClassName=com.mysql.jdbc.jdbc2.optional.MysqlDataSource
spring.datasource.dataSourceProperties.serverName=localhost
spring.datasource.dataSourceProperties.portNumber=3311
spring.datasource.dataSourceProperties.databaseName=mydb
spring.datasource.username=root
spring.datasource.password=root
Ensuite, il suffit d'ajouter
@Bean
@ConfigurationProperties(prefix = "spring.datasource")
public DataSource dataSource() {
return DataSourceBuilder.create().build();
}
J'ai créé un projet test ici: https://github.com/ydemartino/spring-boot-hikaricp
Selon la documentation, il est changé,
https://docs.spring.io/spring-boot/docs/current/reference/html/boot-features-sql.html
Exemple :
spring:
datasource:
url: 'jdbc:mysql://localhost/db?useSSL=false'
username: root
password: pass
driver: com.mysql.jdbc.Driver
hikari:
minIdle: 10
idle-timeout: 10000
maximumPoolSize: 30
Ce sont les changements de configuration suivants que nous pouvons faire sur hikari, veuillez ajouter/mettre à jour en fonction de vos besoins.
autoCommit
connectionTimeout
idleTimeout
maxLifetime
connectionTestQuery
connectionInitSql
validationTimeout
maximumPoolSize
poolName
allowPoolSuspension
readOnly
transactionIsolation
leakDetectionThreshold
Donc, il s'avère que presque tous les paramètres par défaut pour HikariCP fonctionnent pour moi, à l'exception du nombre de connexions à la base de données. J'ai défini cette propriété dans mon application.properties:
spring.datasource.maximumPoolSize=20
Et Andy Wilkinson a raison, pour autant que je sache, en ce sens que vous ne pouvez pas utiliser l'approche de configuration dataSourceClassName pour HikariCP avec Spring Boot.
J'utilise Spring Boot 2.0.4.RELEASE. Hikari est le pool de connexion par défaut et .hikari
n'est plus nécessaire.
application.properties
spring.datasource.driverClassName=com.mysql.jdbc.Driver
spring.datasource.jdbcUrl=jdbc:mysql://localhost:3306/myDB...
spring.datasource.username=xxx
spring.datasource.password=xxx
spring.datasource.poolname=myPool
application.yml
spring:
datasource:
driverClassName: com.mysql.jdbc.Driver
jdbcUrl: jdbc:mysql://localhost:3306/myDB...
username: xxx
password: xxx
poolName: myPool
Et configuration
n'a pas besoin d'étendre HikariConfig
, et DataSourceBuilder
peut être utilisé tel quel.
@Configuration
public class DataSourceConfiguration {
@Bean(name="myDataSource")
@ConfigurationProperties("spring.datasource")
public DataSource myDataSource() {
return DataSourceBuilder.create().build();
}
}
Voici la bonne nouvelle. HikariCP est le pool de connexions par défaut avec Spring Boot 2.0.0.
Notes de version de Spring Boot 2.0.0
La technologie de regroupement de bases de données par défaut de Spring Boot 2.0 est passée de Tomcat Pool à HikariCP. Nous avons constaté que Hakari offrait des performances supérieures et beaucoup de nos utilisateurs le préféraient à Tomcat Pool.
Mon setUp:
Spring Boot v1.5.10
Hikari v.3.2.x (pour évaluation)
Pour bien comprendre la configuration de Hikari Data Source, il est recommandé de désactiver la configuration automatique de Spring Boot pour Data Source.
Ajouter ce qui suit à application.properties:-
spring.autoconfigure.exclude = org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration
Cela désactivera la capacité de Spring Boot de configurer le DataSource lui-même.
Vous avez maintenant la possibilité de définir votre propre configuration personnalisée pour créer le bean HikariDataSource et le renseigner avec les propriétés souhaitées.
REMARQUE :::
Classe publique HikariDataSource étend HikariConfig
Tu dois
Je crois en la définition de ma propre classe de configuration personnalisée ( @Configuration) pour créer la source de données moi-même et remplir avec les propriétés de la source de données définies dans un fichier séparé (que traditional: application.properties)
De cette manière, je peux définir Mon propre sessionFactory Bean utilisant Hibernate a recommandé: "LocalSessionFactoryBean" et remplissez-le avec votre source de données Hikari> et d'autres propriétés basées sur Hiberante-JPA.
Résumé des propriétés de la source de données Hikari basées sur Spring Boot: -
spring.datasource.hikari.allow-pool-suspension = true
spring.datasource.hikari.auto-commit = false
spring.datasource.hikari.catalog =
spring.datasource.hikari.connection-init-sql =
spring.datasource.hikari.connection-test-query =
spring.datasource.hikari.connection-timeout = 100
spring.datasource.hikari.data-source-class-name =
spring.datasource.hikari.data-source-j-n-d-i =
spring.datasource.hikari.driver-class-name =
spring.datasource.hikari.idle-timeout = 50
spring.datasource.hikari.initialization-fail-fast = true
spring.datasource.hikari.isolate-internal-queries = true
spring.datasource.hikari.jdbc-url =
spring.datasource.hikari.leak-detection-threshold =
spring.datasource.hikari.login-timeout = 60
spring.datasource.hikari.max-life =
spring.datasource.hikari.maximum-pool-size = 500
spring.datasource.hikari.minimum-idle = 30
spring.datasource.hikari.password =
spring.datasource.hikari.pool-name =
spring.datasource.hikari.read-only = true
spring.datasource.hikari.register-mbeans = true
spring.datasource.hikari.transaction-isolation =
spring.datasource.hikari.username =
spring.datasource.hikari.validation-timeout =
Avec les dernières versions de spring-boot, le passage à Hikari peut se faire entièrement en configuration. J'utilise 1.5.6.RELEASE
et cette approche fonctionne.
build.gradle:
compile "com.zaxxer:HikariCP:2.7.3"
application YAML
spring:
datasource:
type: com.zaxxer.hikari.HikariDataSource
hikari:
idleTimeout: 60000
minimumIdle: 2
maximumPoolSize: 20
connectionTimeout: 30000
poolName: MyPoolName
connectionTestQuery: SELECT 1
Modifiez connectionTestQuery
pour l'adapter à votre base de données sous-jacente. C'est ça, pas de code requis.
Cela aidera tous ceux qui souhaitent configurer hikaricp pour leur application avec la configuration automatique du ressort. Pour mon projet, j'utilise spring boot 2 avec hikaricp comme pool de connexions JDBC et mysql comme base de données. Une chose que je n’ai pas vue dans d’autres réponses est le data-source-properties
qui peut être utilisé pour définir diverses propriétés qui ne sont pas disponibles dans le chemin spring.datasource.hikari.*
. Cela équivaut à utiliser la classe HikariConfig
. Pour configurer le pool de connexions de source de données et hikaricp pour les propriétés spécifiques à mysql, j'ai utilisé l'annotation Spring Print automatique et les propriétés suivantes du fichier application.yml.
Placez @EnableAutoConfiguration
sur l’un de vos fichiers de bean de configuration.
application.yml fichier peut ressembler à ceci.
spring:
datasource:
url: 'jdbc:mysql://127.0.0.1:3306/DATABASE?autoReconnect=true&useSSL=false'
username: user_name
password: password
hikari:
maximum-pool-size: 20
data-source-properties:
cachePrepStmts: true
prepStmtCacheSize: 250
prepStmtCacheSqlLimit: 2048
useServerPrepStmts: true
useLocalSessionState: true
rewriteBatchedStatements: true
cacheResultSetMetadata: true
cacheServerConfiguration: true
elideSetAutoCommits: true
maintainTimeStats: false