Sebastian
Sebastian

Reputation: 17443

How to render partial responses with Akka HTTP

I would like to render partial response using Akka HTTP. In the request the client should specify which fields to include in the response (e.g. using a fields request parameter, for example: https://www.acme.com/api/users/100?fields=id,name,address).

I would appreciate any pointers on how to solve this.

Upvotes: 1

Views: 173

Answers (1)

Akka http provides a useful DSL known as Directives to solve these types of problems. You can match on a particular path and then extract the HttpRequest query string for the "fields" key:

import akka.http.scaladsl.server.Directives._

val route = get {
  path("api" / "users" / IntNumber) { pathInt =>
    parameter('fields) { fields =>
      complete(generateResponse(pathInt, fields))
    }
  }
}

For the given example request ("https://www.acme.com/api/users/100?fields=id,name,address") the generateResponse function will be called with 100 and id,name,address as the input variables. Say you have some lookup table of the values:

case class Person(id : String, name : String, address : String, age : Int)

val lookupTable : Map[Int, Person] = ???

You can then use this lookup table to get the person and extract the appropriate fields:

def personField(person : Person)(field : String) = field match {
  case "id" => s"\"id\" = \"${person.id}\""
  case "name" => s"\"name\" = \"${person.name}\""
  ...
}

//generates JSON responses
def generateResponse(key : Int, fields : String) : String = {

  val person = lookupTable(key)

  "{ " + 
  fields
    .split(",")
    .map(personField(person))
    .reduce(_ + " " + _)
  + " }"
}

Upvotes: 2

Related Questions