Проблема с расширением приложения Spring WebFlux с помощью реактивного клиента БД: конфликтующие зависимости Maven?
У меня есть небольшое рабочее приложение Spring WebFlux, созданное на основе этого кода:
https://github.com/chang-chao/spring-webflux-reactive-jdbc-sample
Насколько я понял, это некая смесь чисто реактивного программирования и обычных блокирующих реляционных баз данных.
Теперь у меня есть задача добавить в приложение реактивного клиента БД. Я смотрел это руководство:
https://spring.io/guides/gs/accessing-data-r2dbc/
Но как только я добавил в свой pom.xml следующие зависимости:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-r2dbc</artifactId>
<version>2.3.4.RELEASE</version>
</dependency>
<dependency>
<groupId>io.r2dbc</groupId>
<artifactId>r2dbc-h2</artifactId>
<version>0.8.4.RELEASE</version>
<scope>runtime</scope>
</dependency>
мое РАБОЧЕЕ приложение не могло начать говорить, что не может найти bean-компонент репозитория с автоматическим подключением. Эта ошибка исчезла, как только я удалил две зависимости выше.
Первоначальный полный pom.xml РАБОЧЕГО приложения:
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.3.4.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.freelance</groupId>
<artifactId>studentlist</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>student-list</name>
<description>Spring WebFlux application for managing students</description>
<properties>
<java.version>11</java.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-webflux</artifactId>
<version>2.3.4.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
<version>2.3.4.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<version>2.3.4.RELEASE</version>
<scope>test</scope>
<exclusions>
<exclusion>
<groupId>org.junit.vintage</groupId>
<artifactId>junit-vintage-engine</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>io.projectreactor</groupId>
<artifactId>reactor-test</artifactId>
<version>3.3.10.RELEASE</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>com.h2database</groupId>
<artifactId>h2</artifactId>
<version>1.4.200</version>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
Я предполагаю, что некоторые зависимости конфликтуют друг с другом. Есть ли способ действительно использовать эти зависимости со всеми моими другими зависимостями, чтобы я мог следовать этому руководству?
Я не знаю, нужен ли Java-код приложения для этого вопроса, и если да, то какие. А пока я просто добавлю application.properties:
spring.h2.console.enabled=true
spring.h2.console.path=/h2_console
spring.datasource.url=jdbc:h2:~/studentlist
spring.datasource.platform=h2
spring.datasource.initialization-mode=always
spring.datasource.username=sa
spring.datasource.password=
spring.datasource.driverClassName=org.h2.Driver
spring.jpa.generate-ddl=true
spring.jpa.database-platform=org.hibernate.dialect.H2Dialect
spring.jpa.hibernate.ddl-auto = update
spring.jpa.show-sql=true
logging.level.org.springframework=warn
logging.level.org.hibernate.type.descriptor.sql.BasicBinder=trace
logging.level.org.hibernate.SQL=warn
logging.level.io.netty=warn
spring.datasource.maximum-pool-size=100
Добавляя любую из этих двух зависимостей,
spring-boot-starter-data-r2dbc
или же
r2dbc-h2
, без второго достаточно, чтобы вызвать эту ошибку:
2020-10-20 15:31:26.008 WARN 11580 --- [ main] onfigReactiveWebServerApplicationContext : Exception encountered during context initialization - cancelling refresh attempt: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'studentController': Unsatisfied dependency expressed through field 'studentService'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'studentService': Unsatisfied dependency expressed through field 'studentRepository'; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type 'com.freelance.studentlist.repository.StudentRepository' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {@org.springframework.beans.factory.annotation.Autowired(required=true)}
2020-10-20 15:31:26.123 ERROR 11580 --- [ main] o.s.b.d.LoggingFailureAnalysisReporter :
***************************
APPLICATION FAILED TO START
***************************
Description:
Field studentRepository in com.freelance.studentlist.service.StudentServiceImpl required a bean of type 'com.freelance.studentlist.repository.StudentRepository' that could not be found.
The injection point has the following annotations:
- @org.springframework.beans.factory.annotation.Autowired(required=true)
Action:
Consider defining a bean of type 'com.freelance.studentlist.repository.StudentRepository' in your configuration.
Process finished with exit code 1
Я удалил зависимость JPA и сейчас пытаюсь заставить все работать только с r2dbc.
Я полагаю, что мое application.properties больше не будет действительным. Не могли бы вы помочь мне изменить его? Я использую этот фрагмент кода из руководства:
public class R2DBCConfiguration extends AbstractR2dbcConfiguration {
@Bean
public H2ConnectionFactory connectionFactory() {
return new H2ConnectionFactory(
H2ConnectionConfiguration.builder()
.url("jdbc:h2:~/studentlist;DB_CLOSE_DELAY=-1;TRACE_LEVEL_FILE=4")
.username("sa")
.build());
}
}
Я сильно подозреваю, что такие
url
не действует для r2dbc. Что было бы действительной заменой для
jdbc:h2:~/studentlist
URL в случае r2dbc H2 (не в памяти, а только в локальной БД)?
Как мне изменить этот блок кода в application.properties? URL в частности!
**spring.datasource.url=jdbc:h2:~/studentlist**
spring.datasource.platform=h2
spring.datasource.initialization-mode=always
spring.datasource.username=sa
spring.datasource.password=
spring.datasource.driverClassName=org.h2.Driver
Пожалуйста, помогите, если знаете! Не могу пока найти подходящий пример в Google...
1 ответ
В
spring.datasource
для традиционного источника данных Jdbc, для настройки соединения R2dbc используйте
spring.r2dbc
префикс вместо этого в Spring Boot application.properties.
Посмотрите мой пример Spring R2dbc, если вы новичок в Spring Data R2dbc, документацию в Readme.md.