hseeberger / akka-http-json

Integrate some of the best JSON libs in Scala with Akka HTTP

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

How does this work with the Client?

i-am-the-slime opened this issue · comments

I was thinking with the right import
import de.heikoseeberger.akkahttpcirce.FailFastCirceSupport._
I should be able to say:

.withEntity(
      MyCaseClassForWhichIHaveACirceEncoder(7, "Hi")
 )

On an HttpRequest. But I can't.

More context please.

I am trying to use the akka http client in conjunction with this library (the circe version).
However I am not able to supply instances to the HttpRequest via the withEntity method.

Something like this:

import de.heikoseeberger.akkahttpcirce.FailFastCirceSupport._
final case class MyCaseClass(i:Int, s:String)
object MyCaseClass { implicit val d:io.circe.Encoder[MyCaseClass] = ??? }
HttpRequest(
      HttpMethods.POST,
      Uri("http://httpbin.org/post")
    ).withEntity(MyCaseClass(7, "Hi"))

This tells me:

overloaded method value withEntity with alternatives:
[error]   (entity: akka.http.scaladsl.model.MessageEntity)akka.http.scaladsl.model.HttpRequest <and>
[error]   (entity: akka.http.javadsl.model.RequestEntity)akka.http.scaladsl.model.HttpRequest <and>
[error]   (bytes: akka.util.ByteString)akka.http.scaladsl.model.HttpRequest <and>
[error]   (bytes: Array[Byte])akka.http.scaladsl.model.HttpRequest <and>
[error]   (string: String)akka.http.scaladsl.model.HttpRequest
[error]  cannot be applied to (MyCaseClass)
[error]     ).withEntity(MyCaseClass(7, "Hi"))

The same if I do this instead: .withEntity(MyCaseClass(7, "Hi").asJson)

Hmm ... what gave you the impression that this should work?

Basically, what this library or SprayJsonSupport from Akka HTTP gives you, is the possibility to complete requests – i.e. use the complete directive – with a domain object. This is because complete requires an argument of type ToResponseMarshallable and the implicit conversions here provide one for any type which has an Encoder.

What you are trying to do can't work, because there's no support for converting some object into an instance of type HttpEntity. You probably could use something like Marshal(myCaseClass).to[HttpEntity], and that would give you a Future[HttpEntity] which you could use to construct your request.

Ah I see. I misunderstood the scope of the library then. I assumed akka-http expected some kind of typeclass instance for message bodies and this library provided implicit conversions and some helpers to go from the typeclass instance of the JSON library to the akka-http one. It seems that the design of akka-http is quite different from this, though. I only used the http4s client before and wrongly assumed it was similar in akka-http.
Thanks for your response. I will just have to make my own implicit conversions or something to get rid of the boilerplate then 👍 .

Well, as I wrote above, you can go from your object to a request or response with the object marshalled as entity. But as marshalling potentially takes time (for large objects) you get back a future.

Ah I see now. So I would get a future of HttpResponse and that's why there's no way to automatically get an HttpResponse but only a Future[HttpResponse].

commented

In order to marshal your custom case class to a RequestEntity (e.g. for a POST request body), you will need a circe marshaller and unmarshaller for the response you get. Here's a gist for the (un)marshaller you can use: http://codegists.com/code/akka-http-circe-example/