Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Update zio-http to 3.0.0-RC3 #165

Merged
merged 1 commit into from
Nov 7, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion build.sbt
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ lazy val V = new {
val zio = "2.0.18"
val zioJson = "0.6.2"
// val zioMunitTest = "0.1.1"
val zioHttp = "3.0.0-RC2"
val zioHttp = "3.0.0-RC3"
val zioConfig = "4.0.0-RC16"
val zioLogging = "2.1.14"
val zioSl4j = "2.1.14"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,14 +33,12 @@ class MessageDispatcherJVM(client: Client) extends MessageDispatcher {
.pipe(e => Header.ContentType(ZMediaType.application.any.copy(subType = "didcomm-encrypted+json")))
val xForwardedHostHeader = xForwardedHost.map(x => Header.Custom(customName = MyHeaders.xForwardedHost, x))

// xForwardedHost.map(x => Header.(MyHeaders.xForwardedHost, x))
for {
res <- Client
.request(
url = destination,
method = Method.POST,
headers = Headers(Seq(Some(contentTypeHeader), xForwardedHostHeader).flatten),
content = Body.fromCharSequence(msg.toJson),
Request
.post(destination, Body.fromCharSequence(msg.toJson))
.setHeaders(Headers(Seq(Some(contentTypeHeader), xForwardedHostHeader).flatten))
)
.tapError(ex => ZIO.logWarning(s"Fail when calling '$destination': ${ex.toString}"))
.mapError(ex => DispatcherError(ex))
Expand All @@ -51,5 +49,7 @@ class MessageDispatcherJVM(client: Client) extends MessageDispatcher {
case true => ZIO.logWarning(data)
case false => ZIO.logInfo(data)
} yield (data)
}.provideEnvironment(ZEnvironment(client))
}
.provideSomeLayer(Scope.default)
.provideEnvironment(ZEnvironment(client))
}
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
/*
package io.iohk.atala.mediator.utils

import zio.*
Expand Down Expand Up @@ -50,3 +51,4 @@ object MiddlewareUtils {
}

}
*/
Original file line number Diff line number Diff line change
@@ -1,31 +1,38 @@
package io.iohk.atala.mediator.app

import zio.http.Response
import zio.http._
import fmgp.did.DID

