Docs Menu
Docs Home
/ /
/ / /

インデックスの作成

このガイドでは、Dpango モデルを使用してMongoDBインデックスを作成する方法を学習できます。インデックスはクエリの効率を向上させ、クエリとドキュメントストレージの追加機能を提供します。

インデックスがないと、 MongoDB はコレクション内のすべてのドキュメントをスキャンして 、クエリに一致するドキュメントを見つける必要があります。 これらのコレクションスキャンは遅く、アプリケーションのパフォーマンスに悪影響を与える可能性があります。 ただし、クエリに適切なインデックスがある場合、 MongoDB はそのインデックスを使用して検査するドキュメントを制限できます。

Dlango は、モデルにインデックスを作成するために使用できる Indexクラスを提供します。 Dlango MongoDBバックエンドは、モデルが表すMongoDBコレクションに同じインデックスを作成します。

Tip

Indexクラスの詳細については、Diango ドキュメントの Index を参照してください。

このガイドの例では、nutritionフィールドの値として埋め込み Nutrition モデルを含む Recipe モデルを使用します。 これらのモデル クラスには、次の定義があります。

from django.db import models
from django.db.models import Q, F
from django_mongodb_backend.models import EmbeddedModel
from django_mongodb_backend.fields import EmbeddedModelField, ArrayField
from django_mongodb_backend.indexes import SearchIndex, VectorSearchIndex
class Nutrition(EmbeddedModel):
calories = models.IntegerField(default=0)
carb_grams = models.IntegerField(default=0)
protein_grams = models.IntegerField(default=0)
class Recipe(models.Model):
title = models.CharField(max_length=200)
cuisine = models.CharField(max_length=200)
cook_time = models.IntegerField(default=0)
allergens = ArrayField(models.CharField(max_length=100), null=True, blank=True)
ratings = ArrayField(models.IntegerField(default=0), size=10)
nutrition = EmbeddedModelField(Nutrition, null=True, blank=True)
class Meta:
db_table = "recipes"
def __str__(self):
return self.title

Recipe モデルの Metaクラスでは、db_table = "recipes" オプションは、Recipe モデルを recipes と呼ばれるMongoDBコレクションにマッピングするように Diango MongoDBバックエンドに指示します。モデルを使用してMongoDBコレクションを操作する Djangoアプリケーションを作成する方法については、「を使い始める」チュートリアルをご覧ください。

モデルにインデックスを作成するには、モデルの Metaクラスで indexes オプションを指定します。 この indexes オプションの値を、次のコードに示すように、作成するインデックスのリストに設定します。

class Meta:
indexes = [
models.Index(<first index definition>),
models.Index(<second index definition>),
# add more indexes here
]

インデックスを定義するには、次の引数を models.Index() メソッドに渡します。

  • fields:インデックスを作成するフィールドのリストを指定します。 この引数は必須です。

  • name:インデックス名を指定します。 この引数は任意であり、指定しない場合は Diango がインデックス名を自動的に作成します。

  • condition:インデックスを作成するドキュメントのサブセットを指定します。 この引数は任意です。 condition引数の詳細については、このガイドの「 部分インデックス 」セクションを参照してください。

データベース移行を適用すると、Diango MongoDBバックエンドはMongoDBコレクションに同じインデックスを作成します。

Tip

データベース移行を作成して適用する方法については、Dpango ドキュメントの移行を参照してください。

このセクションでは、次のインデックスタイプの作成方法を説明します。

単一フィールドインデックスは、コレクション内の単一フィールドからの情報を保存します。 デフォルトでは 、すべてのMongoDBコレクションには _idフィールドのインデックスがあります。

次の例では、 Recipe モデルの Metaクラスを更新して titleフィールドに単一のフィールドインデックスを作成します。これによりMongoDBバックエンドは recipesコレクションに作成します。

class Meta:
db_table = "recipes"
indexes = [
models.Index(fields=["title"], name="title_idx"),
]

あるいは、次のコードに示すように、モデルの titleフィールドに db_index オプションを設定して、インデックスを作成することもできます。

class Recipe(models.Model):
title = models.CharField(max_length=200, db_index=True)

