Redis — Using master node to save and replicas nodes to read with Springboot.
Redis is an open source (BSD licensed), in-memory data structure store, used as a database, cache, and message broker. Redis provides data structures such as strings, hashes, lists, sets, sorted sets with range queries, bitmaps, hyperloglogs, geospatial indexes, and streams. Redis has built-in replication, Lua scripting, LRU eviction, transactions, and different levels of on-disk persistence, and provides high availability via Redis Sentinel and automatic partitioning with Redis Cluster. (redis.io)
What expect ?
On this article you will learn how to setup a Redis cluster using one principal master node to save data and two instances to read the data, using docker-compose.
We will create a Springboot application able to connect on these instances through two restful endpoints, one to write on master node and another to read on replicas nodes.
Problem
In order to not overload the master node with the main responsability to save and read data, we can provide performance sharing this tasks to a specific nodes.
Replication
At the base of Redis replication (excluding the high availability features provided as an additional layer by Redis Cluster or Redis Sentinel) there is a very simple to use and configure leader follower (master-slave) replication: it allows replica Redis instances to be exact copies of master instances. The replica will automatically reconnect to the master every time the link breaks, and will attempt to be an exact copy of it regardless of what happens to the master. (https://redis.io/topics/replication).
Advantages
- Non-blocking replication.
- Avoid the effort of master to persist and read the data.
- Asynchronous replication.
- High performance.
- Low latency.
Architecture
The Redis master/replica architecture will be like the image below.
Hands-on
Docker Compose
First we started creating a docker-compose.yml file on the root directory.
The Redis setup will be divided in three instances using 6.0.9 version.
- First instance: master, running on default port 6379
- Second instance: replica-1, running on port 6380.
- Third instance: replica-2, running on port 6381.
On the replicas configuration we set a command with parameter to tell the instance that it will be a slave of master.
The last step, redis-commander, is a useful graphical tool to interact with Redis.
Executing
$ docker-compose up
Redis Commander
Redis-Commander is a node.js web application used to view, edit, and manage a Redis Database. (Redis Commander)
Browser: http://localhost:8081/
Adding new key
- Click on master
- Click on Add New Key to test
The keys will be reflected on replicas (double click on nodes)
Application
We start building our application on spring initializr. Three dependencies needed:
- Spring Data Redis: connect to Redis.
- Spring Web: restful endpoints to receive requests.
- Lombok: productivity.
Click on Generate, download the zip file and extract to a workspace.
Importing the project on IDE
Setting Redis instances on application.yml:
RedisConfig.java
RedisController.java
Now you can run your Springboot application.
Writing on Redis
Through the localhost endpoint, you can write data on master instance.
Eg.: Endpoint/transaction_name
http://localhost:8080/login
http://localhost:8080/transfer
http://localhost:8080/password_change
Reading from Redis
Use get endpoint to retrieve all the items storaged on a key.
Browse: http://localhost:8080/get
Can also be checked on redis commander.
Validating
On this step, we can stop only the master instance, responsible to save the data and call get endpoint to validate the read nodes are still responding the calls.
$ docker-compose stop master
If you try to save a new transaction, you will get an error because the master instance is down. However you are able to retrieve all the values.
Conclusion
If your application expect to receive a massive calls to write/read on Redis and you are looking for a better performance, consider creating a specific node to each task.
Full Source Code
All the source code and the project can be downloaded on the git repository below.
References:
https://redis.io/
https://redis.io/topics/replication
https://joeferner.github.io/redis-commander/
https://start.spring.io/