Overview
在本指南中,您可以学习;了解如何使用 Django MongoDB后端对集合运行 MongoDB搜索查询。 MongoDB Search 使您能够对MongoDB集合执行全文搜索。 MongoDB Search 索引指定搜索行为以及要索引的字段。
样本数据
本指南中的示例使用 Movie 和 Theater 模型,它们代表Atlas示例数据集中的 sample_mflix.movies 和 sample_mflix.theaters 集合。模型类具有以下定义:
from django.db import models from django.contrib.gis.db import models from django_mongodb_backend.fields import ArrayField class Movie(models.Model): title = models.CharField(max_length=200) plot = models.TextField(blank=True) runtime = models.IntegerField(default=0) genres = ArrayField(models.CharField(max_length=100), null=True, blank=True) class Meta: db_table = "movies" managed = False def __str__(self): return self.title class Theater(models.Model): theater_id = models.IntegerField(default=0, db_column="theaterId") geo = models.PointField(db_column="location.geo") class Meta: db_table = "theaters" managed = False def __str__(self): return self.theater_id
提示
GeoDjango 字段
Theater 模型使用名为 geo 的 GeoDjango PointField 来存储地理空间数据。要学习;了解有关 GeoDjango 字段的更多信息,请参阅 地理空间数据模型指南。
Movie 和 Theater 模型包括一个内部 Meta 类(用于指定模型元数据)和一个 __str__() 方法(用于定义模型的字符串表示形式)。 要学习;了解这些模型功能,请参阅创建模型指南中的定义模型。
运行代码示例
您可以使用Python交互式Shell来运行代码示例。 要进入Shell ,请从项目的根目录运行以下命令:
python manage.py shell
进入Python Shell后,请确保导入以下模型和模块:
from <your application name>.models import Movie, Theater from django_mongodb_backend.expressions import ( SearchEquals, SearchAutocomplete, SearchExists, SearchIn, SearchPhrase, SearchQueryString, SearchRange, SearchRegex, SearchText, SearchWildcard, SearchGeoShape, SearchGeoWithin, SearchMoreLikeThis, CompoundExpression, SearchScoreOption )
要学习;了解如何创建使用 Movie 模型和Python交互式Shell与MongoDB文档交互的Django应用程序,请访问入门教程。
运行MongoDB搜索查询
要运行MongoDB搜索查询,请使用 Django 的 QuerySet API中的 annotate() 方法。将MongoDB搜索条件(包括搜索操作符)作为 score 参数传递给 annotate()。以下代码显示了运行搜索查询的基本语法:
Model.objects.annotate( score=<Search Operator>(path="<field name", <additional arguments>) )
要指定搜索操作符,请使用 django_mongodb_backend.expressions 模块提供的表达式类。每个类对应一个 Search操作符。
以下部分介绍如何使用每个支持的表达式类运行搜索查询。
SearchEquals
重要
其他索引要求
在搜索查询中使用SearchEquals 表达式之前,请创建一个搜索索引,将相关字段索引为令牌类型。从 Django MongoDB后端 v5.2.2 开始,您可以使用 field_mappings 参数来创建此索引。
SearchEquals表达式匹配字段等于指定值的文档。 这对应于MongoDB equals 操作符。
要使用此操作符,请将以下参数传递给 SearchEquals() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。value:要匹配的值。您可以指定一个字符串值或一个Value实例。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchEquals操作符查询sample_mflix.movies集合中 title 值为 "Finding Nemo" 的文档:
Movie.objects.annotate(score=SearchEquals(path="title", value="Finding Nemo"))
SearchAutocomplete
重要
其他索引要求
SearchAutocomplete在搜索查询中使用 表达式之前,请创建一个搜索索引,将相关字段索引为自动完成类型。从 Django MongoDB后端 v5.2.2 开始,您可以使用 field_mappings 参数来创建此索引。
SearchAutocomplete表达式搜索包含不完整输入字符串中的字符序列的单词或短语。 这对应于MongoDB autocomplete 操作符。
要使用此操作符,请将以下参数传递给 SearchAutocomplete() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。query:要自动完成的输入字符串。 您可以指定一个字符串值或一个Value实例。fuzzy:(可选)启用模糊匹配并允许配置其行为的字典。示例,您可以指定{"maxEdits": 1}以允许在匹配搜索术语之前更改一个字符。要查看所有可用值,请参阅MongoDB Atlas文档中的自动完成选项。token_order:(可选)配置词元序列行为的字符串。您可以将此值设立为"sequential"或"any"。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchAutocomplete表达式查询sample_mflix.movies集合中 title 值以 "First" 开头的文档:
Movie.objects.annotate(score=SearchAutocomplete(path="title", query="First"))
SearchExists
SearchExists表达式匹配存在指定字段的文档。这对应于MongoDB exists 操作符。
要使用此操作符,请将以下参数传递给 SearchExists() 构造函数:
path:要匹配的字段的名称。您可以指定一个字符串值或一个F实例。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchExists表达式在 sample_mflix.movies集合中查询具有 plot字段的文档:
Movie.objects.annotate(score=SearchExists(path="plot"))
SearchIn
重要
其他索引要求
SearchIn在搜索查询中使用 表达式之前,请在相关字段上创建搜索索引。如果要查询string 字段,则必须将其索引为令牌类型。从 Django MongoDB后端 v5.2.2 开始,您可以使用 field_mappings 参数来创建此索引。
SearchIn表达式匹配字段值位于给定列表中的文档。这对应于MongoDB in操作符。
要使用此操作符,请将以下参数传递给 SearchIn() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。value:要匹配的值列表。您可以指定值列表或Value实例。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchIn表达式查询sample_mflix.movies集合中 runtime 值为 100、200 或 300 分钟的文档:
Movie.objects.annotate(score=SearchIn(path="runtime", value=[100, 200, 300]))
SearchPrase
SearchPhrase表达式匹配字段中精确或接近精确的词语序列。这对应于MongoDB短语操作符。
要使用此操作符,请将以下参数传递给 SearchPhrase() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。query:要匹配的短语。您可以指定一个字符串或字符串列表。slop:(可选)短语术语之间允许的最大术语数。synonyms:(可选)搜索索引中定义的同义词映射的名称。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchPhrase表达式查询sample_mflix.movies集合中 plot字段中包含短语 "space adventure" 的文档,这些词语之间最多允许 2 个单词:
Movie.objects.annotate(score=SearchPhrase(path="plot", query="space adventure", slop=2))
SearchQueryString
SearchQueryString操作符允许您对 string 字段执行文本、通配符、正则表达式、模糊和范围搜索。 这对应于MongoDB queryString 操作符。
要使用此操作符,请将以下参数传递给 SearchQueryString() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。query:Lucene 样式的查询字符串。 要学习;了解有关Lucene查询语法的更多信息,请参阅Apache Lucene文档。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchQueryString表达式在 sample_mflix.movies集合查询与 plot字段上的 Lucene 式查询匹配的文档:
Movie.objects.annotate(score=SearchQueryString(path="plot", query="romance AND (paris OR tokyo)"))
SearchRange
重要
其他索引要求
SearchRange在搜索查询中使用 表达式之前,请在相关字段上创建搜索索引。如果要查询string 字段,则必须将其索引为令牌类型。从 Django MongoDB后端 v5.2.2 开始,您可以使用 field_mappings 参数来创建此索引。
SearchRange表达式搜索指定范围内的值。您可以提供范围数值、日期、字符串或 ObjectId 值。 这对应于MongoDB范围操作符。
要使用此操作符,请将以下参数传递给 SearchRange() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。lt:(可选)排除上限 (<)lte: (可选) 包含上限 (<=)gt:(可选)排除下限 (>)gte: (可选) 包含下限 (>=)score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchRange表达式查询sample_mflix.movies集合中 runtime 值介于 90 和 120 分钟之间的文档。
Movie.objects.annotate(score=SearchRange(path="runtime", gt=90, lt=120))
SearchRegex
SearchRegex表达式使用正则表达式匹配字符串字段值。 这对应于MongoDB正则表达式操作符。
要使用此操作符,请将以下参数传递给 SearchRegex() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。query:用于搜索字段内容的正则表达式字符串。allow_analyzed_field:(可选)一个布尔值,表示是否允许与分析字段进行匹配。默认值为False。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchRegex表达式查询sample_mflix.movies集合中 title 值包含单词 "winter" 的文档:
Movie.objects.annotate(score=SearchRegex(path="title", query=r".*winter.*"))
搜索文本
SearchText表达式对字符串字段执行全文搜索。 这对应于MongoDB文本操作符。
要使用此操作符,请将以下参数传递给 SearchText() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。query:搜索术语或短语。fuzzy:(可选)启用模糊匹配并允许配置其行为的字典。示例,您可以指定{"maxEdits": 1}以允许在匹配搜索术语之前更改一个字符。match_criteria:(可选) 是否匹配包含"all"或"any"个搜索词的文档。默认值为"any"。synonyms:(可选) Atlas索引中定义的同义词映射的名称。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchText表达式在 sample_mflix.movies集合中查询plot字段包含 "sudden disappearance" 的文档,并启用了模糊匹配:
Movie.objects.annotate(score=SearchText( path="plot", query="sudden disappearance", fuzzy={"maxEdits": 2}, match_criteria="all" ))
SearchWildcard
SearchWildcard表达式使用通配符模式匹配字符串。这对应于MongoDB操作符。
要使用此操作符,请将以下参数传递给 SearchWildcard() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。query:通配符字符串,可能包含*字符以匹配任何字符序列,以及?字符以匹配任何单个字符。allow_analyzed_field:(可选)允许与分析字段进行匹配的布尔值。默认值为False。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchWildcard表达式查询sample_mflix.movies集合中 title 以 "Star" 开头并以任意字符结尾的文档:
Movie.objects.annotate(score=SearchWildcard(path="title", query="Star*"))
SearchGeoShape
重要
其他索引要求
SearchGeoShape在搜索查询中使用 indexShapestrue5.2.2表达式之前,请创建一个搜索索引,将相关字段索引为地理类型,并将 属性设立为 。从 Django MongoDB后端 v 开始,您可以使用 field_mappings 参数来创建此索引。
SearchGeoShape表达式根据与形状的空间关系过滤文档。 这对应于MongoDB geoShape 操作符符。
要使用此操作符,请将以下参数传递给 SearchGeoShape() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。relation:要测试的空间关系。有效值包括"within"、"intersects"和"disjoint"。geometry:要与之比较的GeoJSON几何对象。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchGeoShape表达式在 sample_mflix.theaters集合中查询在指定多边形内具有 geo 值的文档:
chicago = { "type": "Polygon", "coordinates": [ [ [-87.851, 41.976], [-87.851, 41.653], [-87.651, 41.653], [-87.651, 41.976], [-87.851, 41.976], ] ] } theaters = Theater.objects.annotate(score=SearchGeoShape( path="geo", relation="within", geometry=chicago ))
SearchGeoWithin
重要
其他索引要求
在搜索查询中使用SearchGeoWithin 表达式之前,请创建一个搜索索引,将查询字段索引为地理类型。从 Django MongoDB后端 v5.2.2 开始,您可以使用 field_mappings 参数来创建此索引。
SearchGeoWithin表达式筛选具有指定形状中包含的地理字段的文档。 这对应于MongoDB geoWithin 操作符符。
要使用此操作符,请将以下参数传递给 SearchGeoWithin() 构造函数:
path:要搜索的字段的名称。您可以指定一个字符串值或一个F实例。kind: GeoJSON几何类型:"circle"、"box"或"geometry"。geometry:定义空间边界的GeoJSON几何图形。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchGeoWithin操作符查询sample_mflix.theaters集合以查找具有指定圈子内 geo 值的文档:
circle = { "center": {"type": "Point", "coordinates": [-73.98, 40.75]}, "radius": 5000 } theaters = Theater.objects.annotate(score=SearchGeoWithin( path="geo", kind="circle", geometry=circle ))
SearchMoreLikeThis
SearchMoreLikeThis表达式查找与所提供示例类似的文档。 这对应于MongoDB moreLikeThis 操作符。
要使用此操作符,请将以下参数传递给 SearchMoreLikeThis() 构造函数:
documents:作为相似性提供服务的示例文档或表达式列表。score:(可选)用于配置相关性分数的SearchScoreOption实例。
以下示例使用 SearchMoreLikeThis表达式在 sample_mflix.movies集合中查询与所提供示例文档相似的文档:
Movie.objects.annotate(score=SearchMoreLikeThis([ {"title": "The Godfather"}, {"genres": ["Crime", "Drama"]} ]))
组合表达式
您可以通过以下方式执行结合多个搜索表达式的MongoDB搜索查询:
使用“CompoundExpression”类
CompoundExpression表达式允许您使用布尔逻辑来组合多个搜索表达式。这对应于MongoDB复合运算符符。
您必须将以下一个或多个参数传递给 CompoundExpression() 构造函数:
must:文档必须匹配的表达式列表should:文档应匹配的表达式列表must_not:文档不得匹配的表达式列表filter:过滤结果的表达式列表
您还可以传递以下可选参数:
minimum_should_match:文档必须匹配的最小should子句数score:用于配置相关性分数的 SearchScoreOption 实例
此示例使用 CompoundExpression表达式在 sample_mflix.movies集合中查询符合以下条件的文档:
plot字段存在plot字段包含文本"fast-paced"genres字段不包含"Romance"或"Comedy"
plot_exists = SearchExists(path="plot") plot_text = SearchText(path="plot", query="fast-paced") genres_range = SearchIn(path="genres", value=["Romance", "Comedy"]) Movie.objects.annotate( score=CompoundExpression( must=[plot_exists, plot_text], must_not=[genres_range] ) )
使用按位操作符
您可以使用以下按位运算符来组合搜索表达式:
&:表示逻辑 AND 运算|:表示逻辑 OR 运算~:代表逻辑 NOT 运算
此示例使用 |操作符查询sample_mflix.movies集合以查找与以下一个或两个条件匹配的文档:
plot字段包含文本"heartwarming"genres字段包含"Romance"或"Comedy"
expr = SearchText(path="plot", query="heartwarming") | SearchIn(path="genres", value=["Romance", "Comedy"]) Movie.objects.annotate(score=expr)
配置相关性分数
MongoDB为搜索查询中返回的每个文档分配一个相关性分数。结果设立包含的文档按相关性分数从高到低排序。
您可以使用 SearchScoreOption表达式自定义MongoDB计算和应用相关性分数的方式。SearchScoreOption() 构造函数接受以下参数:
boost:增加与指定表达式匹配的文档的分数constant:对所有匹配应用固定分数function:应用函数来计算分数path:根据字段值对文档进行评分
提示
要学习;了解有关相关性分数的更多信息,请参阅MongoDB Atlas文档中的对结果中的文档进行评分。
以下示例将与 SearchEquals表达式匹配的文档的相关性得分提高了 3 倍:
boost = SearchScoreOption({"boost": {"value": 3}}) Movie.objects.annotate( score=SearchEquals( path="title", value="Life of Pi", score=boost ) )
更多信息
要学习;了解有关创建MongoDB搜索索引的更多信息,请参阅创建索引指南中的搜索索引。
要学习;了解有关MongoDB搜索查询的更多信息,请参阅MongoDB Atlas文档中的MongoDB搜索概述。