SDK for Android 開発者ガイド

CLE2 オフラインを使用しています

検索リクエストは、サーバーに対してオンラインで、またはローカルデバイスに対してオフラインで実行できます。 ローカルデータに対するオフライン検索を有効にするため に、 HERE SDK ではデータを事前取得するさまざまな方法が用意されています。

オフライン モードには次の利点があるため、できるだけ多くの利点があります。

  • ネットワークの不安定性に対する耐障害性。
  • ネットワーク帯域幅をより効率的に使用できます。 オブジェクトごとに 1 つのリクエストを送信する代わりに、リクエストをローカルに集約し、データをバッチで送信できます。
  • ネットワーク帯域幅の節約。 アプリでは、ユーザーの現在の場所に近いデータをキャッシュおよび更新できます。また、レイヤーをプレダウンロードできるのは、 WiFi ネットワークが利用可能になった場合のみです。
  • データがすでにローカルでデバイスで利用できるようになっているため、アプリケーションの応答性が向上し、ユーザー体験とインターフェイスのやり取りが改善される可能性があります。
  • HERE SDK を使用してジオメトリを作成または変更し、データソースおよび情報のストレージとして HERE SDK を効果的に使用してローカルに保存します。

オフラインの CLE2 機能は、簡単に使用できるように設計されています。 すべてのデータベースの同期化と地理空間関連の複雑さは SDK によって処理されるため、アプリ開発の他の部分に集中できます。

ローカルストレージを照会しています

ローカルに保存されたデータを使用して検索するには OFFLINE 、目的のの接続モードをに設定 CLE2Request して、要求を実行します。

CLE2ProximityRequest proximitySearch =
  new CLE2ProximityRequest("HERE_TEST", map.getCenter(), 1000);
proximitySearch.setConnectivityMode(CLE2Request.CLE2ConnectivityMode.OFFLINE);

proximitySearch.execute(new CLE2Request.CLE2ResultListener() {
  @Override
  public void onCompleted(CLE2Result result, String error) {
    if (!error.equals(CLE2Request.CLE2Error.NONE)) {
      // process search results
    } else {
      // handle error
    }
  }
});

検索リクエストをハイブリッドモードまたは自動モードに設定して、オンラインリクエスト中に接続が切断された場合、またはネットワークエラーが発生した場合に、リクエストが自動的にオフライン操作に戻るように指定できます。 検索の実行に使用された接続モードを確認することで、検索がオンラインまたはオフラインのどちらで実行されたかを確認できます。 これは、CLE2ResultオブジェクトgetConnectivityModeUsed()を呼び出して行うことができます。

CLE2ProximityRequest proximitySearch
  = new CLE2ProximityRequest("HERE_TEST", map.getCenter(), 1000);
proximitySearch.setConnectivityMode(CLE2Request.CLE2ConnectivityMode.AUTO);

proximitySearch.execute(new CLE2Request.CLE2ResultListener() {
  @Override
  public void onCompleted(CLE2Result result, String error) {
    if (!error.equals(CLE2Request.CLE2Error.NONE)) {
      // check if data came from online or offline search
      boolean isDataFromServer = result.getConnectivityModeUsed() == CLE2Request.CLE2ConnectivityMode.ONLINE;
    } else {
      // handle error
    }
  }
});
      

ローカルストレージにデータを入力する方法

デフォルトでは、オフライン機能は無効になっており、ローカルストレージにデータが含まれていません。 オフライン検索で使用できるようにジオメトリを追加するには、次の 3 つの方法があります。

  1. などの 1 つ以上のリクエストを実行した後に、検索結果をキャッシュ CLE2ProximityRequestしています。 属性リクエストはキャッシュできません。
  2. 1 つ以上のレイヤーをダウンロードしています。
  3. ローカルデータベースにデータを直接挿入します。

データベースにデータを入力した後 CLE2ConnectivityMode.OFFLINE、各リクエストの接続モードをに切り替えることで、通常どおりオフライン モードでデータをクエリーできます。

