<installation directory>sqljdbc_<version><language>auth
spring-data-r2dbc
and r2dbc-mssql
doing all the heavy lifting. Depending on which database you want to use r2dbc-mssql
can be switched out for another database that has a R2DBC driver (for example r2dbc-postgresql
).AbstractR2dbcConfiguration
and implementing a ConnectionFactory
bean:ConnectionFactory
that contains (as the name suggests) details about the connection to the database. This bean is one component of the DatabaseClient
. This is an important class, as it is central to the execution of SQL within the Spring Data R2DBC module. The rest of the beans the DatabaseClient
is built from are created inside of AbstractR2dbcConfiguration
and fed into the client. Let Spring take the wheel ?? and you will be alright. In all seriousness extending AbstractR2dbcConfiguration
and implementing connectionFactory
will get your application up and running very quickly.@EnableR2dbcRepositories
annotation instructs Spring to find any repository interfaces that extend Spring’s Repository interface. This is used as the base interface for instrumenting Spring Data repositories. We will look at this a little closer in the next section.R2DBCRepository
, Spring will pick up these queries and instrument them as well as providing some typical queries for you, such as findByAllId
. This is where the @EnableR2dbcRepositories
annotation added earlier comes into play. Without this annotation then this repository will not do anything for you and would instead require a completely manual implementation.@Query
is used to define the query a function will provide, with Spring providing the implementation itself. The inputs passed into the query are defined using the format of @<parameter_name>
.Flux
objects returned from these functions are basically the reactive version of a List
. In other words, they return multiple values. These values will be returned and processed as they arrive as long as you have subscribed to the Flux
once it has been created.id
has been made nullable and has a default value of null
to allow Postgres to generate the next suitable value itself. If this is not nullable and an id
value is provided, Spring will actually try to run an update instead of an insert upon saving. There are other ways around this, but I think this is good enough. To be honest, this is a Kotlin specific problem. If you are using Java, then relax, you won’t need to worry about this. That being said, come to the light side and program in Kotlin, all your dreams will be fulfilled if you do (I cannot guarantee that will actually happen ?♂️).people
table defined below:Application
class below makes use of the queries written earlier as well as some that Spring Data provides out of the box.sleep
s have been added to ensure that the reactive code has a chance to work. Reactive applications are meant to do things asynchronously and therefore this application will process the function calls in different threads. Without blocking the main thread, these asynchronous processes might never fully execute. To keep everything tidy, I have removed the sleep
s from the example.onSubscribe
and request
occur on the main thread where the Flux
was called from. Only saveAll
outputs this since it has included the log
function. Adding this to the other calls would have lead to the same result of logging to the main thread.subscribe
function and the internal steps of the Flux
are ran on separate threads.Flux
function ???♀️.ConnectionFactory
and repository queries which will slightly differ between databases. I should probably mention the fact that R2DBC enables you to move towards more reactive applications. I mean this, this post is about R2DBC after all ?♀️. Utilising databases with R2DBC drivers and Spring modules will allow you to build a fully reactive application. Starting from the core of your application (the database) to the edges and endpoints exposed to external clients. Spring’s push for reactive applications as well as the improvements in the R2DBC drivers that are yet to come, will make this sort of transition (if appropriate to your business) less painful and faster to implement.db.properites
file here:<context:property-placeholder location='classpath:db.properties'/>
Where is it located in the project?