---
title: Javalin Part 2
url: https://calvin.my/posts/javalin-part-2
published: 2024-09-05
updated: 2026-09-17
category: Development
tags:
- Javalin
- Kotlin
- Gradle
- Web
summary: Part two of the Javalin introduction explains how to deliver common web content from a Kotlin application. It covers serializing object collections as JSON, configuring classpath directories for static assets, and returning explicit HTTP statuses such as a JSON-formatted not-found response. The article also outlines enabling HTTPS with a self-signed certificate, placing certificate files in application resources, and registering Javalin’s SSL support for local testing.
---

# Javalin Part 2

This article is Part 2 of Javalin 101. It shows the steps to serve a few common type of web content.

## JSON responses

1. To render JSON response, we need to serial/deserialize Kotlin object. There are a few options, such as Jackson.

   ```kotlin
   dependencies {
      ...
       implementation("com.fasterxml.jackson.module:jackson-module-kotlin:2.17.+")
   }
   ```

2. A list of objects can be constructed using "listof" and "mapOf".

   ```kotlin
   app.get("/promotions") { ctx ->
           val promotions = listOf(
               mapOf(
                   "name" to "Promo 1",
                   "description" to "Promo 1 description",
                   "discount" to 10
               ),
               mapOf(
                   "name" to "Promo 2",
                   "description" to "Promo 2 description",
                   "discount" to 20
               )
           )
           ctx.json(promotions)
       }
   ```

3. This gives you a JSON response such as the following.

   ![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/4cd58369-6d23-40a5-b382-39de1cbf68b3.png)
* * *
## Static files

1. Some configuration must be added to serve static files, including the directory and location.

   ```kotlin
   val app = Javalin.create { config ->
           config.staticFiles.add { staticFiles -> {
                   staticFiles.directory = "/public"
                   staticFiles.location = Location.CLASSPATH
               }
           }
       }.start(7777)
   ```

2. Next, create your directory within the application's classpath.

   ![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/32eef90d-58b3-4aea-a861-cbd4a7a8ed60.png)

3. Place the static file into the directory and try to access the URL.

   ![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/565dca83-b3eb-4a04-9548-e4b8ce6387b2.png)
* * *
## Specific Response Code

1. Create an endpoint and specify the status as 404.

   ```kotlin
   app.get("/notfound") { ctx -> ctx.status(404).json(mapOf("message" to "Not found")) }
   ```

2. This gives you a 404 error with a JSON body.

   ![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/f528d424-cdce-4686-978d-43404ae3d5a9.png)
* * *
## Secure with Self-Signed Cert

1. Create and enroll [self-signed cert](../posts/using-a-self-signed-ssl-cert-on-macos).

2. Copy certificate and key to your resources directory

   ![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/1b43ecd2-9941-4fd5-8d00-f6d18266b4c3.png)

3. Add the Javalin SSL plugin

   ```kotlin
   dependencies {
       ...
       implementation("io.javalin.community.ssl:ssl-plugin:6.3.0")
   }
   ```

4. Register the plugin with cert

   ```kotlin
       val app = Javalin.create { config ->
           config.staticFiles.add { staticFiles -> {
                   staticFiles.directory = "/public"
                   staticFiles.location = Location.CLASSPATH
               }
           }
           config.registerPlugin(SslPlugin{ sslConfig ->
               sslConfig.pemFromClasspath(
                   "certs/certificate.pem",
                   "certs/key.pem",
                   null
               )
           })
       }.start()
   ```

5. Run and test the application on https.

   ![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/391ed34a-82e6-4061-b987-4b3e4d404f23.png)
