質問

私たちのプロジェクトではReactiveMongoを使用してPlay 2.2.1を使用しています。

問題は、Enumerator[A]によって返されるReactiveMongoの形式でデータのストリームに、実際にはカンマによって区切られていない値オブジェクトのストリームであり、扱うことができるストリームの開始と終了注釈を持っていません。アレイ開口部とクローズ記述として。

これは、予想されるフォーマットがあるため、JSONコンシューマJS clientに問題が発生します。 [A1,A2, ...]

だから私たちはフープに飛び乗って、最初の要素である場合、Enumeratee[A]Enumerator[String]に変換しました。

    var first:Boolean = true
    val aToStrs = (as.map(a => {
        if(first) {
            first = false;
            Json.stringify(Json.toJson(a))
        } else {
            "," + Json.stringify(Json.toJson(a))
        }
   }))
   Ok.chunked(
       Enumerator.enumInput(Input.El("[")) andThen
       aToStrs andThen
       Enumerator.enumInput(Input.El("]")) andThen
       Enumerator.enumInput(Input.EOF)
   )
.

これは機能しますが、ホイールを発明するように感じます。

この一般的な問題のためのより良い解決策はありますか?

役に立ちましたか?

解決

あなたが彗星やeventsourceを使うならば、あなたが出力を生成する方法を手にしなければならず、実際にクライアント内のアイテムの応答アイテムを解析することもできます。アレイで回答すると、JavaScriptでBuild Int JSONパーサーを使用する前に、自分の解析コードを作成するか、すべてがクライアント側に到着するまで待機することができます。

ストリーミングEventSourceプロトコルではかなり簡単で、Playによく簡単になり、次のようなことができるはずです。

implicit val cometEncoder = new Comet.CometMessage[JsValue](_.toString)
Ok.chunked(yourEnumerator &> EventSource()).as(EVENT_STREAM)
.

とクライアントのHTMLで:

<script type="text/javascript">
  var es = new EventSource(jsRouter.controllers.Application.streamIt().url)

  es.addEventListener("message", function (event) {
    var item = JSON.parse(event.data)
    // ... do something with the json value ...
  })
</script>
.

$YOUR_PLAY_DIR/samples/scala/eventsource-clock/

を調べたいプレイサンプルプロジェクトにはこれの例があります。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top