4

このコードには、いくつかの厄介なネストされたチェックが含まれています...

わかりやすいように書き直すことができると確信していますが、パターンマッチングのものをどのように混合するかについて少し混乱しています

// first tries to find the token in a header: "authorization: ideas_token=xxxxx"
// then tries to find the token in the querystring: "ideas_token=xxxxx"
private def applicationTokenFromRequest(request: Request[AnyContent]): Option[String] = {

  val fromHeaders: Option[String] = request.headers.get("authorization")
  val tokenRegExp = """^\s*ideas_token\s*=\s*(\w+)\s*$""".r

  val tokenFromHeader: Option[String] = {
    if (fromHeaders.isDefined) {
      val header = fromHeaders.get
      if (tokenRegExp.pattern.matcher(header).matches) {
        val tokenRegExp(extracted) = header
        Some(extracted)
      } else {
        None
      }
    } else {
      None
    }
  }

  // try to find it in the queryString
  tokenFromHeader.orElse {
    request.queryString.get("ideas_token")
  }

}

あなたが私に与えることができるヒントはありますか?

4

1 に答える 1

7

for-comprehensionで抽出子を使用するだけで、多くの粗雑さを取り除くことができます。

val Token = """^\s*ideas_token\s*=\s*(\w+)\s*$""".r

val tokenFromHeader = for {
  Token(t) <- request.headers.get("authorization")
} yield t

tokenFromHeader orElse request.queryString.get("ideas_token")

しかし、以下はさらに簡潔で、私の目には少し明確です。

val Token = """^\s*ideas_token\s*=\s*(\w+)\s*$""".r

request.headers.get("authorization") collect {
  case Token(t) => t
} orElse request.queryString.get("ideas_token")

ただし、この 2 つは本質的に同等です。どちらの場合も、値 (存在する場合) を から取り出してOption、正規表現と一致するかどうかを確認するだけです。

于 2012-10-30T16:34:26.683 に答える