JSONインデックス

JSONフィールドはMilvusに構造化メタデータを保存する柔軟な方法を提供します。インデックスを作成しない場合、JSONフィールドに対するクエリはフルコレクションスキャンを必要とし、データセットが大きくなるにつれて遅くなります。JSONインデックスは、JSONデータ内にインデックスを作成することで、高速な検索を可能にします。

JSON インデックスは次のような場合に最適です:

  • 一貫した既知のキーを持つ構造化スキーマ

  • 特定の JSON パスに対する等式および範囲クエリ

  • インデックスを作成するキーを正確に制御する必要があるシナリオ

  • 対象となるクエリのストレージ効率の高い高速化

多様なクエリパターンを持つ複雑なJSONドキュメントについては、JSONシュレッダーを代替手段として検討してください。

JSON インデックスの構文

JSONインデックスを作成する場合、次のように指定します:

  • JSONパス:インデックスを作成したいデータの正確な場所

  • データ・キャスト・タイプ:インデックス化された値の解釈と格納方法

  • オプションの型変換:必要に応じて、インデックス作成中にデータを変換する。

以下は、JSONフィールドにインデックスを付けるための構文です:

# Prepare index params
index_params = MilvusClient.prepare_index_params()

index_params.add_index(
    field_name="<json_field_name>",  # Name of the JSON field
    index_type="AUTOINDEX",  # Must be AUTOINDEX or INVERTED
    index_name="<unique_index_name>",  # Index name
    params={
        "json_path": "<path_to_json_key>",  # Specific key to be indexed within JSON data
        "json_cast_type": "<data_type>",  # Data type to use when interpreting and indexing the value
        # "json_cast_function": "<cast_function>"  # Optional: convert key values into a target type at index time
    }
)

パラメーター

説明

値 / 例

field_name

コレクションスキーマ内のJSONフィールドの名前。

"metadata"

index_type

JSONインデックスには、"AUTOINDEX" または"INVERTED" を指定する必要があります。

"AUTOINDEX"

index_name

このインデックスの一意識別子。

"category_index"

json_path

JSON オブジェクト内のインデックスを作成するキーへのパス。

  • トップレベル・キー:'metadata["category"]'

  • ネストされたキー:'metadata["supplier"]["contact"]["email"]'

  • JSONオブジェクト全体:"metadata"

  • サブオブジェクト:'metadata["supplier"]'

json_cast_type

値を解釈してインデックスを作成するときに使用するデータ型。キーの実際のデータ型と一致する必要があります。

使用可能なキャスト・タイプのリストについては 、以下のサポートされるキャスト・タイプ」を参照してください。

"VARCHAR"

json_cast_function

(オプション)インデックス時に元のキー値をターゲット・タイプに変換します。この設定は、キー値が間違った形式で格納されていて、インデックス作成時にデータ型を変換したい場合にのみ必要です。

使用可能なキャスト関数のリストについては、以下のサポートされるキャスト関数を参照してください。

"STRING_TO_DOUBLE"

サポートされるキャスト型

Milvusはインデックス時のキャスト用に以下のデータ型をサポートしています。これらのデータ型により、効率的なフィルタリングのためにデータが正しく解釈されます。

キャスト型

説明

JSON値の例

BOOL /bool

真/偽の条件でフィルタリングするクエリーを可能にする、ブーリアン値のインデックスに使用されます。

true,false

DOUBLE /double

整数と浮動小数点数を含む数値に使用される。範囲や等号(例えば、>,<,== )に基づくフィルタリングが可能。

42,99.99

VARCHAR /varchar

名前、カテゴリー、IDのようなテキストベースのデータによく使われる。

"electronics","BrandA"

ARRAY_BOOL /array_bool

ブール値の配列のインデックスに使用されます。

[true, false, true]

ARRAY_DOUBLE /array_double

数値の配列のインデックスに使用します。

[1.2, 3.14, 42]

ARRAY_VARCHAR /array_varchar

タグやキーワードのリストに最適。

["tag1", "tag2", "tag3"]

JSON /json

JSONオブジェクト全体またはサブオブジェクトの自動型推論と平坦化。

JSONオブジェクト全体のインデックスを作成すると、インデックスサイズが大きくなる。多キーシナリオの場合は、JSONシュレッダーを検討してください。

任意のJSONオブジェクト

最適なインデックスを作成するために、配列には同じ型の要素を含める必要があります。詳細については、「配列フィールド」を参照してください。

サポートされているキャスト関数

JSON フィールドのキーに不正な形式の値(文字列として格納された数値など)が含まれている場合、json_cast_function 引数にキャスト関数を渡すことで、インデックス作成時にこれらの値を変換できます。

キャスト関数は大文字と小文字を区別しません。以下の関数がサポートされています:

キャスト関数

変換元 → 変換先

使用例

STRING_TO_DOUBLE /string_to_double

文字列 → 数値 (double)

"99.99" に変換する。99.99

変換に失敗した場合(例:非数値文字列)、値はスキップされ、インデックスは作成されない。

JSON インデックスの作成

このセクションでは、実用的な例を使用して、さまざまなタイプの JSON データにインデックスを作成する方法を示します。すべての例では、以下に示すサンプルJSON構造を使用し、適切に定義されたコレクションスキーマでMilvusClientへの接続がすでに確立されていることを前提としています。

サンプルJSON構造