object IndexHtml {
// TODO use the html.Html.fromDomElement()
def html(identity: DID) = Response.html(s"""<html>
|<head>
| <meta charset="UTF-8">
| <title>IOHK Mediator</title>
| <meta name="viewport" content="width=device-width, initial-scale=1.0">
| <meta name="did" content="${identity.did}">
| <link href="https://fonts.googleapis.com/css?family=Roboto:300,400,500" rel="stylesheet">
| <link href="https://unpkg.com/material-components-web@latest/dist/material-components-web.min.css" rel="stylesheet">
| <link rel="stylesheet" href="https://fonts.googleapis.com/icon?family=Material+Icons">
| <script>
| var callback = function () {
| alert('A callback was triggered');
| }
| </script>
| <!-- My APP -->
| <script type="text/javascript" src="public/webapp-fastopt-bundle.js"></script>
|</head>
|
|<body style="margin:0;">
| <div id="app-container"></div>
|</body>
|
|</html>""".stripMargin)
def html(identity: DID) =
Response(
status = Status.Ok,
headers = Headers(Header.ContentType(MediaType.text.html).untyped),
body = Body.fromString(
s"""<!DOCTYPE html>
|<html>
|<head>
| <meta charset="UTF-8">
| <title>IOHK Mediator</title>
| <meta name="viewport" content="width=device-width, initial-scale=1.0">
| <meta name="did" content="${identity.did}">
| <link href="https://fonts.googleapis.com/css?family=Roboto:300,400,500" rel="stylesheet">
| <link href="https://unpkg.com/material-components-web@latest/dist/material-components-web.min.css" rel="stylesheet">
| <link rel="stylesheet" href="https://fonts.googleapis.com/icon?family=Material+Icons">
| <script>
| var callback = function () {
| alert('A callback was triggered');
| }
| </script>
| <!-- My APP -->
| <script type="text/javascript" src="public/webapp-fastopt-bundle.js"></script>
|</head>
|
|<body style="margin:0;">
| <div id="app-container"></div>
|</body>
|
|</html>""".stripMargin
),
)
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,6 @@ import io.iohk.atala.mediator.db.*
import io.iohk.atala.mediator.protocols.*
import io.iohk.atala.mediator.utils.*
import io.netty.handler.codec.http.HttpHeaderNames
import reactivemongo.api.bson.Macros.{*, given}
import reactivemongo.api.bson.{*, given}
import zio.*
import zio.http.*
Expand All @@ -23,7 +22,6 @@ import zio.json.*
import scala.concurrent.ExecutionContext.Implicits.global
import scala.util.Try
import scala.io.Source
import zio.http.internal.middlewares.Cors.CorsConfig
import zio.http.Header.AccessControlAllowOrigin
import zio.http.Header.AccessControlAllowMethods

Expand Down Expand Up @@ -223,18 +221,20 @@ object MediatorAgent {
def make(id: DID, keyStore: KeyStore): ZIO[Any, Nothing, MediatorAgent] = ZIO.succeed(MediatorAgent(id, keyStore))

def didCommApp = {
Http.collectZIO[Request] {
case req @ Method.GET -> Root / "headers" =>
Routes(
Method.GET / "headers" -> handler { (req: Request) =>
val data = req.headers.toSeq.map(e => (e.headerName, e.renderedValue))
ZIO.succeed(Response.text("HEADERS:\n" + data.mkString("\n") + "\nRemoteAddress:" + req.remoteAddress)).debug
case req @ Method.GET -> Root / "health" => ZIO.succeed(Response.ok)
case Method.GET -> Root / "version" => ZIO.succeed(Response.text(MediatorBuildInfo.version))
case Method.GET -> Root / "did" =>
},
Method.GET / "health" -> handler { (req: Request) => ZIO.succeed(Response.ok) },
Method.GET / "version" -> handler { (req: Request) => ZIO.succeed(Response.text(MediatorBuildInfo.version)) },
Method.GET / "did" -> handler { (req: Request) =>
for {
agent <- ZIO.service[MediatorAgent]
ret <- ZIO.succeed(Response.text(agent.id.string))
} yield (ret)
case Method.GET -> Root / "invitation" =>
},
Method.GET / "invitation" -> handler { (req: Request) =>
for {
agent <- ZIO.service[MediatorAgent]
annotationMap <- ZIO.logAnnotations.map(_.map(e => LogAnnotation(e._1, e._2)).toSeq)
Expand All @@ -247,7 +247,8 @@ object MediatorAgent {
_ <- ZIO.log("New mediate invitation MsgID: " + invitation.id.value)
ret <- ZIO.succeed(Response.json(invitation.toPlaintextMessage.toJson))
} yield (ret)
case Method.GET -> Root / "invitationOOB" =>
},
Method.GET / "invitationOOB" -> handler { (req: Request) =>
for {
agent <- ZIO.service[MediatorAgent]
annotationMap <- ZIO.logAnnotations.map(_.map(e => LogAnnotation(e._1, e._2)).toSeq)
Expand All @@ -263,98 +264,78 @@ object MediatorAgent {
OutOfBandPlaintext.from(invitation.toPlaintextMessage).makeURI("")
)
)

} yield (ret)
case req @ Method.POST -> Root
if req.headers
// .header(Header.ContentType) // TODO BUG? this does not work
.get("content-type")
.exists { h =>
// TODO after fix BUG
// h.mediaType.mainType == "application" &&
// (h.mediaType.subType == "didcomm-signed+json" || h.mediaType.subType == "didcomm-encrypted+json")
// TODO after update lib
// h.mediaType.mainType == ZMediaTypes.mainType &&
// (h.mediaType.subType == MediaTypes.SIGNED.subType || h.mediaType.subType == MediaTypes.ENCRYPTED.subType)
h == MediaTypes.SIGNED.typ || h == MediaTypes.ENCRYPTED.typ
} =>
for {
agent <- ZIO.service[MediatorAgent]
data <- req.body.asString
ret <- agent
.receiveMessage(data)
.map {
case None => Response.ok
case Some(value: SignedMessage) => Response.json(value.toJson)
case Some(value: EncryptedMessage) => Response.json(value.toJson)
}
.catchAll {
case MediatorDidError(error) =>
ZIO.logError(s"Error MediatorDidError: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case MediatorThrowable(error) =>
ZIO.logError(s"Error MediatorThrowable: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case StorageCollection(error) =>
ZIO.logError(s"Error StorageCollection: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case StorageThrowable(error) =>
ZIO.logError(s"Error StorageThrowable: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case DuplicateMessage(error) =>
ZIO.logError(s"Error DuplicateKeyError: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case MissingProtocolError(piuri) =>
ZIO.logError(s"MissingProtocolError ('$piuri')") *>
ZIO.succeed(Response.status(Status.BadRequest)) // TODO
}
} yield ret
// TODO [return_route extension](https://github.com/decentralized-identity/didcomm-messaging/blob/main/extensions/return_route/main.md)
case req @ Method.POST -> Root =>
ZIO
.logError(s"Request Headers: ${req.headers.mkString(",")}")
.as(
Response
.text(s"The content-type must be ${MediaTypes.SIGNED.typ} or ${MediaTypes.ENCRYPTED.typ}")
.copy(status = Status.BadRequest)
)
case req @ Method.GET -> Root => { // html.Html.fromDomElement()
},
Method.POST / trailing -> handler { (req: Request) =>
{
if (
req.headers
.get("content-type")
.exists { h => h == MediaTypes.SIGNED.typ || h == MediaTypes.ENCRYPTED.typ }
) {
for {
agent <- ZIO.service[MediatorAgent]
data <- req.body.asString
.catchAll(ex => ZIO.fail(Response.badRequest("Unable to read the body of the request")))
ret <- agent
.receiveMessage(data)
.map {
case None => Response.ok
case Some(value: SignedMessage) => Response.json(value.toJson)
case Some(value: EncryptedMessage) => Response.json(value.toJson)
}
.catchAll {
case MediatorDidError(error) =>
ZIO.logError(s"Error MediatorDidError: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case MediatorThrowable(error) =>
ZIO.logError(s"Error MediatorThrowable: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case StorageCollection(error) =>
ZIO.logError(s"Error StorageCollection: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case StorageThrowable(error) =>
ZIO.logError(s"Error StorageThrowable: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case DuplicateMessage(error) =>
ZIO.logError(s"Error DuplicateKeyError: $error") *>
ZIO.succeed(Response.status(Status.BadRequest))
case MissingProtocolError(piuri) =>
ZIO.logError(s"MissingProtocolError ('$piuri')") *>
ZIO.succeed(Response.status(Status.BadRequest)) // TODO
}
} yield ret
} else
ZIO
.logError(s"Request Headers: ${req.headers.mkString(",")}")
.as(
Response
.text(s"The content-type must be ${MediaTypes.SIGNED.typ} or ${MediaTypes.ENCRYPTED.typ}")
.copy(status = Status.BadRequest)
)
}
},
Method.GET / trailing -> handler { (req: Request) =>
for {
agent <- ZIO.service[MediatorAgent]
_ <- ZIO.log("index.html")
ret <- ZIO.succeed(IndexHtml.html(agent.id))
} yield ret
}
}: Http[
Operations & Resolver & MessageDispatcher & MediatorAgent & MessageItemRepo & UserAccountRepo & OutboxMessageRepo,
Throwable,
Request,
Response
]
} ++ Http
.fromResource(s"public/webapp-fastopt-bundle.js.gz")
.map(_.setHeaders(Headers(Header.ContentType(MediaType.application.javascript), Header.ContentEncoding.GZip)))
.when {
case Method.GET -> Root / "public" / "webapp-fastopt-bundle.js" => true
case _ => false
}
@@ HttpAppMiddleware.cors(
CorsConfig(
allowedOrigin = {
// case origin @ Origin.Value(_, host, _) if host == "dev" => Some(AccessControlAllowOrigin.Specific(origin))
case _ => Some(AccessControlAllowOrigin.All)
},
allowedMethods = AccessControlAllowMethods(Method.GET, Method.POST, Method.OPTIONS),
)
},
Method.GET / "public" / string("path") -> handler { (path: String, req: Request) =>
// RoutesMiddleware
// TODO https://zio.dev/reference/stream/zpipeline/#:~:text=ZPipeline.gzip%20%E2%80%94%20The%20gzip%20pipeline%20compresses%20a%20stream%20of%20bytes%20as%20using%20gzip%20method%3A
val fullPath = s"public/$path"
val classLoader = Thread.currentThread().getContextClassLoader()
val headerContentType = fullPath match
case s if s.endsWith(".html") => Header.ContentType(MediaType.text.html)
case s if s.endsWith(".js") => Header.ContentType(MediaType.text.javascript)
case s if s.endsWith(".css") => Header.ContentType(MediaType.text.css)
case s if s.endsWith(".svg") => Header.ContentType(MediaType.image.`svg+xml`)
case s => Header.ContentType(MediaType.text.plain)
Handler.fromResource(fullPath).map(_.addHeader(headerContentType))
}.flatten
)
// @@
// HttpAppMiddleware.updateHeaders(headers =>
// Headers(
// headers.map(h =>
// if (h.key == HttpHeaderNames.ACCESS_CONTROL_ALLOW_ORIGIN) {
// Header(HttpHeaderNames.ACCESS_CONTROL_ALLOW_ORIGIN, "*")
// } else h
// )
// )
// )
}.sandbox.toHttpApp

}
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,6 @@ import zio.config.*
import zio.config.magnolia.*
import zio.config.typesafe.*
import zio.http.*
import zio.http.Http.{Empty, Static}
import zio.http.ZClient.ClientLive
import zio.json.*
import zio.logging.LogFormat.*
import zio.logging.backend.SLF4J
Expand Down Expand Up @@ -57,17 +55,6 @@ object MediatorStandalone extends ZIOAppDefault {
override val bootstrap: ZLayer[ZIOAppArgs, Any, Any] =
Runtime.removeDefaultLoggers >>> SLF4J.slf4j(mediatorColorFormat)

// val app: HttpApp[ // type HttpApp[-R, +Err] = Http[R, Err, Request, Response]
// Hub[String] & Operations & MessageDispatcher & MediatorAgent & Resolver & MessageItemRepo & UserAccountRepo &
// OutboxMessageRepo,
// Throwable
// ]
val app: Http[
Operations & Resolver & UserAccountRepo & OutboxMessageRepo & MessageDispatcher & MediatorAgent & MessageItemRepo,
(HttpAppMiddleware[Nothing, Any, Nothing, Any] | HttpAppMiddleware[Nothing, Any, Nothing, Any])#OutErr[Throwable],
Request,
Response
] = MediatorAgent.didCommApp
override val run = for {
_ <- Console.printLine( // https://patorjk.com/software/taag/#p=display&f=ANSI%20Shadow&t=Mediator
"""███╗ ███╗███████╗██████╗ ██╗ █████╗ ████████╗ ██████╗ ██████╗
Expand Down Expand Up @@ -103,18 +90,7 @@ object MediatorStandalone extends ZIOAppDefault {
client = Scope.default >>> Client.default
inboundHub <- Hub.bounded[String](5)
myServer <- Server
.serve(
(app @@ (MiddlewareUtils.annotateHeaders ++ MiddlewareUtils.serverTime))
.tapUnhandledZIO(ZIO.logError("Unhandled Endpoint"))
.tapErrorCauseZIO(cause => ZIO.logErrorCause(cause)) // THIS is to log all the erros
.mapError(err =>
Response(
status = Status.BadRequest,
headers = Headers.empty,
body = Body.fromString(err.toString()), // Body.fromString(err.getMessage()),
)
)
)
.serve(MediatorAgent.didCommApp @@ (Middleware.cors))
.provideSomeLayer(DidPeerResolver.layerDidPeerResolver)
.provideSomeLayer(mediatorConfig.agentLayer) // .provideSomeLayer(AgentByHost.layer)
.provideSomeLayer(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -96,7 +96,8 @@ object AppUtils {
href := "https://atalaprism.io",
target := "_blank",
img(
src := "https://atalaprism.io/images/atala-prism-logo-suite.svg",
// src := "https://atalaprism.io/images/atala-prism-logo-suite.svg",
src := "public/atala-prism-logo-suite.svg", // Note: this is not the best server for CDN
className := "logo vanilla",
alt := "Prism Mediator"
),
Expand Down
Loading