CLE2DataManager および CLE2Task

CLE2DataManager このオブジェクトは、ローカルストレージとの中央の対話ポイントです。 この機能を使用すると、次のことが可能になります。

  • 特定のレイヤーのすべてのジオメトリをダウンロードします
  • 現在合計または特定のレイヤーに保存されているジオメトリの数を確認します
  • 特定のレイヤーに属するジオメトリを削除します
  • すべてのアイテムを削除して、ローカルストレージを消去します
  • ローカルまたはリモートのジオメトリを作成、更新、または削除します

CLE2DataManager 公開さ CLE2Task れているデータ管理に関連するすべての操作で、作業単位を表すを使用します。 すべてのデータ管理操作にデータベースアクセス、ネットワーク通信、またはその両方が含まれているため、 CLE2Task は非同期で実行されます。 CLE2Task からオブジェクトを取得 CLE2DataManagerできます。

では CLE2Task、次のことができます。

  • コードの他の部分に渡し CLE2Task ます。は、自己完結型の作業単位です。
  • 操作の結果をサブスクライブします。 複数のサブスクライバがサポートされ、メインスレッドで呼び出されます。
  • タスクの実行を開始します。 タスクは再利用できます。 複数回繰り返し実行できるため、失敗した操作の再試行が非常に簡単になります。
  • 実行中のタスクをキャンセルします。
  • タスクが開始されているかどうかを確認してください。
  • タスクが完了したかどうかを確認してください。
  • タスクが完了するまで待ちます。
  • タスクから、完了した操作のステータスを直接取得します ( エラーを確認 ) 。
  • 正常に終了した操作の結果をタスクから直接取得します。

検索結果をキャッシュしてデータを保存しています

でキャッシュが有効になっている場合 CLE2Request、返されたすべてのジオメトリが自動的にローカルに保存されます。 リクエストをアクティブ化する setCachingEnabled(true) には、リクエストを実行する前に電話をかけてください。

// set query
String query = "CITY=='Berlin'";
request.setQuery(query);

// set Geometry type
request.setGeometry(CLE2GeometryType.LOCAL);

// to cache response
request.setCachingEnabled(true);

request.execute(new CLE2Request.CLE2ResultListener() {
  @Override
  public void onCompleted(CLE2Result result, String error) {
    if (!error.equals(CLE2Request.CLE2Error.NONE)) {
      // request succeeded, which means that the results are now stored locally
    } else {
      // handle error
    }
  }
});

// Now some geometries are in local storage.
// At a later point in time if you'd like to make an offline search,
// switch the connectivity mode to offline.

レイヤーをダウンロードしてデータを保存しています

2 つ目のオプションは、newDownloadLayerTask()メソッドを使用してローカルストレージにデータを挿入するためにCLE2DataManager使用します。

次に、 CLE2 サーバからレイヤ全体をダウンロードする例を示します。

CLE2DataManager.getInstance().newDownloadLayerTask("MYLAYER").start(
  new CLE2Task.Callback<CLE2OperationResult>() {
    @Override
    public void onTaskFinished(CLE2OperationResult result, CLE2Error error) {
      if (error.getErrorCode() == CLE2ErrorCode.NONE) {
        // download succeeded
      } else {
        // handle download error
      }
    }
  });

ローカルストレージから個々のレイヤーを削除したり、ローカルに保存されているすべてのデータを完全に消去したりすることもできます。

// fire and forget method of running tasks (no callback)
CLE2DataManager.getInstance().newDeleteLayersTask(Arrays.asList(new String[]{"MYLAYER"}), StorageType.LOCAL).start();

// by specifying StorageType.REMOTE, it is possible to delete the layers from CLE2 server, so be careful

// wipe out all local data
CLE2DataManager.getInstance().newPurgeLocalStorageTask().start(new CLE2Task.Callback<CLE2OperationResult>() {
  @Override
  public void onTaskFinished(CLE2OperationResult result, CLE2Error error) {
    if (error.getErrorCode() == CLE2ErrorCode.NONE) {
      // notify user that all his data is gone
    }
  }
});

