セカンダリインデックス機能を使用すると、指定した列にインデックスを作成できます。生成されたインデックステーブルのデータは、指定されたインデックスキー列に基づいてソートされます。データテーブルに書き込まれたすべてのデータは、インデックステーブルに自動的に同期されます。データテーブルにデータを書き込んだ後、データテーブル用に作成されたインデックステーブルからデータをクエリできます。これにより、クエリの効率が向上します。
サンプルシナリオ
このトピックでは、セカンダリインデックス機能を使用して通話記録をクエリする方法について説明します。通話が完了すると、通話に関する情報がデータテーブルに記録されます。
次のセクションでは、データテーブルのプライマリキー列と事前定義された列について説明します。
CellNumber列とStartTime列は、データテーブルのプライマリキー列として使用されます。CellNumber列の各値は発信番号を示し、StartTime列の各値は通話の開始時刻を示します。
CalledNumber、Duration、およびBaseStationNumber列は、データテーブルの事前定義された列として使用されます。CalledNumber列の各値は着信番号を示し、Duration列の各値は通話時間を示し、BaseStationNumber列の各値は基地局番号を示します。
次の表に、データテーブルのサンプルデータを示します。Tablestoreのワイドカラムモデルは、データテーブルの行をプライマリキーに基づいてソートし、GetRange操作を提供してデータをクエリします。
CellNumber | StartTime (UNIXタイムスタンプ) | CalledNumber | Duration | BaseStationNumber |
123456 | 1532574644 | 654321 | 60 | 1 |
234567 | 1532574714 | 765432 | 10 | 1 |
234567 | 1532574734 | 123456 | 20 | 3 |
345678 | 1532574795 | 123456 | 5 | 2 |
345678 | 1532574861 | 123456 | 100 | 2 |
456789 | 1532584054 | 345678 | 200 | 3 |
ビジネス要件に基づいて、データテーブル、グローバルセカンダリインデックス、またはローカルセカンダリインデックスを使用して、次のクエリを実行できます。
CellNumber列の値が234567である行をクエリします。
CalledNumber列の値が123456である行をクエリします。
BaseStationNumber列の値が2で、StartTime列の値が1532574740である行をクエリします。
BaseStationNumber列の値が3で、StartTime列の値が1532574861から1532584054の範囲である行のDuration列の値をクエリします。
基地局3によって転送されたすべての通話の合計、平均、最大、および最小通話時間をクエリします。StartTime列の値は1532574861から1532584054の範囲です。
CellNumber列の値が456789で、CalledNumber列の値が345678である行をクエリします。
データクエリ
クエリ要件に基づいて、適切な方法を選択してデータをクエリできます。
方法
次の表に、さまざまなクエリを実装する方法を示します。
データテーブルとセカンダリインデックステーブルの作成に使用されるサンプルコードの詳細については、「付録:データテーブルとセカンダリインデックステーブルを作成するためのサンプルコード」を参照してください。
データテーブルを作成したら、サンプルデータをデータテーブルに書き込む必要があります。データテーブルのデータは、データテーブル用に作成されたインデックステーブルに自動的に同期されます。データの書き込み方法の詳細については、「データの書き込み」を参照してください。
Tablestoreは、インデックスキー列として指定されていないデータテーブルのプライマリキー列を、データテーブル用に作成されたインデックステーブルに自動的に追加します。データテーブルのプライマリキー列とインデックスキー列は、インデックステーブルのプライマリキー列として使用されます。
ローカルセカンダリインデックスを使用する場合、インデックステーブルの最初のプライマリキー列は、インデックステーブルが作成されるデータテーブルの最初のプライマリキー列と同じである必要があります。
クエリ | 方法 |
CellNumber列の値が234567である行をクエリする | GetRange操作を直接呼び出して、データテーブルをスキャンできます。 |
CalledNumber列の値が123456である行をクエリする | CalledNumber列に基づいてインデックステーブルを作成し、GetRange操作を呼び出してインデックステーブルをスキャンできます。 |
BaseStationNumber列の値が2で、StartTime列の値が1532574740である行をクエリする | BaseStationNumber列とStartTime列に基づいてインデックステーブルを作成し、インデックスタイプがグローバルセカンダリインデックスであるインデックステーブルをスキャンするためにGetRange操作を呼び出すことができます。 |
BaseStationNumber列の値が3で、StartTime列の値が1532574861から1532584054の範囲である行のDuration列の値をクエリする | BaseStationNumber列とStartTime列に基づいてインデックステーブルを作成し、Duration列の値のみが返されるように指定してから、インデックスタイプがグローバルセカンダリインデックスであるインデックステーブルをスキャンするためにGetRange操作を呼び出すことができます。 データテーブルからDuration列の値を手動でクエリするか、Duration列をインデックステーブルの属性列として指定できます。 基地局3によって転送され、開始時刻が1532574861から1532584054の範囲であるすべての通話の合計、平均、最大、および最小通話時間をクエリするには、このクエリ方法も使用できます。次に、Duration列で集計を実行して最終結果を取得できます。 説明 クライアント側の計算なしでSQLステートメントを実行して結果を取得することもできます。詳細については、「データのクエリ」を参照してください。 |
CellNumber列の値が456789で、CalledNumber列の値が345678である行をクエリする | CellNumber列とCalledNumber列に基づいてインデックステーブルを作成し、Duration列とBaseStationNumber列をインデックステーブルの属性列として指定してから、インデックスタイプがローカルセカンダリインデックスであるインデックステーブルをスキャンするためにGetRange操作を呼び出すことができます。 |
CellNumber列の値が234567である行をクエリする
CalledNumber列の値が123456である行をクエリする
BaseStationNumber列の値が2で、StartTime列の値が1532574740である行をクエリするBaseStationNumber列の値が2で、StartTime列の値が1532574740である行をクエリする
BaseStationNumber列の値が3で、StartTime列の値が1532574861から1532584054の範囲である行のDuration列の値をクエリする
CellNumber列の値が456789で、CalledNumber列の値が345678である行をクエリするCellNumber 列の値が 456789 で、CalledNumber 列の値が 345678 である行をクエリします
付録:データテーブルとセカンダリインデックステーブルを作成するためのサンプルコード
次のサンプルコードは、このトピックで使用されているデータテーブルとセカンダリインデックステーブルを作成する方法を示しています。インデックスタイプには、ローカルセカンダリインデックスとグローバルセカンダリインデックスが含まれます。
private static final String TABLE_NAME = "CallRecordTable";
private static final String INDEX0_NAME = "IndexOnBeCalledNumber";
private static final String INDEX1_NAME = "IndexOnBaseStation1";
private static final String INDEX2_NAME = "IndexOnBaseStation2";
private static final String INDEX3_NAME = "LocalIndexOnBeCalledNumber";
private static final String PRIMARY_KEY_NAME_1 = "CellNumber";
private static final String PRIMARY_KEY_NAME_2 = "StartTime";
private static final String DEFINED_COL_NAME_1 = "CalledNumber";
private static final String DEFINED_COL_NAME_2 = "Duration";
private static final String DEFINED_COL_NAME_3 = "BaseStationNumber";
private static void createTable(SyncClient client) {
TableMeta tableMeta = new TableMeta(TABLE_NAME);
tableMeta.addPrimaryKeyColumn(new PrimaryKeySchema(PRIMARY_KEY_NAME_1, PrimaryKeyType.INTEGER));
tableMeta.addPrimaryKeyColumn(new PrimaryKeySchema(PRIMARY_KEY_NAME_2, PrimaryKeyType.INTEGER));
tableMeta.addDefinedColumn(new DefinedColumnSchema(DEFINED_COL_NAME_1, DefinedColumnType.INTEGER));
tableMeta.addDefinedColumn(new DefinedColumnSchema(DEFINED_COL_NAME_2, DefinedColumnType.INTEGER));
tableMeta.addDefinedColumn(new DefinedColumnSchema(DEFINED_COL_NAME_3, DefinedColumnType.INTEGER));
// データの有効期間(TTL)を指定します。単位:秒。値-1は、データが期限切れにならないことを示します。データテーブルに1つ以上のインデックステーブルがある場合は、timeToLiveの値を-1に設定する必要があります。
int timeToLive = -1;
// 保持できるデータバージョンの最大数を指定します。データテーブルに1つ以上のインデックステーブルがある場合は、maxVersionsの値を1に設定する必要があります。
int maxVersions = 1;
TableOptions tableOptions = new TableOptions(timeToLive, maxVersions);
ArrayList<IndexMeta> indexMetas = new ArrayList<IndexMeta>();
IndexMeta indexMeta0 = new IndexMeta(INDEX0_NAME);
indexMeta0.addPrimaryKeyColumn(DEFINED_COL_NAME_1);
indexMetas.add(indexMeta0);
IndexMeta indexMeta1 = new IndexMeta(INDEX1_NAME);
indexMeta1.addPrimaryKeyColumn(DEFINED_COL_NAME_3);
indexMeta1.addPrimaryKeyColumn(PRIMARY_KEY_NAME_2);
indexMetas.add(indexMeta1);
IndexMeta indexMeta2 = new IndexMeta(INDEX2_NAME);
indexMeta2.addPrimaryKeyColumn(DEFINED_COL_NAME_3);
indexMeta2.addPrimaryKeyColumn(PRIMARY_KEY_NAME_2);
indexMeta2.addDefinedColumn(DEFINED_COL_NAME_2);
indexMetas.add(indexMeta2);
IndexMeta indexMeta3 = new IndexMeta(INDEX3_NAME);
indexMeta3.addPrimaryKeyColumn(PRIMARY_KEY_NAME_1);
indexMeta3.addPrimaryKeyColumn(DEFINED_COL_NAME_1);
indexMeta3.addDefinedColumn(DEFINED_COL_NAME_2);
indexMeta3.addDefinedColumn(DEFINED_COL_NAME_3);
// indexUpdateModeの値をIUM_SYNC_INDEXに設定します。
indexMeta3.setIndexUpdateMode(IUM_SYNC_INDEX);
// indexTypeの値をIT_LOCAL_INDEXに設定します。
indexMeta3.setIndexType(IT_LOCAL_INDEX);
indexMetas.add(indexMeta3);
CreateTableRequest request = new CreateTableRequest(tableMeta, tableOptions, indexMetas);
client.createTable(request);
}