softwaremill / tapir

Rapid development of self-documenting APIs
https://tapir.softwaremill.com
Apache License 2.0
1.35k stars 405 forks source link

Dedicated error channel for client #244

Closed kamilkloch closed 4 years ago

kamilkloch commented 4 years ago

Currently Endpoint[I, E, O, +S] contains a dedicated server error channel. When an Endpoint is intepreted into an sttp client, this seems to be not enough. For example, client interpreter throws an exception on DecodeFailure: https://github.com/softwaremill/tapir/blob/49bf6951fee1bed6eaf9ec7444b000aabfdcf87c/client/sttp-client/src/main/scala/tapir/client/sttp/EndpointToSttpClient.scala#L276

One option would be to interpret into a Request[Either[DecodeFailure, Either[E, O]] the other to flatten the double-eithers to an error hierarchy.

adamw commented 4 years ago

I suppose that's implemented now with:

trait TapirSttpClient {
  implicit class RichEndpoint[I, E, O, S](e: Endpoint[I, E, O, S]) {
    /**
      * @throws IllegalArgumentException when response parsing fails
      */
    def toSttpRequestUnsafe(baseUri: Uri)(implicit clientOptions: SttpClientOptions): I => Request[Either[E, O], S] =
      new EndpointToSttpClient(clientOptions).toSttpRequestUnsafe(e, baseUri)

    def toSttpRequest(baseUri: Uri)(implicit clientOptions: SttpClientOptions): I => Request[DecodeResult[Either[E, O]], S] =
      new EndpointToSttpClient(clientOptions).toSttpRequest(e, baseUri)
  }
}