Firestore作为 Firebase 生态中的文档型数据库,默认允许任意结构的文档写入,这在面对动态字段结构需求时既灵活也存在数据安全隐患。通过安全规则配置动态字段结构验证,可以在数据写入前校验字段类型、必填项、取值范围等,避免无效或恶意数据进入数据库。
动态字段验证的核心需求场景
实际开发中动态字段结构的需求通常分为两类,对应的验证策略也有区别:
- 已知字段集合的动态可选:字段池固定,不同文档可选择不同的字段组合,比如商品信息中,不同类目的商品有不同的可选属性字段。
- 完全动态字段结构:字段名和数量都不固定,比如用户提交的自定义问卷结果,字段名由用户自定义。
基础验证规则语法铺垫
Firestore安全规则中常用的验证方法包括:
request.resource.data:获取本次请求写入的文档数据resource.data:获取数据库中已存在的文档数据(仅更新、删除场景可用)is关键字:判断值的类型,比如val is stringhasAll:判断对象是否包含指定的所有键keys():获取对象的所有键集合
已知字段集合的动态可选验证实践
假设我们有一个商品集合 products,所有商品都包含基础字段 name(字符串)、price(数字),不同类目的商品可额外携带可选字段:电子类商品可选 battery_life(数字),服装类商品可选 size(字符串)、color(字符串)。
对应的安全规则配置如下:
service cloud.firestore {
match /databases/{database}/documents {
// 匹配products集合下的所有文档
match /products/{productId} {
// 允许创建和更新操作,先校验基础规则
allow create, update: if request.resource.data.keys().hasAll(['name', 'price'])
&& request.resource.data.name is string
&& request.resource.data.price is number
&& request.resource.data.price > 0
// 获取除基础字段外的额外字段
&& let extraKeys = request.resource.data.keys().difference(['name', 'price'])
// 额外字段只能是预定义的可选字段
&& extraKeys.hasOnly(['battery_life', 'size', 'color'])
// 校验可选字段的类型
&& (!extraKeys.has('battery_life') || request.resource.data.battery_life is number)
&& (!extraKeys.has('size') || request.resource.data.size is string)
&& (!extraKeys.has('color') || request.resource.data.color is string);
}
}
}
完全动态字段结构的验证实践
如果是用户自定义表单场景,字段名完全由用户定义,我们可以限制字段值的类型范围,同时限制字段数量,避免恶意写入大量数据。
假设表单提交集合 form_submissions,要求所有字段值只能是字符串、数字、布尔值三种类型,且单个文档字段数不超过20个:
service cloud.firestore {
match /databases/{database}/documents {
match /form_submissions/{submissionId} {
allow create: if request.resource.data.keys().size() <= 20
// 遍历所有字段值,校验类型
&& request.resource.data.values().all((val) => {
return val is string || val is number || val is bool;
});
}
}
}
验证策略的注意事项
- 规则中不要做过于复杂的遍历逻辑,Firestore安全规则有执行时间限制,复杂逻辑可能导致规则执行超时。
- 如果动态字段需要关联其他集合的元数据校验,比如可选字段列表存在另一个集合
field_config中,需要使用get()方法获取配置数据,注意get()调用也会消耗规则执行资源。 - 更新场景下如果需要保留原有字段,需要使用
request.resource.data.keys().hasAll(resource.data.keys())确保原有字段没有被删除,或者针对不需要保留的字段单独做兼容处理。
规则调试方法
配置完规则后,可以在 Firebase 控制台的 Firestore 规则页面使用模拟器测试,输入对应的请求数据,查看规则是否按预期通过或拒绝。如果规则报错,可以逐步拆分条件,定位具体不符合的校验项。
安全规则是 Firestore 数据安全的第一道防线,动态字段验证需要根据实际业务场景平衡灵活性和安全性,避免过度限制影响业务迭代,也不要放宽限制导致数据风险。