web-dev-qa-db-ja.com

AndroidアプリとWebサーバー間でデータを同期する

Androidアプリとサーバーの間でデータ(db record、mediaなど)を同期したいのですが。 Evernoteまたは類似のアプリケーションを見たことがあれば、きっと私の意味を理解しているはずです。

いくつか質問があります(DBレコードを同期したいと想像してください)。

  1. すべてのユーザーは自分用のサーバー領域の一部を持っています(EvernoteDropboxなど)。ユーザーが携帯電話で新しいレコードを作成し、サーバーに新しいレコードを作成するのかもしれません。 どうすればこれらのレコードを一致させることができますか?同じIDのレコードがある場合どのようなアルゴリズムが推奨されますか?

  2. JSONを除く携帯電話とサーバー間でデータを送信する方法はありますか?

  3. SyncAdapterContentProviderが問題を解決できる場合は、正確に説明してください。 (もしあなたが私にいくつかのサンプルやチュートリアルを提供できればOR私の検索を広げて/導くのを助けるどんなアドバイスやキーワードも同様に高く評価されるでしょう)。

247
Omid Nazifi

大きい質問に答えて、すべての質問に回答します。WebサーバーとAndroidアプリの間でデータを同期するにはどうすればよいですか?


WebサーバーとAndroidアプリの間でデータを同期するには、Androidデバイス上にいくつかの異なるコンポーネントが必要です。

永続ストレージ

これは、実際に携帯電話がWebサーバーから受信したデータを実際に保存する方法です。これを達成するための1つの可能な方法は、Sqliteデータベースに裏打ちされたあなた自身のカスタムContentProviderを書くことです。コンテンツプロバイダのためのまともなチュートリアルはここで見つけることができます: http://thinkandroid.wordpress.com/2010/01/13/writing-your-own-contentprovider/

AContentProviderは、保存されているデータとやり取りするための一貫したインタフェースを定義します。必要に応じて、他のアプリケーションがあなたのデータとやり取りすることも可能になります。 ContentProviderの背後には、Sqliteデータベース、キャッシュ、または任意のストレージメカニズムがあります。

SqliteデータベースでContentProviderを使うことを私は確かにお勧めしますが、あなたが望む任意のJavaベースのストレージメカニズムを使うことができます。

データ交換フォーマット:

これは、WebサーバーとAndroidアプリの間でデータを送信するために使用する形式です。最近よく使われている2つのフォーマットはXMLとJSONです。あなたのフォーマットを選ぶとき、あなたはどんな種類の直列化ライブラリが利用可能であるかについて考えるべきです。私は、gsonと呼ばれるjsonシリアライゼーションのための素晴らしいライブラリがあることを手元に知っています。 https://github.com/google/gson XMLにも同様のライブラリが存在することを確認してください。

同期サービス

サーバーから新しいデータを取得し、モバイルコンテンツを更新してサーバーのコンテンツを反映させることができる、ある種の非同期タスクが必要になります。また、コンテンツにローカルの変更を加えたときはいつでもサーバーに通知し、それらの変更を反映させることもできます。 Androidは、このパターンを簡単に解決する方法としてSyncAdapterパターンを提供しています。あなたはユーザーアカウントを登録する必要があるでしょう、そしてそれからAndroidはあなたのためにたくさんの魔法を実行し、そしてあなたが自動的に同期することを可能にします。これは良いチュートリアルです: http://www.c99.org/2010/01/23/writing-an-Android-sync-provider-part-1/


レコードが同じかどうかを識別する方法については、通常、一意のIDを持つアイテムを作成し、それをAndroidデバイスとサーバーの両方に保存します。同じ参照を参照していることを確認するためにそれを使用できます。さらに、 "updated_at"のような列属性を格納して、常に最新のデータを取得できるようにしたり、誤って新しく書き込まれたデータを上書きしないようにすることができます。

303
Grantismo

今日今日について考えると、 受け入れられた答え は古すぎます。私たちが知っているように、この種のアプリケーションを作るのを助けることができるたくさんの新しいライブラリがあります。

あなたはきっとあなたを助けてくれる次のトピックを学ぶべきです:

  • SyncAdapter: アプリケーションの同期アダプタコンポーネントは、デバイスとサーバー間でデータを転送するタスクのコードをカプセル化します。アプリで提供したスケジュールとトリガーに基づいて、同期アダプタフレームワークは同期アダプタコンポーネントのコードを実行します。

  • Realm :Realmはモバイルデータベースです。SQLiteとCore Dataに代わるものです。

  • Retrofit Square、Inc.によるAndroidおよびJava用のタイプセーフHTTPクライアント。学ぶ必要があります a-smart-way-使用後付け

データベースの同期ロジックは次のようになります。 Android携帯のSQLiteデータベースとサーバーのMySQLデータベースを同期するにはどうすればよいですか?

