Scala Spray Routing - 为单个请求执行的两个 HTTP 方法指令

Scala Spray Routing - two HTTP method directives executed for single request

这是我的路线:

pathPrefix("event" / Segment / "user") { id =>
    pathEnd {
        put {
            dbService.addParticipant(id, user)
            complete("OK")
        } ~
        delete {
            dbService.removeParticipant(id, user)
            complete("OK")
        }
    }
} ~  

当向 http://localhost:9999/event/860852c4-768f-430e-9a9d-d1d35e86ede2/user 发送 PUT 或 DELETE 请求时,两个方法指令都会被执行 - 我的意思是 dbService.addParticipant(id, user)dbService.removeParticipant(id, user) 被调用。谁能解释一下这里的问题在哪里?

我看不出这与 official spray example 有何不同:

// extract URI path element as Int
pathPrefix("order" / IntNumber) { orderId =>
  pathEnd {
    // method tunneling via query param
    (put | parameter('method ! "put")) {
      // form extraction from multipart or www-url-encoded forms
      formFields('email, 'total.as[Money]).as(Order) { order =>
        complete {
          // complete with serialized Future result
          (myDbActor ? Update(order)).mapTo[TransactionResult]
        }
      }
    } ~
    get {
      // JSONP support
      jsonpWithParameter("callback") {
        // use in-scope marshaller to create completer function
        produce(instanceOf[Order]) { completer => ctx =>
          processOrderRequest(orderId, completer)
        }
      }
    }
  }

作为@jrudolph pointed out,非叶提取指令中的代码(就像在 pathPrefix("order" / IntNumber) { orderId => 中一样,因为它采用将从请求中提取的 orderId 参数)每次执行request 不管里面的指令是否命中路由。叶指令中的代码(如 complete)仅在路由匹配时执行。

要实现您可能想要的效果,只需将 dbService.addParticipant 移到 complete:

pathPrefix("event" / Segment / "user") { id =>
    pathEnd {
        put {
            complete {
              dbService.addParticipant(id, user)
              "OK"
            }
        } ~
        delete {
            complete {
              dbService.removeParticipant(id, user)
              "OK"
            }
        }
    }
}