In the previous chapter, you were introduced to the process of creating a new Java project and, utilizing the capabilities of Apache Maven, adding the MariaDB R2DBC driver as a dependency to the project. Now that you’ve successfully created an application capable of taking advantage of an R2DBC implementation, it’s time to dive into the capabilities of the specification.
In this chapter, we’re going to expand on that project to examine the Connection object implementations available in the driver. Before continuing, if you haven’t done so yet, I highly recommend reading Chapter 4, which dives into much greater detail on the R2DBC specification connection hierarchy and workflow.
Configuration
For the purposes of this chapter, I’m going to be highlighting what I would consider conventional connection parameters for examples of how to establish a connection to MariaDB. More specifically, I’ll be providing examples that target a local database instance.
To run a program locally means to run it on the machine you are sitting at (or to run it on the same machine it is running on itself), as opposed to causing it to run on some remote machine.
Beyond this sample, if you’d like more information on the configuration options available for MariaDB, or any other DBMS, I highly suggest checking out the official MariaDB documentation.
Database Connectivity
In the last chapter, we walked through the process of getting a database instance up and running on your machine. This was done so that you have access to a MariaDB database instance that you can use to test the capabilities of the MariaDB R2DBC driver. I specifically provided guidance on setting up a local database instance as it requires minimal configuration information in order to establish a connection.
Sample connection parameters
Property | Value | Description |
---|---|---|
Hostname | 127.0.0.1 | The IP address, or domain, of your MariaDB Server. The default IP address for a local database instance is 127.0.0.1. |
Port | 3306 | Port numbers are used as a way to identify how specific processes are to be forwarded. The default port number for MariaDB is 3306. |
Username | app_user | The username needed to connect to a MariaDB database instance. |
Password | Password123! | The password needed to connect to a MariaDB database instance. |
In Chapter 11, I provided SQL statements for creating a new user, app_user, with the password Password123! for a MariaDB database instance. While it’s certainly possible to use any credentials you want, for the sake of simplicity and consistency, I will be using app_user for all connection code settings in this book.
Driver Implementation and Extensibility
As you can see in Table 12-1, the information is minimal. This helps you on two fronts. One, it provides you with the simplest approach to connecting to a MariaDB database. And, two, the requirement of a host, port number, username, and password is something that is common among all other relational databases and, thus, is an example that can be applied to other database vendors and their corresponding R2DBC driver implementations.
Running Reactive Code
Before continuing, it’s important to note that many of the examples going forward in this book will be using non-blocking method execution, such as the subscribe method .
Because we will be using a simple console application, which utilizes a single class and main method, it’s possible, due to the nature of asynchronous event-driven communication, that the application may complete execution before publishers send information to their subscribers.
As a possible workaround, and an approach I’ll be utilizing throughout the next several chapters, code can be added to keep the application running by blocking the current thread.
Keep the current thread threading to allow time for publishers and subscribers to complete processing
The code block from Listing 12-1 is merely a workaround for demonstration purposes. It is unlikely that you’ll want to use such code within more practical, or “real-world,” solutions.
Establishing Connections
In Chapter 4, you learned that the creation of R2DBC Connection object implementations is managed through ConnectionFactory object implementations of a driver.
Before proceeding, it’s important to note that the MariaDB R2DBC driver implements the full hierarchy of connection interfaces and provides a simple naming convention for each of the objects by preceding the names of each object with “Mariadb.” Thus, the driver implements the Connection and ConnectionFactory interfaces as MariadbConnection and MariadbConnectionFactory, respectively.
This type of naming convention is common for other R2DBC driver implementations.
Obtaining MariadbConnectionFactory
Above all else, the MariadbConnectionFactory object is used to manage MariadbConnection objects. Of course, in order to be able to manage MariadbConnection objects, they need to exist, and before that you’ll need to get your hands on a ConnectionFactory implementation. The MariaDB driver provides three approaches for obtaining MariadbConnectionFactory.
Creating a New Connection Factory
Creating a new MariadbConnectionFactory object using MariadbConnectionConfiguration
MariadbConnectionConfiguration
The MariadbConnectionConfiguration class is specific to the MariaDB driver in that it doesn’t derive from or implement an entity that exists within the R2DBC SPI.
However, the [DriverName]ConnectionConfiguration object is common among every driver implementation to date, but not only because of the naming convention. Connection configuration objects function to manage both standard and vendor-specific connectivity options.
Example MariadbConnectionConfiguration getter method usages
Connection configuration objects also provide a sort of bridge, through ConnectionFactoryProvider implementations, to assist in the ConnectionFactory implementation discovery process using the ConnectionFactoryOptions class.
ConnectionFactory Discovery
Harkening again back to Chapter 4, remember that ConnectionFactories, a class within the R2DBC SPI, provides two ways, both using the get method, to retrieve a driver ConnectionFactory implementation.
Retrieving an existing MariadbConnectionFactory object using a ConnectionFactoryOptions object
Remember that in Chapter 11 I provided you with the SQL commands for adding a new user, app_user, to a MariaDB database instance.
Retrieving an existing MariadbConnectionFactory object using an R2DBC connection URL
Ultimately, the R2DBC URL is parsed to create a ConnectionFactoryOptions object that is then used by the ConnectionFactories class to obtain a ConnectionFactory just as it did in Listing 12-4.
Creating a Connection
Creating a new database connection
A Mono is a Reactive Streams Publisher object implementation, provided by the Project Reactor library, with the specific intention of streaming 0–1 elements.
Notice that the ConnectionFactory interface’s create method returns a Mono<MariadbConnection>, which is a Project Reactor implementation of the Reactive Streams API’s Publisher<T> and the R2DBC specification’s Publisher<Connection>.
And remember that due to the nature of event-based development, there’s no telling when the MariadbConnection object will be published. Because of that, it may be useful, in certain situations, to wait for the publisher to send a Connection object before proceeding.
Creating and waiting on a new database connection
Validating and Closing Connections
After obtaining a MariadbConnection object , you can use the validate method to, yep, you guessed it, check whether the connection is still valid.
Validating a connection
This example shows the usage of ValidationDepth.LOCAL, because of the local connection. For more information on ValidationDepth options, be sure to check out Chapter 4.
Closing a connection
Putting It All Together
The complete connection sample
The resulting output from executing the code in Listing 12-10
The code in Listing 12-10, while very simple, provides foundational connection functionality that I’ll continue to expand on in upcoming chapters.
Metadata
Lastly, it’s possible to inspect information, or metadata, about the ConnectionFactory and Connection object implementations (Listing 12-12, Listing 12-13).
Using MariadbConnectionFactoryMetadata
Using MariadbConnectionMetadata
Show Me the Code
You can find a complete, fully compilable sample application in the GitHub repository dedicated to this book. If you haven’t done so already, simply navigate to https://github.com/apress/r2dbc-revealed to either git clone or directly download the contents of the repository. From there you can find a sample application dedicated to this chapter in the ch12 folder.
Summary
There’s no doubt that the ability to connect to a data source is one of the, if not the most, important capabilities of a database driver. This chapter is crucial for taking the theoretical information you learned about in Chapter 4 and seeing it in action through the use of a driver implementation.
In this chapter, you gained an understanding of how to use the MariaDB R2DBC driver to create and manage database connections. The foundation provided in this chapter will be incredibly useful for upcoming chapters where we’ll dive into concepts like statement execution, transaction management, connection pooling, and many more.