形状を挿入してデータを保存しています

クラス newGeometryTask() のメソッドを使用 CLE2DataManager すると、位置情報ベースのデータを生成して、ローカル、リモート、またはその両方に保持できます。 このファクトリメソッドは CLE2Task 、いつでも操作の結果を開始、キャンセル、または取得するために使用できるオブジェクトを返します。

public CLE2Task<CLE2OperationResult> newGeometryTask(
    OperationType operationType,
    String layerId,
    List<CLE2Geometry> geometryData,
    StorageType storageType)
  • このメソッドの最初のパラメータは、次のいずれかの操作タイプを記述します。
    • OperationType.CREATE
    • OperationType.UPDATE
    • OperationType.DELETE
    ジオメトリのクエリは CLE2Request 、それぞれの特殊なクラスを介して実行されるため、「読み取り」の操作 HERE は作成されません。
  • 2 番目のパラメーターは、操作を適用するレイヤーです。
  • 3 番目のパラメーターは、形状自体を含むリストです。
  • 最後のパラメータでは、HERE CLE2 サーバを使用してローカルストレージ (StorageType.LOCAL) またはリモートストレージ (StorageType.REMOTE) のどちらで操作するかを定義します。
注 : このセクションでは、ローカルオプションでのこのメソッドの使用方法について説明しますが、すべての操作 ( 作成、更新、削除 ) を使用してリモートレイヤーを変更することもできます。

次の例では、形状を作成してローカルに保存する方法を示します。


final int geometryCount = 100;
Random rand = new Random();
List<CLE2Geometry> geometries = new ArrayList<>(geometryCount);

// generate random point across the globe
for (int i = 0; i < geometryCount; i++) {
  GeoCoordinate newPoint = new GeoCoordinate(
      (rand.nextFloat()) * 180 - 90,
      (rand.nextFloat()) * 360 - 180);

  CLE2PointGeometry point = new CLE2PointGeometry(newPoint);
  point.setAttribute("i", Integer.toString(i));
  point.setAttribute("COLOR", rand.nextInt() % 2 == 0 ? "BLUE" : "RED");
  geometries.add(point);
}

// create task for storing new geometries locally
// if the layer does not exist already, it is created,
// otherwise the geometries are added to existing layer
CLE2Task<CLE2OperationResult> createLocal = CLE2DataManager.getInstance().newGeometryTask(
    OperationType.CREATE, "RED_VS_BLUE", geometries, StorageType.LOCAL);

createLocal.start(new CLE2Task.Callback<CLE2OperationResult>() {
  @Override
  public void onTaskFinished(CLE2OperationResult result, CLE2Error error) {
    if (error.getErrorCode() == CLE2ErrorCode.NONE) {
      // success
    }
  }
});

ローカルレイヤーをアップロードしています

ローカルに保存されたレイヤーをサーバーにアップロードできます。 この処理には 2 つの操作 ( ローカルストレージからのフェッチとアップロード ) が必要なため、コールバックへの侵入を防ぐために、個々のタスクを同期的に実行することをお勧めします。 もちろん、これは AsyncTask などの独自のスレッドで行う必要があります。


AsyncTask<String, Void, Boolean> localToRemoteAsyncTask = new AsyncTask<String, Void, Boolean>() {
  @Override
  protected Boolean doInBackground(String... strings) {
    CLE2DataManager dataManager = CLE2DataManager.getInstance();
    boolean success = false;
    for (String layerId : strings) {
      // grab data from local storage
      CLE2Task<List<CLE2Geometry>> fetchLocalTask = dataManager
          .newFetchLocalLayersTask(Arrays.asList(new String[] {layerId}))
          .start()
          .waitForResult(5, TimeUnit.SECONDS);

      success = fetchLocalTask.isFinished()
          && fetchLocalTask.getError().getErrorCode() == CLE2ErrorCode.NONE;
      if (!success) {
        break;
      }

      // upload the data to the server creating a new layer or replacing existing one
      CLE2Task<CLE2OperationResult> uploadTask = dataManager
          .newUploadLayerTask(layerId, fetchLocalTask.getResult())
          .start()
          .waitForResult(15, TimeUnit.SECONDS);

      success = uploadTask.isFinished()
          && uploadTask.getError().getErrorCode() == CLE2ErrorCode.NONE;
      if (!success) {
        break;
      }
    }
    return success;
  }
};

