Tayeb Chlyah is a Java lead architect with solid experience on performance large-scale applications, microservices, and NoSQL databases. He has developed a couple of open source Java libraries for Couchbase.

 

Introduction

Every successful developer needs to keep up to date with cutting-edge new technologies and emerging trends, trying them, playing with them, seeing if they can fit into a project, and how they can improve upon them.

But how can one achieve that in a fast-changing world where new technologies and frameworks are born daily?

If you are a Java full-stack developer, you are very lucky: JHipster is the solution to quickly apprehend new technologies in best way. It is a Yeoman generator, a scaffolding system, that helps you generate complete applications combining one of the best frameworks in web development: Spring Boot backend and Angular or React frontend.

Of course, you can use Spring Initialzr, or implement everything by yourself, but to successfully implement those combinations is not trivial at all. You need to spend a lot of time studying each concept, and then try to glue everything together, without forgetting tests, which can be very expensive and error-prone. And most of all, it can discourage you or, at best, oblige you to focus on one of the frameworks.

JHipster builds fully tested applications quickly and easily, using best practices, methodologies, and strategies. It proposes a lot of options (Architecture monolith or microservices; Database SQL or NoSQL; Security session, JWT, or OAuth2 authentication; Other WebSocket, caches, Docker, Kubernetes …), which can help you try the best technologies out there, and choose the most suitable combinations for your use case.

Today we are going to focus on some of the most important new architectural concepts: microservices and NoSQL with Couchbase.

Why Couchbase?

Couchbase is a NoSQL document-oriented database. With document databases, you have a schemaless design which allows you to change your data freely and easily. You can also store the whole structure in a single document, avoiding lots of unnecessary joins, which means naturally faster read and write operations.

Couchbase exposes a fast key-value store and a powerful query engine along with built-in indexers to query data with N1QL, a SQL-like language for JSON documents. With its masterless distributed architecture, it is very easy to scale. It can deliver millions of operations per second without the need of a third-party cache to perform. Couchbase also comes with built-in full-text search, an analytics engine, and a complete mobile solution.

Why microservices?

Microservice architecture is a pattern of developing software systems that focus on building applications as a set of small, modular, and loosely coupled services, enabling easier continuous delivery, better testability, scalability, and improved fault isolation. Each service can be written in different languages and may use different data storage techniques, which enables the ability to organize development around multiple feature teams.

But microservices comes with some challenges: decomposing the application into services can be very complicated, and is very much an art. Developers also have to deal with the additional complexity of a distributed system.

JHipster handles most of the complexities of microservices: Service discovery and configuration with Consul or JHipster Registry (Netflix Eureka, Spring Cloud Config Server, and monitoring dashboard), load balancing with Netflix Ribbon, fault tolerance with Netflix Hystrix, and centralized logging and monitoring with jhipster-console (Elasticsearch, Logstash and Kibana personalized stack), and more.

Creating a brewery microservice

Prerequisites:

yarn global add generator-jhipster

Generate an API Gateway

In order to access our different services in a microservice architecture, we’re going to need an API Gateway. It is the entrance to your microservices. It provides HTTP routing (Netflix Zuul) and load balancing (Netflix Ribbon), quality of services (Netflix Hystrix), security (Spring Security), and API documentation (Swagger) for all microsevices.

In a terminal window:

JHipster asks about the type of application you want to create and what features you want to include. You can find all the details about available options on JHipster WebsiteUse the following answers in order to generate a gateway with Couchbase support.

Generate a brewery microservice application

In couchbase-jhipster-microservices-example, create a brewery directory, then run jhipster to generate a microservice with Couchbase database with the following answers:

Generate brewery entities

Create a file brewery.jh in couchbase-jhipster-microservices-example directory with the following JDL (JHipster Domain Language):

paginate Beer with pager
paginate Brewery with infinite-scroll

In a terminal window, run the following commands:

When asked to overwrite files, always answer a.

Run the microservice architecture

In order to run our architecture, we need to start the following:

  1. JHipster Registry
  2. Keycloack: an open source identity and access management solution
  3. Couchbase Server
  4. Brewery microservice
  5. Gateway

Fortunately, JHipster has a docker-compose sub-generator that will start all necessary services without headache. But first, we need to build our applications. In couchbase-jhipster-microservices-example:

Now, we can generate docker-compose.yml using the following command and answers:

In order to make our app work with a local keycloak, we need to add to your hosts file (Windows: C:\Windows\System32\drivers\etc\hosts, Mac/Linux: /etc/hosts) the following line:

