Можно ли установить код ответа от Marshaller в spray.io?

У меня есть следующий фрагмент кода, где dataService возвращает Option[LocationDataResult]. Я хотел бы установить NotFound, когда dataService возвращает None и отправить данные обратно в случае Some(...).

У меня есть следующий код:

  val route: Route = {
    pathPrefix("service" / "data") {
      pathPrefix( "infobox") {
        get {
          parameters(('mes.as[String], 'oks.as[String])) {
            (me, okr) =>

              val resp = dataService.ask(GetocationInfoboxData(me,okr)).mapTo[LocationInfoboxDataResult]
                .map(remapInfoboxToResponseObject(_)).map { r =>
                r match {
                  case None => StatusCodes.NotFound
                  case Some(dataToRespond) => dataToRespond
                }
              }

              complete {
                resp
              }
          }
        }
      }
    }
  }


  implicit val responseMarhaller: Marshaller[LocationInfobox] = Marshaller.of[WikiLocationInfobox](ContentTypes.`application/json`) { (value, contentType, ctx) =>
    val result: String = mapper.writeValueAsString(value)
    ctx.marshalTo(HttpEntity(contentType, result))
  }

Я не могу найти правильный путь от marshaller и от маршрута через полную функцию. Я не могу заставить его работать.

Может кто более опытный подскажет? Я упускаю здесь какую-то важную концепцию?

Спасибо

ОБНОВЛЕНИЕ: Сообщение об ошибке «Выражение типа Future[Object] не соответствует ожидаемому типу ToResponseMarsallable.


person jaksky    schedule 10.08.2015    source источник


Ответы (2)


Код выглядит нормально, не уверен, что не работает. Попробуйте переписать его с директивами Spray для фьючерсов вместо того, чтобы доделывать сам фьючерс:

val locationData = dataService.ask(GetocationInfoboxData(me,okr)).mapTo[LocationInfoboxDataResult]

onSuccess(locationData.map(remapInfoboxToResponseObject)) {
  case None => complete(StatusCodes.NotFound)
  case Some(data) => complete(data)
}
person 4lex1v    schedule 10.08.2015

Это отлично работает для меня, используя преимущества MetaMarshallers

          val resp = dataService.ask(GetocationInfoboxData(me, okr)).mapTo[LocationInfoboxDataResult].map(remapInfoboxToResponseObject(_)).map{
            r =>
              r match {
                case None => Left(StatusCodes.NotFound)
                case Some(data) => Right(data)
              }
          }
         complete(resp)
person jaksky    schedule 10.08.2015