複合インデックスは、コレクション内の複数のフィールドからデータを収集してソートします。 MongoDB は、インデックスで指定された最初のフィールドごとにデータをグループ化し、その後は後続のフィールドごとにデータをグループ化します。

次の例では、 Recipe モデルの Metaクラスを更新して title フィールドと cook_time フィールドに複合インデックスを作成します。これによりMongoDBバックエンドは recipesコレクションに作成します。

class Meta:
db_table = "recipes"
indexes = [
models.Index(fields=["title", "cook_time"]),
]

マルチキー インデックスは、配列フィールドからデータを収集してソートします。 配列フィールドにインデックスを作成すると、 MongoDB は自動的にそのインデックスをマルチキーインデックスとして設定します。

次の例では、 Recipe モデルの Metaクラスを更新して allergens 配列フィールドに複合インデックスを作成します。これによりMongoDBバックエンドは recipesコレクションに作成します。

class Meta:
db_table = "recipes"
indexes = [
models.Index(fields=["allergens"], name="allergy_idx"),
]

埋め込みモデル値を保存するフィールドにインデックスを作成できます。埋め込みドキュメントとしてMongoDB は埋め込みドキュメントとして表現します。

次の例では、 Recipe モデルの Metaクラスを更新して nutrition 埋め込みモデルフィールドにインデックスを作成します。このMongoDBは recipesコレクションに作成されます。

class Meta:
db_table = "recipes"
indexes = [
models.Index(fields=["nutrition"]),
]

重要

前の例で作成されたインデックスは、埋め込みドキュメント全体を指定するクエリでのみ使用されます。 埋め込みドキュメント内の特定のフィールドに対するクエリでは、インデックスは使用されません。 ただし、内部 Metaクラスを Nutrition モデルに追加し、indexes オプションを指定することで、埋め込みドキュメント内のフィールドにインデックスことができます。

このセクションでは、次の高度なインデックスタイプの作成方法を説明します。

警告

検索インデックスの移行

新しいMongoDB Search またはベクトル検索インデックス を作成し、データベース移行コマンドを実行すると、Diango が移行を適用するまでに時間がかかる場合があります。データの整合性を確保するために、Diango はMongoDB がインデックス操作を完了するまでブロックします。コレクションのサイズに応じて、移行が完了するまでに 秒または 分かかる場合があります。

MongoDB Search インデックスは、 MongoDBコレクションに対する全文検索であるMongoDB Search クエリの動作を指定します。

検索インデックスを作成するには、モデルの Metaクラスの indexes オプションを SearchIndexオブジェクトに割り当てます。次の引数を任意の順序で SearchIndex() コンストラクターに渡します。

  • fields:インデックスを作成するフィールド。

  • name:(任意) 検索インデックスの名前。この引数を指定しない場合、Diango はインデックス名を自動的に生成します。

Diango MongoDBバックエンド v5.2.2 以降では、次の引数を SearchIndex() に渡すこともできます。

  • field_mappings:(任意)フィールド名をインデックスオプションにマッピングする辞書。 fieldsの代わりにこの引数を使用して、個々のフィールドに対してインデックス動作を指定する複雑な検索インデックスを作成できます。

  • analyzer:(任意) インデックス作成中に string フィールドに適用するアナライザ。この引数を指定しない場合、 MongoDB Server はデフォルトでlucene.standard になります。

  • search_analyzer:(任意)クエリ テキストに適用するアナライザ。この引数を指定しない場合、その値はanalyzer 値と同じになります。両方の引数を省略すると、 MongoDB Server はデフォルトでlucene.standard になります。

Tip

MongoDB Search のクエリとインデックスの詳細については、次のリソースを参照してください。

次の例では、 Recipe モデルの Metaクラスを更新して、titleフィールドに "title_search_idx" という名前の基本検索インデックスを作成します。

class Meta:
db_table = "recipes"
indexes = [
SearchIndex(
fields=["title"],
name="title_search_idx",
)
]

次の例では、 cuisineフィールドをtoken 型としてインデックス化し、アナライザをlucene.simple に設定する検索インデックスを作成します。

class Meta:
db_table = "recipes"
indexes = [
SearchIndex(
name="cuisine_search_idx",
field_mappings={
"cuisine": {
"type": "token"
}
},
analyzer="lucene.simple"
)
]

