2016-03-04 47 views
0

我遇到了一个我目前无法解决的问题。我正在做多个http请求,在每个响应中,它应该有一个Array[DTAnnotation]。我想积累所有结果列表到一个(这不是问题在这里)。我的问题是我无法返回WSResponse的结果。我尝试什么:从多个HTTP请求中提取并累加结果

import mymodel.{DTFeatures, DTResponse, DTRequest, DTAnnotations} 

def checkForSpike 
    (
    awsKey : String, 
    collection : JSONCollection, 
    record : Record, 
    features : Array[DTFeatures] 
) : Unit = { 
    val url = config.getString("url").getOrElse 
    val holder = WS.url(url) 
    val complexHolder = 
    holder.withHeaders(("Content-Type","application/json")) 
    // excepting result is List[Array[DTAnnotations]] 
    val test : List[Array[DTAnnotations]] = 
    for(feature <- features) yield { 
    val dtFeature = Json.stringify(Json.toJson(DTRequest(feature))) 
    val futureResponse = complexHolder.post(dtFeature) 
    Logger.info("Make the HTTP POST Request in " + (t1 - t0) + " msecs") 
    futureResponse.map { response => 
     Logger.info("Get response in " + (System.currentTimeMillis - t1)) 
     if(response.status == 200) { 
     response.json.validate[DTResponse].map { dtResponse => 
      // I want to return this 
      dtResponse.annotations 
     }.recoverTotal { _ => 
      Logger.debug("invalid json") 
     } 
     } else { 
     Logger.debug(Json.prettyPrint(Json.obj("status" -> response.status, "body" -> response.body))) 
     } 
    } 
     Await.result(futureResponse, 10.seconds) 
    } 
} 

因为响应是一个Future,我尝试添加Await得到注解,但我在打字阶段一个错误:

[error] found : Array[play.api.libs.ws.WSResponse] 
[error] required: List[Array[DTAnnotation]] 

我怎么能解决这个问题?谢谢 !

回答

1

有一些错误可以避免这种情况发挥作用。我添加一个与您的预期类型一致的版本,如果您有问题,我会在评论中回答。

def checkForSpike 
    (
    awsKey: String, 
    collection: JSONCollection, 
    record: Record, 
    features: Array[DTFeatures] 
): Unit = { 
    val url = config.getString("url").getOrElse 
    val holder = WS.url(url) 
    val complexHolder = 
     holder.withHeaders(("Content-Type", "application/json")) 
    // excepting result is List[Array[DTAnnotations]] 
    val test: List[Array[DTAnnotations]] = 
     for (feature <- features.toList) yield { 
     val dtFeature = Json.stringify(Json.toJson(DTRequest(feature))) 
     val futureResponse = complexHolder.post(dtFeature) 
     val futureAnnotations: Future[Array[DTAnnotations]] = futureResponse.map { response => 
      if (response.status == 200) { 
      response.json.validate[DTResponse].map { dtResponse => 
       // I want to return this 
       dtResponse.annotations 
      }.recoverTotal { _ => 
       Logger.debug("invalid json") 
       ??? // An Array response should be expected, maybe empty 
      } 
      } else { 
      Logger.debug(Json.prettyPrint(Json.obj("status" -> response.status, "body" -> response.body))) 
      ??? // An Array response should be expected, maybe empty 
      } 
     } 

     Await.result(futureAnnotations, 10.seconds) 
     } 
    } 

问题:

  • 要素必须被转换,如果你希望一个列表是通过为修真返回
  • 未来的响应返回地图 另一个未来列表,此值应在等待中使用
  • 为确保所有分支中futureAnnotations的类型正确,类型应该是有效的
+0

工程像魅力!也感谢您的时间和意见 – alifirat

+1

不客气。一旦你有它的工作,你可以改进一点。避免等待并阅读有关组合期货的信息。 Daniel Westheide的教程非常好。这是关于期货的章节http://danielwestheide.com/blog/2013/01/09/the-neophytes-guide-to-scala-part-8-welcome-to-the-future.html –

+0

您是否打算使用'flatMap'而不是'map'? – alifirat