Categories
Scala

Run a Json REST API with Scala Http4s in 5 minutes

In this quick tutorial, we will show you how to run a Json REST API with Scala in 5 minutes and only 10 lines of code, thanks to the awesome Http4s library.

0) Prerequisites

You need java and sbt installed on your machine. In this tutorial, I am using Java 11 and Sbt 1.5.5.

1) Code folder

Create a project folder called api somewhere on your local machine. All the files needed for this tutorial will be created in this folder.

2) build.sbt

In your folder api, create a file named build.sbt, with following content:

val http4sVersion = "1.0-232-85dadc2"
val circeVersion = "0.14.1"
lazy val api = (project in file(".")).
  settings(
    scalaVersion := "2.12.4",
    libraryDependencies ++= Vector(
      "org.typelevel" %% "cats-effect" % "2.5.1"
    ) ++ Seq(
      "org.http4s" %% "http4s-dsl",
      "org.http4s" %% "http4s-blaze-server",
      "org.http4s" %% "http4s-circe"
    ).map(_ % http4sVersion) ++ Seq(
      "io.circe" %% "circe-core",
      "io.circe" %% "circe-generic",
      "io.circe" %% "circe-parser"
    ).map(_ % circeVersion))

3) Scala server code

Create a file with path:

api/src/main/scala/com/Server.scala

where api is the folder you created on your local machine at step 1). Write the following content in the Server.scala file:

package com

import cats.effect._
import io.circe.generic.auto._
import io.circe.syntax.EncoderOps

import org.http4s._
import org.http4s.circe._
import org.http4s.dsl.io._
import org.http4s.implicits._
import org.http4s.server.blaze._

import scala.concurrent.ExecutionContext.global

object Server {
  implicit val cs: ContextShift[IO] = IO.contextShift(global)
  implicit val timer: Timer[IO] = IO.timer(global)
  implicit val ce: ConcurrentEffect[IO] = IO.ioConcurrentEffect

  def main(args: Array[String]): Unit = {
    val server = BlazeServerBuilder[IO](global).bindHttp(8080, "localhost").withHttpApp(routes.orNotFound).resource
    server.use(_ => IO.never).unsafeRunSync()
  }

  case class Example(a: String, b: Int)

  val routes = HttpRoutes.of[IO] {
    case GET -> Root => Ok(Example("hello", 2).asJson)
  }
}

3) Sbt Assembly plugin

Create a file with path:

api/project/plugins.sbt

where api is the folder you created on your local machine at step 1). Write the following content in the plugins.sbt file:

addSbtPlugin("com.eed3si9n" % "sbt-assembly" % "0.15.0")

4) Build and run the API

First, let’s build the fat jar. To do this, open a terminal and go to the root of your api folder and run:

sbt assembly

You should now have the following file on your machine: api/target/scala-2.12/api-assembly-0.1.0-SNAPSHOT.jar . We are going to use this path to execute the Java command. To start the REST API, run this command in your terminal:

java -jar target/scala-2.12/api-assembly-0.1.0-SNAPSHOT.jar

Now, your API runs at localhost:8080. You can test it using curl (use another terminal to use curl. If you take over the current one, it will stop the API, and the curl command won’t work):

$ curl localhost:8080
{"a":"hello","b":2}

That’s it for this tutorial ! If you have any question, please leave a reply below, we answer within 24 hours.

Leave a Reply

Your email address will not be published. Required fields are marked *