Play Framework for comprehension type mismatch

时间:2018-01-19 05:05:56

标签: scala oauth playframework

我正在使用Play Framework 2.6.11版,在构建Application控制器时,我得到错误

Expression of type IndexedSeq[(ConsumerKey, RequestToken)] doesn't 
conform to expected type Option[(ConsumerKey, RequestToken)]
代码中的

import com.google.inject.Inject
import play.api.Configuration
import play.api.libs.oauth.{ConsumerKey, RequestToken}
import play.api.mvc.{ BaseController,  ControllerComponents}

import scala.concurrent.Future

class Application @Inject() (config: Configuration, c: ControllerComponents) extends BaseController {
  def tweets = Action.async {
    val credentials : Option[(ConsumerKey, RequestToken)] = for {
      apiKey <- config.get[String]("twitter.apiKey")
      apiSecret <- config.get[String]("twitter.apiSecret")
      token <- config.get[String]("twitter.token")
      tokenSecret <- config.get[String]("twitter.tokenSecret")
    } yield (
      ConsumerKey(apiKey.toString, apiSecret.toString),
      RequestToken(token.toString, tokenSecret.toString)
    )

    // use credentials to invoke twitter API and return Ok
    Future.successful { Ok } 
  }
}

1 个答案:

答案 0 :(得分:2)

您的代码中的问题是get中的方法Configuration将返回String而不是Option[String],因此您将平坦地覆盖字符串。

如果你的配置键是可选的,你应该使用方法getOptional,所以如果所有四个配置键都存在,你最终会得到元组

import com.google.inject.Inject
import play.api.Configuration
import play.api.libs.oauth.{ConsumerKey, RequestToken}
import play.api.mvc.{ BaseController,  ControllerComponents}

import scala.concurrent.Future

class Application @Inject() (config: Configuration, c: ControllerComponents) extends BaseController {
  def tweets = Action.async {
    val credentials : Option[(ConsumerKey, RequestToken)] = for {
      apiKey <- config.getOptional[String]("twitter.apiKey")
      apiSecret <- config.getOptional[String]("twitter.apiSecret")
      token <- config.getOptional[String]("twitter.token")
      tokenSecret <- config.getOptional[String]("twitter.tokenSecret")
    } yield (
      ConsumerKey(apiKey.toString, apiSecret.toString),
      RequestToken(token.toString, tokenSecret.toString)
    )

    // use credentials to invoke twitter API and return Ok
    Future.successful { Ok } 
  }    
}

Play Api Documentation