管理索引
本页面介绍了如何管理索引。如需详细了解索引,请参阅索引概览。
准备工作
请确保您分配有以下任一角色,然后才能在与 MongoDB 兼容的 Firestore 中创建索引:
roles/datastore.ownerroles/datastore.indexAdminroles/editorroles/owner
如需授予角色,请参阅授予单个角色。如需详细了解 Firestore 角色及关联权限,请参阅预定义角色。
如果您定义了自定义角色,则必须为其分配以下所有权限才能创建索引:
datastore.indexes.createdatastore.indexes.deletedatastore.indexes.getdatastore.indexes.listdatastore.indexes.update
创建索引
如需创建索引,请完成以下步骤:
MongoDB API
使用 createIndex() 方法创建索引。例如:
-
db.restaurants.createIndex({"cuisine" : 1})
-
db.restaurants.createIndex({"cuisine" : 1}, {sparse: true})
-
还支持使用
db.runCommand()创建索引,但最多只能创建一个索引。db.runCommand({"createIndexes":"restaurant", "indexes": [{"key": {"cuisine":1}, "name": "cuisine_index"}]})
注意以下限制:
Google Cloud 控制台
gcloud CLI
如需创建索引,请使用 gcloud firestore indexes composite create 命令。将 api-scope 设置为 mongodb-compatible-api。
gcloud firestore indexes composite create \ --database='DATABASE_ID' \ --collection-group=COLLECTION \ --field-config=FIELD_CONFIGURATION \ --query-scope=collection-group \ --density=dense \ --api-scope=mongodb-compatible-api
替换以下内容:
- DATABASE_ID:数据库 ID。
- COLLECTION:集合名称。
- FIELD_CONFIGURATION:字段配置。为每个字段添加
--field-config=field-path=。例如:--field-config=field-path=user-id,order=descending \ --field-config=field-path=score,order=descending如需详细了解如何配置这些字段,请参阅
--field-config。
如需创建稀疏索引,请设置 --density=sparse-any。
如需创建多键索引,请添加 --multikey 标志。
如需创建唯一索引,请添加 --unique 标志。
Terraform
使用 google_firestore_index 资源,并将 api_scope 设置为 MONGODB_COMPATIBLE_API,将 query_scope 设置为 COLLECTION_GROUP。
resource "google_firestore_index" "index" { database = "DATABASE_ID" collection = "COLLECTION" api_scope = "MONGODB_COMPATIBLE_API" query_scope = "COLLECTION_GROUP" // You can include multiple field blocks fields { field_path = "FIELD_PATH" order = "ORDER" } // Optional multikey = true density = "DENSITY" }
替换以下内容:
- DATABASE_ID:所选数据库的数据库 ID
- COLLECTION:要编入索引的集合的名称
- FIELD_PATH:要编入索引的字段的名称
- ORDER:
ASCENDING或DESCENDING之一。 - DENSITY:
SPARSE_ANY或DENSE之一。
创建文本索引
如果您想在集合中搜索特定字符串,请创建文本索引。
如需为集合创建文本索引,请完成以下步骤:
MongoDB API
使用 createIndex() 方法创建文本索引。在以下示例中,当文档写入 cities 集合并填充 country 或 food 字段时,这些字段会被编入索引以供搜索。
db.cities.createIndex({"country": "text", "food": "text"})
字段必须是字符串或字符串数组,才能编入索引。
数组索引不会编入搜索索引。因此,对 a.1.b 进行索引编制时,系统会在 {a: {1: {b: something}}} 中对 something 进行索引编制,但不会在 {a: [one, {b: something}]} 中进行索引编制。
您还可以使用 db.runCommand() 创建索引。每个集合只能有一个文本索引,但您可以在一个 db.runCommand() 中创建多个不同类型的索引。以下示例使用 db.runCommand() 创建文本索引:
db.runCommand({
createIndexes: "cities",
indexes: [
{
key: { "country": "text", "food": "text" },
name: "country_text_food_text"
}
]
})
指定默认语言
您还可以选择指定默认语言,或指定文档中将包含默认语言的字段路径。
在以下示例中,myLanguageField 被指定为 language_override。如果 cities 集合中的某个文档包含名为 myLanguageField 的字段,则该字段的值用于确定为该特定文档的 country 字段编制索引时所用的语言。该值会替换 french 的默认语言。
db.cities.createIndex({"country": "text"}, {"default_language": "french", "language_override": "myLanguageField"})
- 您可以输入语言的完整名称 (
english),也可以输入其双字母 ISO 语言代码 (en)。 - 如果未设置默认语言,则 Firestore 默认为英语。
- 语言替换字段必须是顶级字段。如果未设置,则语言替换字段默认为
language。 - 如果您将默认语言设置为
null字符,则与 MongoDB 兼容的 Firestore 不会将任何字段用作语言替换项。
展开可查看支持的语言列表
| 语言代码 | 语言名称 |
|---|---|
| "und" | 自动检测 |
| "af" | 南非荷兰语 |
| "ak" | Akan |
| “sq” | 阿尔巴尼亚语 |
| "am" | 阿姆哈拉语 |
| “ar” | 阿拉伯语 |
| “hy” | 亚美尼亚语 |
| "az" | 阿塞拜疆语 |
| “eu” | 巴斯克语 |
| “是” | 白俄罗斯语 |
| "bn" | 孟加拉语 |
| "bs" | 波斯尼亚语 |
| "bg" | 保加利亚语 |
| “我的” | 缅甸语 |
| "ca" | 加泰罗尼亚语 |
| "ceb" | 宿务语 |
| "chr" | 切罗基文 |
| "zh" | 中文 |
| “zh-Hant” | 中文_繁体 |
| "hr" | 克罗地亚语 |
| “cs” | 捷克语 |
| "da" | 丹麦语 |
| "nl" | 荷兰语 |
| "en" | 英语 |
| "eo" | 世界语 |
| "et" | 爱沙尼亚语 |
| “fil” | 菲律宾语 |
| "fi" | 芬兰语 |
| "fr" | 法语 |
| "gl" | 加利西亚语 |
| "ka" | 格鲁吉亚语 |
| “de” | 德语 |
| "el" | 希腊语 |
| “gu” | 古吉拉特文 |
| “ht” | 海地克里奥尔语 |
| "ha" | 豪萨语 |
| “haw” | 夏威夷语 |
| "iw" | 希伯来语 |
| “嗨” | 印地语 |
| "hmn" | 苗语 |
| “hu” | 匈牙利语 |
| “是” | 冰岛语 |
| "ig" | 伊博语 |
| “id” | 印度尼西亚语 |
| "ga" | 爱尔兰语 |
| "it" | 意大利语 |
| "ja" | 日语 |
| "jv" | 爪哇语 |
| “kn” | 卡纳达语 |
| "kk" | 哈萨克语 |
| “km” | 高棉语 |
| "ko" | 韩语 |
| "lo" | 老挝语 |
| "la" | 拉丁语 |
| "lv" | 拉脱维亚语 |
| “lt” | 立陶宛语 |
| "lb" | 卢森堡语 |
| "mk" | 马其顿语 |
| "mg" | 马尔加什语 |
| "ms" | 马来语 |
| "ml" | 马拉雅拉姆语 |
| "mt" | 马耳他语 |
| “mi” | 毛利语 |
| "mr" | 马拉地语 |
| "mfe" | 莫里森语 |
| "mn" | 蒙古语 |
| “sr-ME” | 塞尔维亚语_黑山 |
| "ne" | 尼泊尔语 |
| “否” | 挪威语 |
| "ny" | 尼昂加语 |
| “或” | 奥里亚语 |
| “fa” | 波斯语 |
| “pl” | 波兰语 |
| “pt-BR” | 葡萄牙语_巴西 |
| “pt-PT” | 葡萄牙语_葡萄牙 |
| “pa” | 旁遮普语 |
| “ro” | 罗马尼亚语 |
| “ru” | 俄语 |
| "gd" | 苏格兰盖尔语 |
| "sr" | 塞尔维亚语 |
| “st” | 南索托语 |
| "si" | 僧伽罗文 |
| “sk” | 斯洛伐克语 |
| “sl” | 斯洛维尼亚语 |
| “所以” | 索马里语 |
| "es" | 西班牙语 |
| "su" | 巽他语 |
| "sw" | 斯瓦希里语 |
| "sv" | 瑞典语 |
| “tg” | 塔吉克语 |
| "ta" | 泰米尔语 |
| "te" | 泰卢固语 |
| “th” | 泰语 |
| "tr" | 土耳其语 |
| “uk” | 乌克兰语 |
| “ur” | 乌尔都语 |
| "uz" | 乌兹别克语 |
| "vi" | 越南语 |
| "cy" | 威尔士语 |
| "yi" | 意第绪语 |
| "yo" | 约鲁巴语 |
| "zu" | 祖鲁语 |
对文本索引进行分区
您还可以使用某个字段对索引进行分区,以便按特定字段值过滤查询。如果您始终需要在查询的索引中过滤特定字段,则此配置可让您运行性能更高的查询。
如需创建带有分区的索引,请按如下所示配置 firestoreOptions 字段:
db.runCommand({
createIndexes: "cities",
indexes: [
{
key: { "country": "text", "food": "text"},
name: "country_text_food_text"
firestoreOptions: {"customPartitionFields": ["PARTITIONED_FIELD"]
}
]
})
其中:
PARTITIONED_FIELD是用于分区的字段的名称。此值必须是字符串,并且必须引用顶级字段。针对分区索引运行查询时,您可以根据此字段的值过滤结果。例如,您可以使用city对索引进行分区。如果文本索引中定义了city字段,用户就可以针对特定城市进行查询。分区必须仅包含一个字段。如果您对索引进行分区,则只能运行指定了分区字段的查询。
局限性
Google Cloud 控制台
在 Google Cloud 控制台中,前往数据库页面。
从数据库列表中选择一个数据库。
在导航菜单中,点击索引。
点击创建索引,然后点击创建搜索索引。
(可选)输入索引的名称。
前往搜索类型,然后选择文本。
输入集合 ID。
输入至少一个字段路径。
可选:指定默认语言。
例如,您将语言覆盖路径设置为
myLanguageField。如果集合中的文档包含名为myLanguageField的字段,则该字段的值用于确定为索引中定义的字段编制索引时所用的语言。该值会替换索引的默认语言。点击创建。
新索引会显示在索引列表中,且与 MongoDB 兼容的操作会开始创建索引。创建索引后,您会在索引旁边看到一个绿色对勾标记。如果未创建索引,请参阅索引构建错误以了解可能的原因。
创建 2dsphere 索引
创建 2dsphere 索引以执行地理空间查询,并搜索位于特定经纬度一定范围内的文档。
如需为集合创建 2dsphere 索引,请完成以下步骤:
MongoDB API
使用 createIndex() 方法创建索引。例如:
db.restaurants.createIndex({"location" : "2dsphere", "region": "2dsphere"})
还支持使用 db.runCommand() 创建索引,但最多只能创建一个索引:
db.runCommand({
createIndexes: "restaurants",
indexes: [
{
key: { "location": "2dsphere", "region": "2dsphere" },
name: "location_2dsphere_region_2dsphere"
}
]
})
对 2dsphere 索引进行分区
您还可以使用某个字段对索引进行分区,以便按特定字段值过滤查询。如果您始终需要在查询的索引中过滤特定字段,则此配置可让您运行性能更高的查询。
如需创建带有分区的索引,请按如下所示配置 firestoreOptions 字段:
db.runCommand({
createIndexes: "restaurants",
indexes: [
{
key: { "location": "2dsphere", "region": "2dsphere" },
name: "location_2dsphere_region_2dsphere"
firestoreOptions: {"customPartitionFields": ["PARTITIONED_FIELD"]
}
]
})
其中:
PARTITIONED_FIELD是用于分区的字段的名称。针对分区索引运行查询时,您可以根据此字段的值过滤结果。例如,如果您的索引包含用于表示地区位置的region字段,您可以使用region对索引进行分区,以便用户可以查询其所在地区的餐厅。如果您对索引进行分区,则只能运行指定了分区字段的查询。
局限性
Google Cloud 控制台
删除索引
如需删除索引,请完成以下步骤:
MongoDB API
使用 dropIndex() 方法删除索引。例如:
使用索引名称删除索引
db.restaurants.dropIndex("cuisine_index")
使用索引定义删除索引
db.restaurants.dropIndex({"cuisine" : 1})
Google Cloud 控制台
-
在 Google Cloud 控制台中,前往数据库页面。
- 从数据库列表中选择一个数据库。
- 在导航菜单中,点击索引。
- 在索引列表中,针对要删除的索引,从更多按钮 中选择删除。
- 点击删除索引。
gcloud CLI
如需查找索引的名称,请使用
gcloud firestore indexes composite list命令。gcloud firestore indexes composite list \ --database='DATABASE_ID'
将 DATABASE_ID 替换为相应的数据库 ID。
-
如需删除索引,请使用
gcloud firestore indexes composite delete命令。gcloud firestore indexes composite delete INDEX_NAME \ --database='DATABASE_ID'
替换以下内容:
- INDEX_NAME:索引的名称
- DATABASE_ID:数据库 ID
索引构建时间
为了构建索引,与 MongoDB 兼容的 Firestore 必须创建索引,然后使用现有数据回填索引条目。创建索引所需的时间取决于以下因素:
索引的最短构建时间为几分钟,即使空数据库也是如此。
回填索引条目所需的时间取决于属于新索引的现有数据的数量。与索引定义匹配的字段值越多,回填索引条目所需的时间就越长。
管理长时间运行的操作
索引构建是长时间运行的操作。以下部分介绍了如何处理索引的长时间运行的操作。
在您开始创建索引后,与 MongoDB 兼容的 Firestore 会为该操作分配一个唯一名称。操作名称的前缀为 projects/PROJECT_ID/databases/DATABASE_ID/operations/,例如:
projects/PROJECT_ID/databases/DATABASE_ID/operations/ASA1MTAwNDQxNAgadGx1YWZlZAcSeWx0aGdpbi1zYm9qLW5pbWRhEgopEg
在为 describe 命令指定操作名称时,您可以省略前缀。
列出所有长时间运行的操作
如需列出长时间运行的操作,请使用 gcloud firestore operations list 命令。此命令会列出正在进行和最近完成的操作。最近几天内完成的操作都会列出:
gcloud firestore operations list
查看操作状态
您可以列出单个长时间运行的操作的详细信息,而不是列出所有长时间运行的操作:
gcloud firestore operations describe operation-name
估计完成时间
操作运行时,查看 state 字段的值可了解操作的总体状态。
用于获取长时间运行的操作的状态的请求也会返回指标 workEstimated 和 workCompleted。workEstimated 表示操作将处理的预估文档总数。workCompleted 表示目前已处理的文档数。操作完成后,workCompleted 会反映实际处理的文档总数,可能与 workEstimated 的值不同。
如需预估操作的进度,请将 workCompleted 除以 workEstimated。
以下是创建索引的进度示例:
{
"operations": [
{
"name": "projects/project-id/operations/AyAyMDBiM2U5NTgwZDAtZGIyYi0zYjc0LTIzYWEtZjg1ZGdWFmZWQHEjF0c2Flc3UtcmV4ZWRuaS1uaW1kYRUKSBI",
"metadata": {
"@type": "type.googleapis.com/google.firestore.admin.v1.IndexOperationMetadata",
"common": {
"operationType": "CREATE_INDEX",
"startTime": "2020-06-23T16:52:25.697539Z",
"state": "PROCESSING"
},
"progressDocuments": {
"workCompleted": "219327",
"workEstimated": "2198182"
}
},
},
...
操作完成后,操作说明将包含 "done": true。查看 state 字段的值,了解操作的结果。如果响应中未设置 done 字段,则表示操作尚未完成。