リアルタイムのコラボレーション中に保存する方法


10

複数のユーザーに同じドキュメントを編集してもらいたい。私が直面している問題は、新しいユーザーが参加したときに、古いドキュメントが表示される可能性があることです。新しいユーザーが最新の変更を確実に取得する方法を教えてください。

私が考えたいくつかの解決策:

  • すべての変更を保存します。UIの動作が遅くなり、dbに負荷がかかるため、このソリューションは好きではありません。

  • 新しいユーザーが参加すると、他のすべてのクライアントで保存をトリガーします。他のクライアントが保存した後、ドキュメントをロードします。これにより、依然として矛盾が生じる可能性があります。

他の提案は参考になります。

更新:提案されたソリューションであるGoogle Realtime APIを調べたところ、次のことがわかりました。

  1. アプリのユーザーはGoogleドライブを持っている必要があり、ドライブへのアクセスを許可する必要があります。これは、せいぜいぎこちないUIフローを提示したり、Googleドライブを持たないユーザーがリアルタイム機能を使用できないようにすることができます。

  2. あなたの側で行われるすべての共有設定は、Googleドキュメント用複製する必要があります。

更新2:目標を達成するために、GoogleのFirebaseを使用しました


新しいユーザーと既にアクティブなユーザーが同じドキュメントを編集/表示しているのに違いがあるのはなぜですか?
アンディ

@Andy私が現在行っているのは、ユーザーが行うすべての変更をソケット経由でブロードキャストすることです。これらの変更は、ブラウザーを開いているユーザーのUIを更新しますが、すぐにはデータベースに保存されません。そのため、新しいユーザーが参加すると、データベースからドキュメントが読み込まれ、まだ保存されていない最近の変更がすべて表示されないという状況があります。
dev.e.loper 2013

1
すでに変更を送信していて、現在と同じ動作を残したい場合は、クライアントの1つに最後のビューを新しいクライアントに送信するよう依頼するか、すべての変更を取得し、新しいクライアントが参加したときに最新のクライアントを送信する1つの仮想クライアントをサーバーに置くことができます。それを見る。
Dainius 2013

回答:


14

グーグルドライブ

独自のバージョンのGoogleドキュメントを作成する場合は、Google Realtime APIをご覧になることをお勧めします。Googleは最近、他の開発者がリアルタイムのコラボレーションを可能にするために使用したのと同じツールを使用できるようにする目的でこれをリリースしました。これにより、開発にかかる時間を節約し、実用的な製品をより早く入手できます。

ドキュメント内のデータを簡単に取得し、定期的にデータベースにプッシュするか、データベース自体を交換の「参加者」として、すべての変更を聞いてログに記録することができます。また、リアルタイムAPIで使用できる独自のデータ構造をユーザーが定義できるため、必要に応じて自由に拡張できます。

Googleドライブ以外

したがって、あなたの調査によると、Googleドライブはオプションではありません。それは問題ありませんが、どれだけ入れたかによっては、タフになり、おそらく機能しなくなります。

この問題を解決するために使用する一般的な戦略 次のとおりです。

  1. サーバーを通信マルチプレクサにします。各ユーザーはサーバーと通信し、サーバーはその情報を他のすべてのユーザーに送信します。このように、サーバーは常にドキュメントの最新のビューを持っています。

  2. 競合解決のためのサードパーティのアルゴリズム/モジュールを見つけます。紛争の解決は困難であり、まだ完璧ではありません。これを単独で行うと、プロジェクトの範囲が大きくなりすぎてしまいます。サードパーティのアルゴリズムを使用できない場合は、1人のユーザーだけがエリアを編集できるようにすることをお勧めします。そのため、ユーザーはエリアを編集する前にロックを取得する必要があります。非常に古く、非常に速くなります。

  3. 新しいユーザーが参加したら、最新のドキュメントを提供し、コマンドのストリーミングを自動的に開始します。サーバーは最新のビューを持っているので、自動的に表示できます。

  4. 特定の間隔でデータベースにバックアップします。バックアップする頻度を決定します(5分ごと、またはおそらく50回の変更ごと)。これにより、必要なバックアップを維持できます。

問題:これは完全な解決策ではないので、直面する可能性のあるいくつかの問題を次に示します。

  1. サーバーのスループットがパフォーマンスのボトルネックになる可能性があります

  2. 読み取り/書き込みを行う人が多すぎると、サーバーが過負荷になる可能性があります

  3. メッセージが失われると、人々が同期しなくなる可能性があるため、定期的に同期するようにしてください。これは、メッセージ全体を再度送信することを意味します。


