-
Notifications
You must be signed in to change notification settings - Fork 1
/
RpcClient.scala
43 lines (33 loc) · 1.66 KB
/
RpcClient.scala
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
package frontend
import cats.effect.{Async, IO}
import cats.implicits.*
import org.scalajs.dom
import sloth.{Request, RequestTransport}
import sloth.ext.jsdom.client.*
import scala.scalajs.js
import scala.scalajs.js.JSConverters.*
object RpcClient {
import chameleon.ext.upickle.given
private val headers: IO[Map[String, String]] = lift {
unlift(authnClient.session).map(token => "Authorization" -> s"Bearer $token").toMap
}
private val httpConfig = headers.map(headers => HttpRequestConfig(headers = headers))
private val requestClient = sloth.Client[String, IO](HttpRpcTransport(httpConfig))
val call: rpc.RpcApi = requestClient.wire[rpc.RpcApi]
}
// TODO: use from sloth library again, once https://github.com/cornerman/sloth/pull/252 is merged
object HttpRpcTransport {
def apply[F[_]: Async]: RequestTransport[String, F] = apply(HttpRequestConfig().pure[F])
def apply[F[_]: Async](config: F[HttpRequestConfig]): RequestTransport[String, F] = new RequestTransport[String, F] {
override def apply(request: Request[String]): F[String] = for {
config <- config
url = s"${config.baseUri}${request.method.traitName}/${request.method.methodName}"
requestArgs = new dom.RequestInit { headers = config.headers.toJSDictionary; method = dom.HttpMethod.POST; body = request.payload }
response <- Async[F].fromPromise(Async[F].delay(dom.fetch(url, requestArgs)))
_ <- Async[F].raiseWhen(!response.ok)(
new Exception(s"${request.method.traitName}.${request.method.methodName} returned HTTP ${response.status}")
)
result <- Async[F].fromPromise(Async[F].delay(response.text()))
} yield result
}
}