Build REST API with Spring Boot and Kotlin
Tags: kotlin, spring, springboot, rest
Published: 2021-04-11 01:41:46

---
title: Build REST API with Spring Boot and Kotlin
published: true
date: 2021-03-20 03:00:06 UTC
description: Learn about building a simple micro-service application using Spring Boot and Kotlin. Dedicated support for Kotlin was introduced since Spring Framework 5.0
tags: kotlin, spring, springboot, rest
cover_image: https://dev-to-uploads.s3.amazonaws.com/uploads/articles/s4clq6ebl5l4fmmdjo31.jpg
canonical_url: https://theanirban.dev/build-rest-api-spring-boot-kotlin/
---

## 1. Overview
In this article, we're going to build a REST API using Spring Boot 2.x and Kotlin. Meanwhile, dedicated support for Kotlin was introduced since Spring Framework 5.0. We can read about the supported features in the official [Spring Framework documentation](https://github.com/spring-projects/spring-framework/wiki/Spring-Framework-Versions).

In particular, the application will expose data via a REST API and persist data in an embedded H2 database.

## 2. Use Case
We'll build Restful APIs for an employee information application. **A user can create, retrieve, update and delete an employee using this application**. An employee has an id, username, first name, last name, email id, and date of birth. Moreover, the username of an employee must be unique.

**We'll use an embedded H2 database as our data source along with JPA and Hibernate to access the data from the database**.

