I have an example SpringBoot app in Kotlin and WebFlux. I divided whole application into modules (as I'm used to from asp.net).
Modules:
- core (models, DTO, helpers, etc...) referenced everywhere
- data (repositories, tables...) referenced only in business
- business (services, handlers...) referenced in api
- api actual SpringBoot application
My problem now is how to properly work with ReactiveCrudRepository<> and repositories in general. I have config class in data module to enable R2dbcRepositories.
@Configuration
@EnableR2dbcRepositories("me.janam.data")
open class RepositoriesConfiguration {
}
Now if I create table and repository
interface IPersonRepository: ReactiveCrudRepository<PersonTable, Long> {
@Query("SELECT * FROM person.person limit 1")
fun getOne(): Mono<PersonTable>
}
and try to use it in business module I'm getting an error
Cannot access 'org.springframework.data.repository.reactive.ReactiveCrudRepository' which is a supertype of 'me.janam.data.features.person.repositories.IPersonRepository'. Check your module classpath for missing or conflicting dependencies
Of course if I add
implementation("org.springframework.data:spring-data-commons:2.4.6")
into my business module everything works fine. But somehow this feels strange to me. Is this the right way how to do this?
Also not part of my main question but here is complete config and I like to hear some opinion on it as i'm mainly asp.net dev. Thx.
root - settings.gradle.kts:
rootProject.name = "springboot-example"
include(":api")
include(":business")
include(":data")
include(":core")
root - gradle.properties:
kotlin.code.style=official
kotlin_version=1.4.31
kotlinx_coroutines_reactor_version=1.4.3
r2dbc_postgresql_version=0.8.7.RELEASE
postgresql_version=42.2.19
spring_context_version=5.3.5
root - build.gradle.kts:
import org.jetbrains.kotlin.gradle.tasks.KotlinCompile
plugins {
kotlin("jvm") version "1.4.31"
id("io.spring.dependency-management") version "1.0.11.RELEASE"
}
subprojects {
apply(plugin = "io.spring.dependency-management" )
dependencyManagement {
}
}
group = "me.janam"
version = "1.0-SNAPSHOT"
repositories {
mavenCentral()
}
dependencies {
//implementation("org.springframework:spring-context:5.3.5")
testImplementation(kotlin("test-junit5"))
testImplementation("org.junit.jupiter:junit-jupiter-api:5.6.0")
testRuntimeOnly("org.junit.jupiter:junit-jupiter-engine:5.6.0")
}
tasks.test {
useJUnitPlatform()
}
tasks.withType<KotlinCompile>() {
kotlinOptions.jvmTarget = "13"
}
core - build.gradle.kts:
import org.jetbrains.kotlin.gradle.tasks.KotlinCompile
plugins {
kotlin("jvm")
}
group = "me.janam"
version = "1.0-SNAPSHOT"
repositories {
mavenCentral()
}
dependencies {
testImplementation(kotlin("test-junit5"))
testImplementation("org.junit.jupiter:junit-jupiter-api:5.6.0")
testRuntimeOnly("org.junit.jupiter:junit-jupiter-engine:5.6.0")
}
tasks.test {
useJUnitPlatform()
}
tasks.withType<KotlinCompile>() {
kotlinOptions.jvmTarget = "13"
}
data - build.gradle.kts:
import org.jetbrains.kotlin.gradle.tasks.KotlinCompile
val kotlinx_coroutines_reactor_version: String by project
val r2dbc_postgresql_version: String by project
val postgresql_version: String by project
val spring_context_version: String by project
plugins {
kotlin("jvm")
}
group = "me.janam"
version = "1.0-SNAPSHOT"
repositories {
mavenCentral()
}
dependencies {
implementation(project(":core"))
implementation("org.springframework:spring-context:$spring_context_version")
implementation("org.springframework.boot:spring-boot-starter-data-r2dbc:2.4.4")
runtimeOnly("io.r2dbc:r2dbc-postgresql:$r2dbc_postgresql_version")
runtimeOnly("org.postgresql:postgresql:$postgresql_version")
implementation("org.jetbrains.kotlinx:kotlinx-coroutines-reactor:$kotlinx_coroutines_reactor_version")
testImplementation(kotlin("test-junit5"))
testImplementation("org.junit.jupiter:junit-jupiter-api:5.6.0")
testRuntimeOnly("org.junit.jupiter:junit-jupiter-engine:5.6.0")
}
tasks.test {
useJUnitPlatform()
}
tasks.withType<KotlinCompile>() {
kotlinOptions.jvmTarget = "13"
}
business - build.gradle.kts:
import org.jetbrains.kotlin.gradle.tasks.KotlinCompile
val kotlinx_coroutines_reactor_version: String by project
val spring_context_version: String by project
plugins {
kotlin("jvm")
}
group = "me.janam"
version = "1.0-SNAPSHOT"
repositories {
mavenCentral()
}
dependencies {
implementation(project(":core"))
implementation(project(":data"))
implementation("org.springframework:spring-context:$spring_context_version")
implementation("org.jetbrains.kotlinx:kotlinx-coroutines-reactor:$kotlinx_coroutines_reactor_version")
implementation("org.springframework.data:spring-data-commons:2.4.6") //TODO
testImplementation(kotlin("test-junit5"))
testImplementation("org.junit.jupiter:junit-jupiter-api:5.6.0")
testRuntimeOnly("org.junit.jupiter:junit-jupiter-engine:5.6.0")
}
tasks.test {
useJUnitPlatform()
}
tasks.withType<KotlinCompile>() {
kotlinOptions.jvmTarget = "13"
}
api - build.gradle.kts:
import org.jetbrains.kotlin.gradle.tasks.KotlinCompile
plugins {
id("org.springframework.boot") version "2.4.4"
// Přesunuto do rootu
id("io.spring.dependency-management")
kotlin("jvm")
kotlin("plugin.spring") version "1.4.31"
}
group = "me.janam"
version = "1.0-SNAPSHOT"
//java.sourceCompatibility = JavaVersion.VERSION_13
repositories {
mavenCentral()
}
dependencies {
implementation(project(":core"))
implementation(project(":business"))
//implementation("org.springframework.boot:spring-boot-starter-data-r2dbc")
implementation("org.springframework.boot:spring-boot-starter-rsocket")
implementation("org.springframework.boot:spring-boot-starter-webflux")
implementation("com.fasterxml.jackson.module:jackson-module-kotlin")
implementation("io.projectreactor.kotlin:reactor-kotlin-extensions")
implementation("org.jetbrains.kotlin:kotlin-reflect")
implementation("org.jetbrains.kotlin:kotlin-stdlib-jdk8")
implementation("org.jetbrains.kotlinx:kotlinx-coroutines-reactor")
//runtimeOnly("io.r2dbc:r2dbc-postgresql")
//runtimeOnly("org.postgresql:postgresql")
testImplementation("org.springframework.boot:spring-boot-starter-test")
testImplementation("io.projectreactor:reactor-test")
}
tasks.withType<KotlinCompile> {
kotlinOptions {
freeCompilerArgs = listOf("-Xjsr305=strict")
jvmTarget = "13"
}
}
tasks.withType<Test> {
useJUnitPlatform()
}