データ管理に関する考慮事項

オフラインで CLE2 を使用する場合にデータ管理を行う際に役立つヒントを次に示します。

ローカルのみの形状

すべての CLE2Geometry オブジェクトには、次のプロパティがあります。

  1. ジオメトリ ID 。でアクセスできます getGeometryId()
  2. locality フラグ。でアクセスできます isLocal()

ジオメトリ ID はレイヤーに固有です。 ジオメトリオブジェクトが作成されたばかりの場合、そのジオメトリ ID はで null 、ローカル性フラグはです false

locality フラグは、このジオメトリがローカルコンテキストにのみ属しているかどうかを示します。つまり、このジオメトリは取得されなかったか、 CLE2 サーバーを通過しなかったことを示します。 true 局所性フラグが設定されたジオメトリには、ローカルで生成された一意のジオメトリ ID があります。 それ以外の場合は、サーバー指定の ID が含まれます。 このサーバー指定の ID は、によって作成 newGeometryTask()されたデータベースに直接保存されている形状のローカルで生成された ID には関連付けられません。

注 : サーバーを通過せずにジオメトリをローカルに保存する機能が提供されているため、接続が利用できない場合に、これらのオブジェクトのデータの永続性を管理する必要はありません。

簡単にするために、ジオメトリをローカルデータベースに直接保存する場合は、別のレイヤー名を使用してジオメトリを保持してください。 後で必要な時点でこれらのジオメトリをサーバーと共有する必要がある場合 は、CLE2DataManagernewFetchLocalLayersTask()メソッドを使用してすべてのローカルジオメトリを取得し、newUploadLayerTask()またはnewGeometryTask()作成操作 (OperationType.CREATE) を使用してアップロードします。 これにより isLocal() 、プロパティを確認する必要がなくなります。

これらの概念を使用すると、ジオメトリを異なるレイヤーやコンテキストに移動し、これらのツールを使用してデータを整理できます。

データの整合性

の使用 newUploadLayer() は主に管理者ユーザーに限定する必要があります。この方法では、サーバー内の既存のすべてのジオメトリが削除され、提供されているジオメトリを使用してレイヤーが再作成されるためです。 ユーザーがこのレイヤーの最新の情報を持っていない場合、別のユーザーのアップロードが上書きされる可能性があるため、データが失われる可能性があります。

したがって、連続的または同時的なジオメトリのアップロードを行うシナリオで newGeometryTask() は、 OperationType.CREATE メソッドをまたはで使用 OperationType.UPDATEします。 「追加のみ」の方法で操作するか、または既存のジオメトリのみを更新することで、ユーザーがジオメトリをサーバーに同時にアップロードしている場合でもデータの損失を回避できます。

現在の制限事項

現在、 CLE2 サーバの個別のユーザーアカウント管理は利用できません。 セキュリティ上の理由から、アプリ資格情報を完全に非表示にしておくように注意してください。 アプリケーションでユーザーアカウントのアクセス機能が必要な場合 は、サービスサポート連絡して詳細を確認してください

注 : 地理空間クエリーは CLE2 の中心であるため 、 HERE SDK ではオフライン モードでの属性検索をサポートしていません。 地理空間クエリの 1 つ ( 近接など ) を使用してデータをフィルタリングし、結果を十分な数に絞り込むことができます。その結果をさらにフィルタリングするには、ジオメトリの属性キー値辞書を反復処理して、ほとんどのアプリケーションでパフォーマンスへの影響がないようにします。