{
  "metadata": { 
    "category": "electronics",
    "brand": "BrandA",
    "in_stock": true,
    "price": 99.99,
    "string_price": "99.99",
    "tags": ["clearance", "summer_sale"],
    "supplier": {
      "name": "SupplierX",
      "country": "USA",
      "contact": {
        "email": "support@supplierx.com",
        "phone": "+1-800-555-0199"
      }
    }
  }
}

基本設定

JSONインデックスを作成する前に、インデックスパラメータを準備してください:

# Prepare index params
index_params = MilvusClient.prepare_index_params()

例 1: 単純な JSON キーにインデックスを作成する

category フィールドにインデックスを作成し、製品カテゴリによる高速フィルタリングを可能にします:

index_params.add_index(
    field_name="metadata",
    index_type="AUTOINDEX", # Must be set to AUTOINDEX or INVERTED for JSON path indexing
    index_name="category_index",  # Unique index name
    params={
        "json_path": 'metadata["category"]', # Path to the JSON key
        "json_cast_type": "varchar" # Data cast type
    }
)

例 2: 入れ子になったキーにインデックスを作成する

サプライヤーの連絡先を検索するために、深くネストされたemail フィールドにインデックスを作成します:

# Index the nested key
index_params.add_index(
    field_name="metadata",
    index_type="AUTOINDEX", # Must be set to AUTOINDEX or INVERTED for JSON path indexing
    index_name="email_index", # Unique index name
    params={
        "json_path": 'metadata["supplier"]["contact"]["email"]', # Path to the nested JSON key
        "json_cast_type": "varchar" # Data cast type
    }
)

例 3: インデックス時にデータ型を変換する

数値データが誤って文字列として格納されることがあります。STRING_TO_DOUBLE のキャスト関数を使用して適切に変換し、インデックスを作成します:

# Convert string numbers to double for indexing
index_params.add_index(
    field_name="metadata",
    index_type="AUTOINDEX", # Must be set to AUTOINDEX or INVERTED for JSON path indexing
    index_name="string_to_double_index", # Unique index name
    params={
        "json_path": 'metadata["string_price"]', # Path to the JSON key to be indexed
        "json_cast_type": "double", # Data cast type
        "json_cast_function": "STRING_TO_DOUBLE" # Cast function; case insensitive
    }
)

重要:変換に失敗したドキュメント(例えば、"invalid" のような非数値文字列)がある場合、そのドキュメントの値はインデックスから除外され、フィルタリングされた結果には表示されません。

例 4: オブジェクト全体をインデックス化する

JSONオブジェクト全体をインデックス化し、その中の任意のフィールドに対するクエリを可能にする。json_cast_type="JSON" を使用すると、システムは自動的に以下の処理を行います:

  • JSON構造をフラットにする:入れ子になったオブジェクトは、効率的なインデックス作成のためにフラットパスに変換される。

  • データ型を推測する:各値は、その内容に基づいて、数値、文字列、ブーリアン、または日付に自動的に分類される。

  • 包括的なカバレッジを作成:オブジェクト内のすべてのキーとネストされたパスが検索可能になります。

上記のサンプルJSON構造ではmetadata オブジェクト全体にインデックスを付けます:

# Index the entire JSON object
index_params.add_index(
    field_name="metadata",
    index_type="AUTOINDEX",
    index_name="metadata_full_index",
    params={
        "json_path": "metadata",
        "json_cast_type": "JSON"
    }
)

すべてのsupplier 情報など、JSON 構造の一部だけにインデックスを付けることもできます:

# Index a sub-object
index_params.add_index(
    field_name="metadata",
    index_type="AUTOINDEX", 
    index_name="supplier_index",
    params={
        "json_path": 'metadata["supplier"]',
        "json_cast_type": "JSON"
    }
)

インデックス構成の適用

すべてのインデックス・パラメータを定義したら、それらをコレクションに適用します:

# Apply all index configurations to the collection
MilvusClient.create_index(
    collection_name="your_collection_name",
    index_params=index_params
)

インデックスの作成が完了すると、JSON フィールドのクエリは自動的にこれらのインデックスを使用してパフォーマンスを向上させます。

よくある質問

クエリのフィルター式が、インデックス化されたキャスト型とは異なる型を使用する場合はどうなりますか?

フィルタ式がインデックスのjson_cast_type と異なる型を使用している場合、milvusはインデックスを使用せず、データが許す限り、より低速なブルートフォーススキャンにフォールバックする可能性があります。最高のパフォーマンスを得るためには、フィルタ式を常にインデックスのキャスト型に合わせてください。例えば、数値インデックスがjson_cast_type="double" で作成された場合、数値フィルタ条件のみがインデックスを利用します。

JSON インデックスを作成する際、JSON キーが異なるエンティティ間でデータ型に一貫性がない場合はどうなりますか?

一貫性のないデータ型は、部分的なインデックス作成につながる可能性があります。たとえば、metadata["price"] フィールドが数値 (99.99) と文字列 ("99.99") の両方として格納されている場合、json_cast_type="double" でインデックスを作成すると、数値のみがインデックス化されます。文字列形式のエントリはスキップされ、フィルタ結果には表示されません。

同じJSONキーに複数のインデックスを作成できますか?

いいえ、各JSONキーは1つのインデックスしかサポートしていません。データに一致するjson_cast_type 。ただし、JSONオブジェクト全体にインデックスを作成し、そのオブジェクト内のネストされたキーにインデックスを作成することはできます。

JSONフィールドはデフォルト値の設定をサポートしていますか?

いいえ、JSONフィールドはデフォルト値をサポートしていません。ただし、フィールドの定義時にnullable=True を設定して、空のエントリを許可することはできます。詳細については、「Nullable & Default」を参照してください。