On 25/04/2017 00:13, Andras Szerdahelyi wrote:
I have a need to encode exception messages in to a specific JSON format in
my http responses. I was wondering how I could catch a
DeserializationException in my route or outside of it or encode the
DeserializationException.
Here's how I did it so that it integrasted into my existing REST service
error handling:
Wrapped the deserialization operation in a try block:
def getParam[T: JsonReader](params: MMap[String, JsValue], key:
String, delete: Boolean = true): T = {
val value = params.get(key) match {
case Some(v) => try {
v.convertTo[T]
} catch {
case de: DeserializationException => throw
deserializationToRESTException(de, key)
}
case None => throw RESTException(ERR_MISSING_ARG(key))
}
if (delete) params -= key
value
}
val restErrorRE: Regex = """^Expected (\w+) as \w+, but got (.+)$""".r
def deserializationToRESTException(de: DeserializationException, key:
String) = {
val msg = de.msg match {
case restErrorRE(t, v) => s"expected $key to be $t but got $v"
case _ => s"invalid value for $key"
}
RESTException(ERR_INVALID_ARG(msg), de)
}
Then I wrapped all the individual deserialization calls in a try block:
try {
:
val name = getParam[String](fields, "name")
val uid = getParam[Int](fields, "uid")
:
} catch {
case re: RESTException => complete(re.toResponse)
final case class RESTException(error: RESTError, cause: Throwable =
null) extends Exception(error.toString, cause) {
def toResponse: HttpResponse = error.toResponse
}
final case class ERR_INVALID_ARG(det: String = null)
extends RESTErrorWithDetail(400, "invalid input argument", det)
RESTErrorWithDetail just maps the error code and message onto a normal
HttpResponse containing the HTTP status code and a JSON formatted error
message:
override def toResponse: HttpResponse = {
if (detail != null) {
HttpResponse(status = code, entity =
HttpEntity(MediaTypes.`application/json`,
"""{ "fault": { "code": %d, "name": %s, "message": %s }
}""".format(
code, name.toJson, s"$msg ($detail)".toJson)))
} else {
super.toResponse
}
}
That way the JSON deserialization errors are handled as normal
completions rather than using a specific Akka-HTTP exception handler.
--
Alan Burlison
--
--
Read the docs: http://akka.io/docs/
Check the FAQ: http://doc.akka.io/docs/akka/current/additional/faq.html
Search the archives: https://groups.google.com/group/akka-user
---
You received this message because you are subscribed to the Google Groups "Akka User List" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To post to this group, send email to [email protected].
Visit this group at https://groups.google.com/group/akka-user.
For more options, visit https://groups.google.com/d/optout.