Skip to content

Instantly share code, notes, and snippets.

@DanielBlanco
Created February 9, 2021 19:53
Show Gist options
  • Save DanielBlanco/4e8f514ed730fe3cc2f8da8878e182d7 to your computer and use it in GitHub Desktop.
Save DanielBlanco/4e8f514ed730fe3cc2f8da8878e182d7 to your computer and use it in GitHub Desktop.
An sttp+zio fetch backend (used in scala.js)
package app.util
import org.scalajs.dom.document
import org.scalajs.dom.experimental.{BodyInit, Response, Request => FetchRequest}
import scala.scalajs.js
import scala.scalajs.js.{Promise, UndefOr}
import sttp.capabilities.Effect
import sttp.client3.{AbstractFetchBackend, FetchOptions}
import sttp.client3.impl.zio._
import sttp.client3.internal.NoStreams
import sttp.model.{MediaType, Uri}
import sttp.monad._
import zio._
class FetchZioBackend(fetchOptions: FetchOptions, customizeRequest: FetchRequest => FetchRequest)
extends AbstractFetchBackend[Task, Nothing, Any](fetchOptions, customizeRequest)(new RIOMonadAsyncError[Any]) {
override val streams: NoStreams = NoStreams
override protected def addCancelTimeoutHook[T](result: Task[T], cancel: () => Unit): Task[T] = {
result.tapBoth(_ => UIO.effectTotal(cancel()), _ => UIO.effectTotal(cancel()))
}
override protected def handleStreamBody(s: Nothing): Task[UndefOr[BodyInit]] = {
ZIO.succeed(js.undefined)
}
override protected def handleResponseAsStream(response: Response): Task[(Nothing, () => Task[Unit])] = {
Task.fail(new IllegalStateException("ZIO FetchBackend does not support streaming responses"))
}
override protected def transformPromise[T](promise: => Promise[T]): Task[T] = {
ZIO.fromPromiseJS(promise)
}
}
object FetchZioBackend {
def apply(
fetchOptions: FetchOptions = FetchOptions.Default,
customizeRequest: FetchRequest => FetchRequest = identity
): FetchZioBackend =
new FetchZioBackend(fetchOptions, customizeRequest)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment