ClojureScript、Om、Core.async: イベントを適切に処理する方法 質問する

ClojureScript、Om、Core.async: イベントを適切に処理する方法 質問する

リッチクライアントのウェブサイトデザインにOmを使うことを検討しました。core.asyncを使うのは今回が初めてです。チュートリアルを読んでhttps://github.com/swannodette/om/wiki/基本チュートリアル削除操作を処理するために core.async チャネルが使用されているのを見たことがあります (ハンドラーですべての作業を行うのではなく)。削除にそのチャネルを使用するのは、そのアイテムを含むリストを実際に操作するアイテム レベルにカーソルがあるスコープで削除コールバックが宣言されているからだという印象を受けました。

チャネルについてさらに詳しく知るために、リッチ・ヒッキーの講演を見ましたhttp://www.infoq.com/presentations/clojure-core-asyncここで彼は、イベントコールバックからアプリケーションロジックを取り出すためにチャネルを使用するのがいかに良いアイデアであるかを説明しています。このことから、チュートリアルの削除チャネルの実際の目的は、アプリケーションを構築する方法を示すことだったのではないかと考えました。もしそうなら、

  • そのパターンに関連するベストプラクティスは何ですか?

  • すべての種類のイベントに対して個別のチャネルを作成する必要がありますか? つまり、新しいイベントを作成するためのコントローラーを追加する場合、アプリケーション内の別の場所のグローバル状態にオブジェクトを追加するために使用されるオブジェクト作成用の新しいチャネルも作成することになりますか?

  • アイテムのリストがあり、そのうちの 1 つのアイテムに詳細/簡潔な状態フラグがあるとします。 の場合は、detailed?よりtrue多くの情報が表示され、 の場合は、detailed?よりfalse少ない情報が表示されます。カーソル (グローバル状態オブジェクト内のリスト項目へのビュー) で使用するクリック時イベントを関連付けましたom/transact!

(let [toggle-detail-handler 
      (fn [e]
        (om/transact! (get-in myitem [:state])
                      #(conj % {:detailed? (not (:detailed? %))})))]
  (html [:li {:on-click toggle-detail-handler}
         "..." ])) 

これは非常に簡潔なスニペットである可能性があり、コールバック イベントを実際のロジックの変更から分離する手段としてチャネルを使用することの全体的な利点は、最初は労力に見合わないように思われますが、より複雑な例での全体的な利点はこれを上回ります。しかし、一方で、このような詳細/詳細でない切り替えのために追加のチャネルを導入すると、ソース コードにかなりの負荷がかかるようにも思われます。

デザイン全体の問題について、ヒントやアドバイス、その他の考えを教えていただければ幸いです。視点ちょっと迷った気がします。

ベストアンサー1

カーソル経由で通信できないコンポーネント間の通信にはチャネルを使用します。

たとえば、次のような場合にチャネルを使用します。

  • 通信コンポーネントはアプリの状態を共有しません (例: カーソルが階層データ構造の異なるブランチを指している)
  • アプリの状態外でリアルタイムに伝達される変更(例えば、コンポーネント A がコンポーネント B のローカル状態を変更したいが、コンポーネント B は A の子ではない(そうでない場合は に渡すことで実行できる:stateom/build
  • Omコンポーネントツリーの外部と通信したい

私は「ドメイン状態」をアプリ状態アトムに保持し、GUI状態をコンポーネントのローカル状態に保持することを好みます。つまり、アプリの状態とはレンダリングされており、地方自治体は. (ここで、「どのように」はどの部分を指すかを示します) たとえば、テキスト エディターを作成している場合、アプリの状態は編集中のドキュメントであり、ローカルの状態は編集中のページ、太字が選択されているかどうかなどです。

一般的に、私はペアを配置する単一の通信チャネルを使用します[topic value]。次に、パブそしてサブメッセージをルーティングします。たとえば、(def p (async/pub ch first))トピックを使用してイベントをディスパッチし、トピックを(om/sub p my-ch :foo)使用してメッセージを受信します。通常、この単一の通信チャネルを Om の共有状態に保存します。:foomy-ch

複数のチャネルを使用することがありますが、これは汎用的なメッセージングのためではなく、特定のパイプラインやワークフローを設定するために行います。たとえば、データ ストリームに対して処理を行う処理コンポーネントのパイプラインがある場合、エンドポイントを Om アプリケーションに接続したチャネル チェーンとして設定する場合があります。一般的な UI 開発では、これはまれです。また、Om コンポーネント用に Qt 風のシグナル/スロット システムを試しており、共有シグナル チャネルを使用するか、各シグナルを独自のチャネルにするかをまだ実験中です。どちらのアプローチが優れているかはまだ決まっていません。

おすすめ記事