Tip

前の例の検索インデックス構成の詳細については、Atlas ドキュメントの次のリソースを参照してください。

MongoDB ベクトル検索インデックスを使用すると、キーワード一致ではなく、セマンティック意味に基づいてデータをクエリできます。ベクトル検索を全文検索クエリとAIフレームワークと統合して、ユースケースの範囲をサポートできます。

ベクトル検索インデックスを作成するには、モデルの Metaクラスの indexes オプションを VectorSearchIndexオブジェクトに割り当てます。次の引数を任意の順序で VectorSearchIndex() コンストラクターに渡します。

  • name:(任意)ベクトル検索インデックスの名前。この引数を指定しない場合、Diango はインデックス名を自動的に生成します。

  • fields:インデックスを作成するフィールド。少なくとも 1 つは、サイズ のある FloatField または IntegerField の値の配列で表されるベクトルフィールドである必要があります。

  • similarities: 使用する類似度関数"cosine""dotProduct"、または "euclidean" 類似度関数を使用できます。関数は、単一の string 値または個々のベクトルフィールドに関数を割り当てる値のリストとして指定されます。

次の例では、Recipe モデルの Metaクラスを更新して、ratingsベクトルフィールドと cook_time 数値フィールドに "vector_search_idx" という名前のベクトル検索インデックスを作成します。

class Meta:
db_table = "recipes"
indexes = [
VectorSearchIndex(
name=["vector_search_idx"],
fields=["ratings", "cook_time"],
similarities=["cosine", "euclidean"],
)
]

Tip

ベクトル検索のクエリとインデックスの詳細については、次のリソースを参照してください。

部分インデックスでは、コレクション内の指定フィルター条件を満たすドキュメントのみがインデックス、ストレージ使用量とパフォーマンスのコストが削減されます。

部分インデックスを作成するには、condition 引数を models.Index() メソッドに渡します。 条件値をフィルター条件を含む Qオブジェクトに設定します。 condition 引数を使用する場合は、name 引数も models.Index() に渡す必要があります。

Tip

Q オブジェクトの詳細については、Diango ドキュメントの Q を参照してください。

次の例では、 Recipe モデルの Metaクラスを更新して cuisineフィールドに部分インデックスを作成し、Diango MongoDBバックエンドに cook_time の値が 30 より小さいドキュメントのみをインデックスに指示します。

class Meta:
db_table = "recipes"
indexes = [
models.Index(fields=["cuisine"],
condition=Q(cook_time__lt=30),
name="fast_cuisine_idx"),
]

一意なインデックス により、インデックス フィールドに重複する値が保存されるのを防ぐことができます。 単一のフィールドでは、一意のインデックスにより、指定されたフィールドに値が最大 1 回表示されるようになります。 複数のフィールドでは、一意なインデックス により、インデックスキー値の任意の組み合わせが最大 1 回表示されるようになります。

次の例では、 Recipe モデルの cuisineフィールド を更新し、unique オプションを True に設定して一意の単一フィールドインデックスを作成します。

cuisine = models.CharField(max_length=200, unique=True)

注意

unique オプションを True に設定すると、指定されたフィールドにインデックスが自動的に作成されます。

次の例では、 Recipe モデルの Metaクラスを更新して、title フィールドと cuisine フィールドに複合インデックスを作成します。 このコードでは、constraintsオプションを UniqueConstraintインスタンスに設定し、次のフィールドに一意の複合インデックスを作成します。

class Meta:
db_table = "recipes"
constraints = [
models.UniqueConstraint(fields=["title", "cuisine"],
name="unique_regional_meal"),
]

Tip

constraints オプションを UniqueConstraint に設定すると、指定されたフィールドにインデックスが自動的に作成されます。Meta クラスの constraint オプションの詳細については、Dmango ドキュメントの「 制約 」を参照してください。

このガイドで言及されているインデックスの種類の詳細については、次のMongoDB Serverマニュアル リソースを参照してください。

Dlango モデルでのインデックス作成の詳細については、Diango ドキュメントの Index を参照してください。

戻る

データのモデル化

項目一覧