尝试 return Future[Result] 时在 playframework 中获取控制器 return 类型错误
getting controller return type error in playframework when trying to return Future[Result]
我的控制器流程非常复杂,这就是它的使用方式:
- get the request
- translate it to my model
case it succeed:
insert some record to my db
case it succeed:
perform some api call
case it succeed:
match its returned value
case failed:
recover with proper result
case failed:
recover with proper result
case failed:
recover with proper result
但是在我的代码中我得到一些错误,我在某处没有正确返回结果的未来...
错误:
expression of type unit doesnt conform to expected type
Future[Result]
这是代码:
def myApiMethod ...
val requestAsModel = request.body.extractOpt[MyModel]
requestAsModel match {
case Some(req) =>
// returning Future
dbService.insert.onComplete {
case Success(x) =>
myApiService.doSomething(req).map {
case good: GoodRes => Ok(Extraction.decompose(good))
case bad: BadRes => BadRequest(Extraction.decompose(bad))
} recover {
case ex =>
InternalServerError
}
case Failure(ex) => Future {InternalServerError}
}
case None =>
Future.successful(BadRequest("not a good body content"))
}
}
所以你看到这里的问题了吗?
以这种方式编写控制器看起来是个好习惯吗?
谢谢
未来 onComplete 方法 returns 单元 documentation。
您需要将 onComplete 替换为 flatMap 调用才能将结果 future 转换为 Future[Result]:
dbService.insert.flatMap{
case Success(x) =>
myApiService.doSomething(req).map {
case good: GoodRes => Ok(Extraction.decompose(good))
case bad: BadRes => BadRequest(Extraction.decompose(bad))
} recover {
case ex =>
InternalServerError
}
case Failure(ex) => Future {InternalServerError}
}
我建议阅读这篇文章Scala Futures guide。特别是关于组成期货的部分。
我的控制器流程非常复杂,这就是它的使用方式:
- get the request
- translate it to my model
case it succeed:
insert some record to my db
case it succeed:
perform some api call
case it succeed:
match its returned value
case failed:
recover with proper result
case failed:
recover with proper result
case failed:
recover with proper result
但是在我的代码中我得到一些错误,我在某处没有正确返回结果的未来...
错误:
expression of type unit doesnt conform to expected type Future[Result]
这是代码:
def myApiMethod ...
val requestAsModel = request.body.extractOpt[MyModel]
requestAsModel match {
case Some(req) =>
// returning Future
dbService.insert.onComplete {
case Success(x) =>
myApiService.doSomething(req).map {
case good: GoodRes => Ok(Extraction.decompose(good))
case bad: BadRes => BadRequest(Extraction.decompose(bad))
} recover {
case ex =>
InternalServerError
}
case Failure(ex) => Future {InternalServerError}
}
case None =>
Future.successful(BadRequest("not a good body content"))
}
}
所以你看到这里的问题了吗?
以这种方式编写控制器看起来是个好习惯吗?
谢谢
未来 onComplete 方法 returns 单元 documentation。 您需要将 onComplete 替换为 flatMap 调用才能将结果 future 转换为 Future[Result]:
dbService.insert.flatMap{
case Success(x) =>
myApiService.doSomething(req).map {
case good: GoodRes => Ok(Extraction.decompose(good))
case bad: BadRes => BadRequest(Extraction.decompose(bad))
} recover {
case ex =>
InternalServerError
}
case Failure(ex) => Future {InternalServerError}
}
我建议阅读这篇文章Scala Futures guide。特别是关于组成期货的部分。