はい、変更はすべてのクライアントにブロードキャストされ、クライアントには(うまくいけば)バージョンがブラウザに表示されます。すべてのアクションでドキュメントを更新するというのは、どうすればよいのですか?
dev.e.loper 2013年

または、少なくとも定期的な「同期」タイムフレームを使用して、ドキュメントの現在の状態がバックグラウンドで送信され、全員が同じページにいることを確認します。どのくらいの頻度で、ユーザーがドキュメントを変更する速度に依存します。このようにして、新しい人に送信するための確立された方法と、それが過度に発散しないことを確認する機能がすでにあります。
Ampt 2013年

1
+1。人生を困難にしないでください。グーグルは、車輪を再発明する必要なしにこれをうまく行います。
Neil

Google RealtimeはGoogleドライブに保存されますか?Googleドライブではなくデータベースに保存したい。
dev.e.loper 2013年

@ dev.e.loperが回答に関する情報を追加しました。
Ampt、2013

3

サーバー上のドキュメントの永続的なコピーを1つお勧めします。クライアントがサーバーに接続すると、UPDATEすべての変更を含むコマンドがそのクライアントに発行されます。

ワークフローの更新

ユーザーがトリガーの変更を引き起こす->クライアントがUPDATEサーバーに送信->サーバーUPDATEがクライアントに送信

実行可能なトリガー

  1. ユーザーが[保存]をクリックする
  2. ユーザーが特定のタスクを完了する
    • セルの編集を終了します
    • 文/段落/行の編集を終了します
  3. ユーザーが[元に戻す]をクリックする
  4. ユーザーがReturnキーを押した
  5. ユーザーがキーを入力する(変更ごとに保存)

実装の更新

一連のUPDATEコマンドを使用してドキュメントを再作成できるようにすることをお勧めします。これにより、サーバーが各UPDATEを保存し、新しいクライアントが接続したときにクライアントに一連の更新を送信し、それ自体がドキュメントを再作成して表示することができます。ユーザー。また、別のSAVEコマンドを使用して、UPDATEを一時的な変更としてUNDOリクエストに使用でき、サーバーが閉じているか、すべてのクライアントが切断された場合にSAVEに実際に保存して再度開くようにすることもできます。


2
紛争解決についてはどうですか?2人が同じテキスト領域を同時に編集するとどうなりますか?また、これはDBに負荷をかけるようで、これはOPが回避しようとしていたものです。それは彼が必要とするもののために実行可能かもしれません。
Ampt、2013

@Amptこのモデルを使用してスプレッドシートを作成しました。競合が発生した場合、更新される特定の各タスクは最新バージョンに完全に置き換えられました。したがって、セルの編集を最後に完了した人は、以前に更新されたセルをマージせずに完全に置き換えます。
Korey Hinton

1
たとえば、これがワードドキュメントである場合、1つの文が別の文を上書きしますか?
Ampt、2013

@Amptはい、代わりに、作業中のものをロックする方法を実装することもできますが、私は簡単な方法を採用しました。
コレイヒントン2013

3

1)Knockout.jsを見てください

これはMVVMパターンに従い、モデルへの変更に基づいてビューに通知を自動的にプッシュします。たとえば、監視可能な配列を調べて、その方法についてもう少し情報を提供します。

2)それをSignalR組み合わせると、ドキュメントで作業している他のユーザーに通知を送信できるようになります。彼らのサイトから:

SignalRはまた、ASP.NETアプリケーションでサーバーからクライアントへのRPC(サーバー側の.NETコードからクライアントのブラウザーでJavaScript関数を呼び出す)を実行するための非常にシンプルな高レベルAPIを提供し、接続管理に役立つフックを追加しますたとえば、接続/切断イベント、グループ化接続、承認。

したがって、変更が発生するたびにSignalR呼び出しを行うには、Knockout.js内のモデルレベルでいくつかのフックを設定する必要があります。他のクライアントはSignalRからの通知を受け、その後の対応する変化をトリガーする彼らの彼らのビューまで押し戻しますモデルのコピーを、。

これは2つのフレームワークの興味深い組み合わせであり、詳細を処理するために、より多くの情報を検索および収集できるはずです。

たとえば、このコードプロジェクトの例は、具体的にはCo Working UIs and Continuous Clientsあなたがやろうとしていることのように思われるものに対処しています。