Before starting everything, make sure you have configured Docker with enough memory and CPUs, then run:

Once everything finishes starting, open a browser to Gateway (http://localhost:8080/), click on account, then sign in.

You should be redirected to keycloak, log in using admin for both user and password.

You’ll return to the gateway, where you can see administration interfaces, change language, view and edit your entities…

 

 

JHipster-registry

Now open your browser to http://localhost:8761/. You’ll be automatically signed in since you have already done that in keycloak, which is the magic of oauth2 authentication.

Apart from being the backbone of your microservice application, as it is a discovery server with Eureka that handles routing, load balancing and scalability, and a configuration server with Spring Cloud Config Server that provides runtime configuration of your applications, JHipster registry is also an administration server, where you can visualize your application instances, health, metrics, and logs.

How does it work ?

Accessing the database

First, you need access to brewery-couchbase instance. In order to do so, update docker-compose/docker-compose.yml to publish its administration interface port with the following:

Let’s apply our changes, on docker-compose directory:

When everything is up, open Couchbase administration interface on http://localhost:8091/, then log in using Administrator as user and password as password. Open brewery bucket Documents.

Couchmove
As you can see, your bucket is already populated with some documents: JHipster populates bootstrap documents using Couchmove, a Java data migration library for Couchbase, widely inspired from Flyway, as it strongly favors simplicity and convention over configuration.

You can take a look on changelog files in

  • V0.1__initial_setup directory: contains user and authority documents, used by Spring Security to authenticate users.
  • V0__create_indexes.n1ql: creates needed indexes.

As Flyway or liquibase for SQL databases, Couchmove maintains changelog documents, keeping track of executed changelogs.

Spring Boot and Spring Data Couchbase

JHipster generates a Spring Boot 2 application, and uses Spring Data to access relational and non-relational databases. In our case, it is using Spring Data Couchbase to provide integration with the Couchbase Server database. But it goes much further by personalizing how it works:

By default, Spring Data Couchbase uses N1qlCouchbaseRepository.java which leverages N1QL only for paging or sorting findAll operations. All other operations are using views as you can see in the implementation of SimpleCouchbaseRepository.java. Since view indexes are always accessed from disk, they are not quite as performant.

Let’s see how JHipster improves this behavior:

DatabaseConfiguration class configures and starts Couchmove migrations, and also enables Couchbase Repositories but with a custom base class: CustomN1qlCouchbaseRepository

This class extends the default repository to auto-generate document ID before saving, and enables usage of N1QL for all operations by implementing CustomN1qlRespository interface:

Ids are auto generated using GeneratedValue annotation with a prefix using IdPrefix annotation, which by default is the name of the class, separated by __ delimiter.

Tests

We said earlier that JHipster-generated applications are fully tested with unit and integration tests, but how does it work for integration ones?

For Couchbase, it uses Couchbase testContainers, which is a module extending testcontainers, a Java library that makes it easy to launch any Docker containers for the duration of JUnit tests, in order to automatically start an instance of Couchbase Server, and configure it with the necessary services, users, buckets, and indexes.

In order to run the tests, run the following command in a terminal window:

Populate some data

In order to populate some data, we will take advantage of Couchbase Sample buckets. Open Settings tab, Sample Buckets, then select beer-sample, and click on Load Sample Data.

You need to shape data in Spring Data Couchbase serialization format. To do so, open Query tab, and execute the following queries:

Here is an example of an inserted beer document:

Now let’s see how JHipster handles newly inserted documents. Navigate to Gateway, Entities, then open Brewery. JHipster first loads 20 breweries, and if you scroll down, it loads more! It proposes page navigation for Beer entity, because we choose this behavior when generating entities with brewery.jh JDL.

Source code

The source code for generated applications is available at tchlyah/couchbase-jhipster-microservices-example.

What’s next?

JHipster, with the help of Elasticsearch, proposes an option that adds search capabilities on top of the database. But Couchbase has an out-of-the-box Full-Text Search feature that provides extensive capabilities for natural-language querying. Why not implement that support into JHipster? If you can help, don’t hesitate to contribute!

If you have any questions, tweet me at @tchlyah or leave a comment below.

Posted by Laura Czajkowski, Developer Community Manager, Couchbase

Laura Czajkowski is the Snr. Developer Community Manager at Couchbase overseeing the community. She’s responsible for our monthly developer newsletter.

Leave a reply