## 3. Setup
We can use the Spring Initializer tool to create a Spring Boot application. Besides, we can read about the other ways that we can create a Spring Boot project in the [blog post](https://theanirban.dev/how-to-create-a-spring-boot-project/).

**Subsequently, we will add Spring Web, Spring Data JPA, H2 Database, Spring Boot Devtools as the dependencies**. So now we have all the basic dependencies in the `build.gradle.kts` that will allow us to work with Spring Boot and Kotlin:

{% gist https://gist.github.com/anirban99/766f2ca4a72fba3634c17b9793c76281 %}

The Gradle build file also contains some essential plugins:
- The `kotlin-spring` compiler plugin is a wrapper on top of the `all-open` plugin. **The `all-open` compiler plugin ensures that the Kotlin classes are annotated and their members are `open`.** This makes it convenient to use libraries such as Spring AOP that require classes to be open unlike Kotlin classes and their members which are final by default.
- The `kotlin-jpa` compiler plugin is a wrapper on top of the `no-arg` plugin. **The `no-arg` compiler plugin generates a no-argument constructor for classes annotated with `Entity`, `MappedSuperclass`, and `Embeddable`.** This ensures that JPA (Java Persistence API) can instantiate the class since it expects a no-argument constructor defined for its entities.

{% gist https://gist.github.com/anirban99/cc3abf8610d39b9813cafa095d105de3 %}

### 3.1. Configure Database
We have to configure the H2 database properties so that Spring Boot can create a data source. To define such properties, we can use an external configuration. **Furthermore, we can define such external configuration using properties files, YAML files, environment variables, and command-line arguments**.

**In general, Spring Boot provides the `application.properties` file to define such database properties by default**. The properties file uses a key-value format.

**Alternatively, we can use YAML-based configuration files which use hierarchical data**. The YAML files significantly help to avoid repeated prefixes and make is more readable compared to the properties file:

{% gist https://gist.github.com/anirban99/833cfa625b8e58386ec7ef617c83d31c %}

We can also use the `application.yml` file to define hibernate properties:
- We set the `ddl-auto` property to `update`. It will update the database schema based on the modifications in the domain model in our application.
This default value is `create-drop` if we use an embedded database without any schema manager.
**In case we're using a schema manager such as Liquibase or Flyway, we should consider using `validate`.** It tries to validate the database schema according to the entities that we have created in the application and throws an error if the schema doesn’t match the entity specifications.
- The `show-sql` property enables logging of SQL statement.
- The `generate-ddl` property ensures whether to initialize the schema on startup.
- The `dialect` property ensures that Hibernate generates better SQL for the chosen database.

## 4. Domain Model - Kotlin Data class
**The domain model is the core part of the application**. We can create a domain model `Employee` using a data class.

**In addition, a `data class` in Kotlin automatically generates `equals/hashCode` pair, `toString`, and `copy` functions.** Besides, We don't need to define getter and setter methods like Java:

{% gist https://gist.github.com/anirban99/b8e4a261ee76a8e77a61efac0473de67 %}

- The `@Entity` annotation specifies that the class is an entity and mapped to a database table.
- The `@Table` annotation specifies the name of the database table that is used for mapping.
**If we use the `@Table` annotation without a table name, then Spring generates the table name from the class name**.
- The `@Id` annotation specifies the property which is the primary key in the entity class.
- The `@GeneratedValue` annotation specifies the generation strategies for the values of the primary keys.
- The `@Column` annotation specifies the mapped column for a persistent property. If we do not use the `@Column` annotation, then Spring generates the column name from the property name.

## 5. Repository
We're going to create a repository interface to interact with the database. **Moreover, the `EmployeeRepository` interface will extend from the `JpaRepository` interface**. This ensures that all the CRUD methods on the `Employee` entity are available:

{% gist https://gist.github.com/anirban99/7745ebba131517262973ef1f30745405 %}

- The `@Repository` annotation specifies that the class is a repository and represents the data access layer in our application.

## 6. Service
Now, we're going to create a service class that will provide the business logic. **Besides, the service layer can interact with the data access layer using JPA**.

We inject an instance of the `EmployeeRepository` via constructor in `EmployeeService`:

{% gist https://gist.github.com/anirban99/4cafa2d72fe7e1ef5132da0ba59f88e9 %}

- The `@Service` annotation specifies that the class is a service.
- The `getAllEmployees()` function can fetch a list of all employees.
- The `getEmployeesById()` function can fetch one employee based on the id. We provide the employee id as a parameter to the function.
- The `createEmployee()` function can create a new employee. We provide the required properties of the new employee as a parameter to the function.
- The `updateEmployeeById()` function can update the employee details based on the id. We provide both the employee id and the properties as parameters to the function.
- The `deleteEmployeesById()` function can delete an employee based on the id. We provide the employee id as a parameter to the function.

## 7. Controller
We implement the APIs for all the CRUD operations in the controller layer which invokes the underlying service.

We define a `EmployeeController` as our controller class. **In particular, it's a REST controller that provides endpoints for creating, manipulating, and deleting employees**.

The `EmployeeService` class is wired into the controller to return the values. Also, we reuse the entities as data transfer object for simplicity:

{% gist https://gist.github.com/anirban99/1d6a02f6103f08d20de3fefc5fce35ca %}

The `@RestController` annotation specifies that the class is a controller and capable of handling requests. It combines both the `@Controller` and `@ResponseBody` annotations.

**Spring provides several annotations to handle the different incoming HTTP requests like GET, POST, PUT and DELETE**. These annotations are `@GetMapping`,`@PostMapping`,`@PutMapping`, and `@DeleteMapping`.

## 8. Running the application
We can run the application using the following command in the terminal:

```Bash
gradle bootRun
```

The Spring Boot application will start running at http://localhost:8080.

## 9. Exploring the APIs
### 9.1. Create an Employee
We send the following request to create an employee:
{% gist https://gist.github.com/anirban99/f98f76f255fc229a7f397566948462e7 %}

We receive the following response in JSON format:
{% gist https://gist.github.com/anirban99/b562f3d9085babcbde9fb7c4b74a3697 %}

### 9.2. Get All Employees
We send the following request to fetch all employees:
{% gist https://gist.github.com/anirban99/c96743fe05ede0aff85a6ee693ad512b %}

We receive the following response in JSON format:
{% gist https://gist.github.com/anirban99/bf248d76f382d7d189789483f9450db5 %}

### 9.3. Get an Employee
We send the following request to fetch an employee based on the employee id:
{% gist https://gist.github.com/anirban99/1a2be23a14956343f3ffb53fde0741b0 %}

We receive the following response in JSON format:
{% gist https://gist.github.com/anirban99/ae7066e435aeae32718ca979fb5c24e1 %}

### 9.4. Update an Employee
We send the following request to update employee properties based on the employee id:
{% gist https://gist.github.com/anirban99/86f178b22c50cddef9e5a467154cf7c1 %}

We receive the following response in JSON format:
{% gist https://gist.github.com/anirban99/e60f1081ebc672230ed788785876a9fe %}

### 9.5. Delete an Employee
We send the following request to delete an employee based on the employee id:
{% gist https://gist.github.com/anirban99/a4a934508ce4ff8636e3b9e7b36c27c6 %}

## 10. Conclusion
In this tutorial, we looked into creating a microservice application and expose REST API using Kotlin and Spring Boot. In the process, I have also used some best practices which we can utilize while building such applications.

The code for these examples is available on [GitHub](https://github.com/anirban99/spring-boot-examples/tree/main/spring-boot-boilerplate).

To learn more, check out the [related articles](https://theanirban.dev/categories/spring-boot) on Spring Boot.

_Originally published on [Anirban's Tech Blog](https://theanirban.dev/)_.