ニューエイジのWebアプリケーションは、ニューエイジのユーザーエクスペリエンスを提供する必要があり、コワーキングおよび継続的なクライアントシナリオを適切に処理する必要があります。これには、ユーザーインターフェース自体がデバイス間およびユーザー間で適切に同期し、アプリケーションとユーザーインターフェースの状態が「そのまま」維持されることを保証することが含まれます。

このブログ投稿は、2つのパッケージの使用について説明し、従来のASP.NETアプローチとは対照的である一連のブログ投稿へのエントリーポイントのようです。あなたがあなたのサイトをデザインしている間に考慮すべきいくつかのポイントを提供するかもしれません。

このブログ投稿はもう少し基本的なようで、2つのパッケージを組み合わせるための基礎を提供します。

開示:私は上記のリンクのいずれとも関係がありません。また、それらのコンテンツを実際に調べて、それがどれほど健全で正しいかを確認していません。


2

ソリューションは、運用変革(OT)です。聞いたことがない場合は、OTはマルチサイトのリアルタイム同時実行を行うアルゴリズムのクラスです。OTはリアルタイムgitのようなものです。これは、任意の量の遅延(ゼロから延長休日まで)で機能します。ユーザーは低帯域幅でライブの同時編集を行うことができます。OTは、再試行なし、エラーなし、データの上書きなしで、複数のユーザー間で結果整合性を提供します。

しかし、OTの実装は困難な作業であり、時間がかかります。したがって、http://sharejs.org/のような外部ライブラリを使用したい場合があります。


1
Google Realtime APIはOT youtu.be/hv14PTbkIs0?t=14m20s を実行しています。クライアントとサーバーの両方で実行しています。ShareJSドキュメントを読んで明確な答えを得ることができませんでしたが、ShareJSがクライアントとサーバーの両方でOTを実行すると想定していますか?
dev.e.loper 2013

1

これは主に、ドキュメントの種類とユーザーの共同作業方法に依存します。

しかし、私は:

  1. すべてのクライアントが保存されていない変更を時々サーバーに送信できるようにします(ユーザーがドキュメントをどのように処理するかによって異なります)。
  2. サーバーはユーザーのセッションにデルタを格納します(ファットクライアントの場合でもセッションのようなものが必要です)
  3. 同じドキュメントを編集/表示している他のクライアントは、それらの一時的な変更、または少なくともその可能性のあるヒントを受け取ります。

利点:

  • 誰かが「保存」をクリックしない限り、DBは更新されません。
  • クライアントがクラッシュした場合のバックアップ(セッション期間中)
  • サーバーはどのクライアントにどのデータを転送するかを決定します(たとえば、メモだけで機能をすぐに開始し、後でより高度なマージとハイライトを実装できます)

短所:

  • 「リアルタイム」ではありません-たとえば、30秒ごとに送信しますが、その時間に誰かが3つの文章を入力します。
  • ネットワークトラフィックの増加-ドキュメントとコラボレーションに依存
  • おそらく大規模なセッション
  • 多くのユーザーが共同作業を行い、多くの変更を行う場合、計算量が増える

1

基本的に、あなたが求めているのは、共有された可変状態をどのように処理するかです。保存は簡単な部分です。しかし、同時に同じものを編集している複数の人々にどのように対処しますか?同時編集をすべてリアルタイムで同期しながら、すべてのユーザーが同じドキュメントを表示できるようにします。

たぶん集まったので、難しい問題です!いくつかの実用的なソリューションがあります:

  1. 真の同時編集を許可しないようにアプリケーション要件を変更します。編集はソース管理システムと同様にマージでき、結果は各クライアントにブロードキャストされます。これを自分で作成することもできますが、ユーザーエクスペリエンスは低下します。
  2. 状態変化の同期を、既存のテクノロジーと統合するオープンソースソリューションに外部委託します。ShareDBは、この分野の現在のリーダーです。運用変革に基づいており、少なくとも1つの本番システムで使用されています。これは、あなたが懸念している節約の問題を解決しますが、共同アプリケーションに必須の追加のUX機能には役立ちません。
  3. Convergence(免責事項:私は創設者です)などの既製のプラットフォームを使用して、困難なすべてのビットを処理します。また、カーソル/マウスの追跡、選択、チャットなどのリアルタイムコラボレーション用の追加ツールを利用して、優れたコラボレーションエクスペリエンスをすばやく構築することもできます。既存のすべてのツールの適切なまとめについては、この質問を参照してください。
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.