ディスパッチ結果をリクエストに使用される URL とパラメータでラップする次のモナドを scala に実装しました。
import org.json4s._
import scala.concurrent.{ExecutionContext, Future}
case class Result[T](url:String,params:JValue,result:Future[T]) {
self =>
def flatMap[S](f: T => Result[S])(implicit executionContext:ExecutionContext):Result[S] = {
val result_ = f andThen (_.result)
Result(self.url,self.params,this.result flatMap result_)
}
def map[B](f: T => B)(implicit executionContext:ExecutionContext):Result[B] =
Result(this.url,this.params,this.result map f )
}
私が抱えている問題は、の定義にありflatmap
ます。flatmap
が正しいためには、とurl
がparams
から来ている必要がありf
ますf: T => Result[S]
。上記の例では、正常にコンパイルされ、署名はまさに私が必要としているものですが、self.url
andは、 andがedで更新されていないことをself.params
意味します。つまり、 and変数を取得する方法がわかりませんが呼び出されているときのアプリケーションから。url
params
Result
flatMap
url
param
f
flatMap
にはT
が必要ですが、 andにRequest[S]
は必要ありません。適切に定義できるように をから分離するスカラの方法は何でしょうか?url
params
url,params
result
flatMap
注: モナドの背後にある一般的な目的はHTTP
、ディスパッチ (つまりFuture[T]
) の結果を処理しながら、 を更新してリクエストに使用できるようにすることurl
です。を変更しますparams
flatMaps
url
params
result
result
編集:これは私が現在モナドをどのように使用しているかの例です
val restResponse = for {
token <- Authenticate.Helpers.mainLogin // Type Result[String]
userSessionToken <- Authenticate.Helpers.loginToken("someUser","somePassword",token) // Type Result[String]
someOtherCommand <- DataService.getInitialData(token,userSessionToken) map
(_ \ "someData" \ "someMoreData" \\ "evenMoreData" match {
case JString(s) => s
case JArray(items) =>
items.collectFirst { case JString(s) =>s}.head
}) // Type Result[String], the map is working over the `JValue` inside Future[JValue] that is held within the Request[JValue]
someData <- DataService.getData(token,userSessionToken) // Type Result[JValue]
} yield itemSummaries
println(restResponse.url) // should print the url of someData, but is instead printing the url of token. restResponse.result is the correct value however
以前は、これは理解のFuture[T]
ためにうまくいきましたが、そうすると、使用されているURL/パラメーターが失われたことに注意してください