索引类型(续11)
索引条目
此索引配置会生成文档的以下索引条目:
| 索引 | 编入索引的数据 |
|---|---|
| 自动索引条目 | |
| city_name ASC | city_name: “San Francisco” |
| city_name DESC | city_name: “San Francisco” |
| neighborhoods ASC | neighborhoods: [“Mission”, “Downtown”, “Marina”] |
| neighborhoods DESC | neighborhoods: [“Mission”, “Downtown”, “Marina”] |
| temperatures ASC | temperatures: {summer: 67, winter: 55} |
| temperatures DESC | temperatures: {summer: 67, winter: 55} |
| temperatures.summer ASC | temperatures.summer: 67 |
| temperatures.summer DESC | temperatures.summer: 67 |
| temperatures.winter ASC | temperatures.winter: 55 |
| temperatures.winter DESC | temperatures.winter: 55 |
| neighborhoods 数组包含 | neighborhoods: “Mission” |
| neighborhoods 数组包含 | neighborhoods: “Downtown” |
| neighborhoods 数组包含 | neighborhoods: “Marina” |
| 手动索引条目 | |
| city_name ASC, neighborhoods ARRAY | city_name: “San Francisco”, neighborhoods: “Mission” |
| city_name ASC, neighborhoods ARRAY | city_name: “San Francisco”, neighborhoods: “Downtown” |
| city_name ASC, neighborhoods ARRAY | city_name: “San Francisco”, neighborhoods: “Marina” |
| city_name DESC, neighborhoods ARRAY | city_name: “San Francisco”, neighborhoods: “Mission” |
| city_name DESC, neighborhoods ARRAY | city_name: “San Francisco”, neighborhoods: “Downtown” |
| city_name DESC, neighborhoods ARRAY | city_name: “San Francisco”, neighborhoods: “Marina” |
索引和价格
使用索引时,您的应用会产生存储费用。 如需详细了解如何计算索引的存储空间大小,请参阅索引条目大小。
使用索引合并
虽然 Cloud Firestore 会为每个查询使用索引,但实际上没有必要为每个查询都创建一个索引。如果查询使用多个等式 (==) 子句和非必需的 orderBy 子句,Cloud Firestore 可以重复利用现有的索引。Cloud Firestore 可以将针对简单等式过滤条件创建的索引合并起来,构建运行更大的等式查询所需的索引。
通过找出可使用索引合并的情况,您可以降低索引产生的费用。例如,一个餐厅评分应用有一个 restaurants 集合:
-
restaurants
-
burgerthyme
name : "Burger Thyme"category : "burgers"city : "San Francisco"editors_pick : truestar_rating : 4
此应用使用如下所示的查询。此应用使用的是 category、city 和 editors_pick 等式子句的组合,并始终按 star_rating 进行升序排序:
Web
db.collection("restaurants").where("category", "==", "burgers")
.orderBy("star_rating")
db.collection("restaurants").where("city", "==", "San Francisco")
.orderBy("star_rating")
db.collection("restaurants").where("category", "==", "burgers")
.where("city", "==", "San Francisco")
.orderBy("star_rating")
db.collection("restaurants").where("category", "==", "burgers")
.where("city", "==" "San Francisco")
.where("editors_pick", "==", true )
.orderBy("star_rating")
您可以为每个查询创建一个索引:
| 集合 | 编入索引的字段 | 查询范围 |
|---|---|---|
| 餐馆 | category、 star_rating | 集合 |
| 餐馆 | city、 star_rating | 集合 |
| 餐馆 | category、 city、 star_rating | 集合 |
| 餐馆 | category、 city、 editors_pick、 star_rating | 集合 |
但更好的方式是,充分利用 Cloud Firestore 合并等式子句索引的功能,来减少索引的数量:
| 集合 | 编入索引的字段 | 查询范围 |
|---|---|---|
| 餐馆 | category、 star_rating | 集合 |
| 餐馆 | city、 star_rating | 集合 |
| 餐馆 | editors_pick、 star_rating | 集合 |
此索引集不仅更小,还可支持其他查询:
Web
db.collection("restaurants").where("editors_pick", "==", true)
.orderBy("star_rating")
索引限制
索引存在以下限制。如需详细了解配额和限制,请参阅配额和限制。
| 限制 | 详细信息 |
|---|---|
| 一个数据库的复合索引数量上限 | - 200(如果尚未为 Google Cloud 项目启用结算功能)。 如果您需要更多配额,则必须为 Google Cloud 项目启用结算功能。 - 1000(如果您为 Google Cloud 项目启用了结算功能)。 您可以与支持团队联系,申请提高此限制。 |
| 数据库单字段配置的数量上限 | - 200(如果尚未为 Google Cloud 项目启用结算功能)。 如果您需要更多配额,则必须为 Google Cloud 项目启用结算功能。 - 1000(如果您为 Google Cloud 项目启用了结算功能)。 一个字段级配置可以包含同一字段的多个配置。例如,单字段索引例外项和针对同一字段的 TTL 政策将被视为一个字段配置计入限额。 |
| 每个文档的索引条目数量上限 | 40000 索引条目的数量是文档的以下各项数量的总和: - 单字段索引条目的数量 - 复合索引条目的数量 如需了解 Cloud Firestore 如何将一个文档和一组索引转变为索引条目,请参阅此索引条目数示例。 |
| 复合索引中的字段数上限 | 100 |
| 索引条目的大小上限 | 7.5 KiB 如需了解 Cloud Firestore 如何计算索引条目大小,请参阅索引条目大小。 |
| 一个文档的索引条目的大小总和上限 | 8 MiB 总大小是文档的以下各项的大小总和: - 文档的单字段索引条目的大小总和 - 文档的复合索引条目的大小总和 |
| 编入索引的字段值的大小上限 | 1500 字节 超出 1500 字节的字段值会被截断。包含被截断的字段值的查询可能会返回不一致的结果。 |
索引最佳实践
对于大多数应用,您可以依靠自动索引和错误消息链接来管理索引。不过,在以下情况下,您可能需要添加自动索引例外项:
| 场景 | 说明 |
|---|---|
| 大型字符串字段 | 如果您的字符串字段通常包含不用于查询的长字符串值,您可以选择不将该字段编入索引来降低存储费用。 |
| 向所含文档具有依序值的集合进行高速率写入 | 如果您将在某个集合中的各文档之间依序递增或递减的字段(如时间戳)编入索引,则向该集合写入数据的最大速率为每秒 500 次写入。如果您不根据具有序列值的字段进行查询,可以选择不将该字段编入索引来绕过此限制。 例如,在具有高写入速率的 IoT 使用场景中,一个所含文档具有时间戳字段的集合可能会达到每秒 500 次的写入限制。 |
| TTL 字段 | 请注意,如果您使用 TTL(存留时间)政策,则 TTL 字段必须是一个时间戳。默认情况下,系统会将 TTL 字段编入索引,这可能会在流量传输速率较高时影响性能。最佳实践是为 TTL 字段添加自动索引例外项。 |
| 大型数组或映射字段 | 大型数组或映射字段可能会达到每个文档 40,000 个索引条目的限制。如果您的查询不是基于大型数组或映射字段,建议您不要将该数组或字段编入索引。 |
如果您使用对多个字段使用范围和不等式运算符的查询,请参阅索引编制注意事项,以便优化 Cloud Firestore 查询的性能和费用
如需详细了解如何解决索引编制问题(索引扇出、INVALID_ARGUMENT 错误),请参阅问题排查页面。