すべての新しい学習者に頑張ってください。 :)

あなたがこれをあなた自身で書くならば、これらは覚えておくべきポイントのいくつかです

デバイスと同期サーバー間の適切な認証

デバイスとサーバー間の同期プロトコル。それは通常、認証、データ交換、ステータス交換(どの操作がうまくいったか、そしてどれが失敗したか)の3段階で行われます。

ペイロードフォーマットを選択してください。実際のデータを表すために、SyncMLベースのXMLとJSONベースの形式を混在させることをお勧めします。プロトコルにはSyncML、実際に交換されるデータにはJSONを使用します。 JSON Arrayを使用してデータにアクセスするのは簡単なので、データを操作しながらJSON Arrayを使用することが常に推奨されます。

クライアントとサーバーの両方でデータの変更を追跡します。同期セッション中に変更されたIDの変更履歴を管理できます。また、オブジェクトが正常に同期されたら、変更ログを消去します。同期ステータス、つまり最後の同期時刻を確認するためにブール変数を使用することもできます。最後の同期が行われた時刻をエンドユーザーが識別するのに役立ちます。

サーバー上でデータが変更されたときに同期セッションを開始するには、サーバーからデバイスに通信する方法が必要です。あなたはC2DMを使用するか、あなた自身の永続的なtcpベースのコミュニケーションを書くことができます。 TCPアプローチはとてもシームレスです

複数のデバイス間でデータの変更を複製する方法

そして最後に大事なことを言い忘れましたが、競合を検出して処理する方法

これが良い出発点として役立つことを願っています。

24
openmobster

@Grantismoは全体的に優れた説明を提供します。誰が実際にこのことを行っているのか知りたいのであれば、2014年のGoogle IO AppでGoogleがどのように機能したかを見てみることをお勧めします。彼らがリリースするアプリ。そこから学ぶことがたくさんあります。

これはそれについてのブログ記事です: http://Android-developers.blogspot.com.br/2014/09/conference-data-sync-gcm-google-io.html

基本的には、アプリケーション側では、シグナリング用のGCM、データのフェッチおよびコンテンツプロバイダとの適切な通信を行うための同期アダプタを使用します(そう、アプリケーションの他の部分からの直接アクセスからDBを分離します)。

また、2015年のコードをご覧になりたい場合は、 https://github.com/google/iosched をご覧ください。

14
Ciro Costa

たとえば、テーブルtodoTableMySqlからSqliteに同期するとします。

まず、todoTableSqliteの両方に対して、MySqlに列名version (type INT)を作成します enter image description here

次に、1つの列名currentVersion(INT)を持つテーブル名database_versionを作成します。
enter image description here

MySqlでは、todoTableに新しい項目を追加するか、項目を更新するときに、この項目のバージョンを+1だけアップグレードし、currentVersionをアップグレードする必要があります enter image description here

Androidで、(手動で同期ボタンを押すか、期間を指定してサービスを実行して)同期する場合:

Sqlite currentVersion(現在は1)を使用してリクエストをサーバーに送信します。
サーバーでは、MySqlのどの項目がSqliteのcurrentVersion(1)より大きいバージョン値を持つかがわかります(この例では、バージョン2の項目3がAndroidに応答します)。

SQLiteでは、todoTableに新しい項目を追加または更新し、currentVersionをアップグレードします。

7
Phan Van Linh

parseplatform.org をご覧ください。それはオープンソースプロジェクトです。

(同様にあなたが back4app.com で利用可能な商用パッケージに行くことができます。)

それは素晴らしいAndroidクライアントサイドAPIを提供する非常に簡単でユーザーフレンドリーなサーバーサイドデータベースサービスです。

6
Kyle

これを達成するための1つの方法は、データを待つサーバー側アプリケーションを用意することです。データはJavaのHttpRequestオブジェクトを使って送信することも、独自のTCP/IPデータ転送ユーティリティを書くこともできます。データはJSONフォーマットまたはあなたが適切であると思う他のフォーマットを使って送ることができます。機密情報が含まれている場合は、サーバーに送信する前にデータを暗号化することもできます。すべてのサーバーアプリケーションは、HttpRequestsが入ってきてデータを解析し、必要な場所に保存するのを待つだけです。

3
Mayank

@Grantismoは、Androidの同期コンポーネントの概要を説明しています。

SyncManagerAndroidライブラリは、Android Syncフレームワーク(AbstractThreadedSyncAdapter.OnPerformSync)にプラグインするための単純な双方向同期実装を提供します。

https://github.com/sschendel/SyncManagerAndroid

1
Sean

Hessian に似たバイナリWebサービスプロトコルを使用することをお勧めします。それは非常にうまく機能し、彼らはAndroidの実装を持っています。少し重いかもしれませんが、構築しているアプリケーションによって異なります。お役に立てれば。

1
Neo