別のサービスからコンテンツを受信し、処理して応答を返すhttp4sサーバーを実装したいと考えています。
元のサービスはリダイレクトを使用するため、Follow リダイレクトミドルウェアを追加しました。生成されたログを確認するために、Logger ミドルウェアも追加しました。
サービスの骨組みは次のとおりです。
implicit val clientResource = BlazeClientBuilder[F](global).resource
val wikidataEntityUrl = "http://www.wikidata.org/entity/Q"
def routes(implicit timer: Timer[F]): HttpRoutes[F] = HttpRoutes.of[F] {
case GET -> Root / "e" / entity => {
val uri = uri"http://www.wikidata.org/entity/" / ("Q" + entity)
val req: Request[F] = Request(uri = uri)
clientResource.use { c => {
val req: Request[F] = Request(Method.GET, uri)
def cb(resp: Response[F]): F[Response[F]] = Ok(resp.bodyAsText)
val redirectClient = Logger(true,true,_ => false)(FollowRedirect[F](10, _ => true)(c))
redirectClient.fetch[Response[F]](req)(cb)
}}}}
次のようにcurlを使用してサービスにアクセスしようとすると:
curl -v http://localhost:8080/e/33
応答には元のコンテンツの最初の部分が含まれ、次のように終了します。
transfer closed with outstanding read data remaining
* Closing connection 0
ログを見ると、次の行が含まれています。
ERROR o.h.s.blaze.Http1ServerStage$$anon$1 - Error writing body
org.http4s.InvalidBodyException: Received premature EOF.
これは、時期尚早の EOF を受信するときにエラーが発生したことを示しています。
私はこの問題で可能な答えを見つけました:しかし、答えは、tohttpService.
ストリームを使用してコードを書き直す必要があると思いますが、より慣用的な方法はわかりません。いくつかの提案?