database - 如何在 Firestore 中构造彩票开奖应用程序的数据?
问题描述
我正在 react-native + Cloud Firestore 中开发一个应用程序,旨在为每个填写表格的用户生成随机数/票证。这些号码将允许用户参与电子彩票并竞争促销奖品。
这些数字应按系列分隔,例如:
Series 1 - numbers can range from 0 to 99,999 thousand.
Series 2 - numbers can range from 0 to 99,999 thousand.
Series N - numbers can range from 0 to 99,999 thousand.
系统要求是:
- 必须维护为每个用户生成的系列和号码(为客户保存的号码);
- 每个促销还必须包含生成的数字和系列(促销中生成的数字,总计);
在 Cloud Firestore 的第一个结构中,我们创建了如下结构:
Promotion - Series - Number
(random doc) - 01 - 00131 ...
(random doc) - 01 - 97879 ...
(random doc) - 09 - 99999
Promotion 是一个集合,Series 是一个提升子集合,Number 是一个 Series 子集合。
但是,通过这种方式,在firestore API中已经进行了许多查询,例如,获取一个系列中要生成的可用数字,从而可以生成一个新的数字。
我们发现的另一种方法是数字的子集合可以是 Series 集合中的数组。这将减少查询。
100,000 个数字数组会超过最大 1mb 文档大小吗?例如,它可以用于带有 map 的结构,以编写超出数量的其他属性,如下所示:
Promotion - Series - Numbers: Map?
解决方案
“100,000 个数字数组会超过最大 1mb 文档大小吗?”
数组中的每个数字将消耗8 个字节,因此只有数组值约为 800KB,然后文档和字段名称的一些开销仍应低于限制。
但是,您需要确保进入 UI 中的 Single Field Indexes 并为数组字段创建一个例外,因为每个数组值消耗 2 个索引条目(整个数组本身消耗 2 个),因此您肯定会超过 20K每个文档限制的索引条目。注意:这意味着您将无法查询该数组。
“但是,通过这种方式,已经在 firestore API 中进行了许多查询,例如,获取要在系列中生成的可用编号,从而可以生成新编号。”
我猜这两个不成文的假设:
- 同一号码不能提供给多个客户
- 大多数(如果不是所有)系列中的数字将被分配
如果 2 不正确,您可以只生成一个数字,查看它是否存在,如果存在则重新生成并重试。如果将分配大部分或全部号码,这将变得更加昂贵。
另一种方法是做混合方法。
对于 100,000 个数字,创建 1000 个文档,每个文档拥有 100 个数字,并将这 100 个数字存储在一个名为 的数组中ticket_number
:
/promotions/<series number>/numbers/<nnnn>
--> ticket_number: [nnnn01, nnnn02, ..., (nnnn+1)00]
如果该范围内的数字仍然可用,则在每个文档上都有一个名为的布尔字段available
设置为。true
如果不是,请删除该字段或将其设置为false
使用此处概述的方法从这些文档中选择一个随机文档full == true
。从此文档中从数组中选择一个随机票号,将其删除并更新文档。
最终,所有值都将以这种方式选择,而只需要为每张票读取和写入一个文档(以及将选定的编号/系列写入单独的文档)。
写入速率注意事项
请注意,建议每个文档的最大持续速率为每秒 1 次写入。在单文档方法中,这将意味着数字分配缓慢或某些上游批处理机制。
通过使用混合方法,您可以跨更多文档进行分片以提高写入速率。在我上面给出的示例中,每秒写入 1000 次。
推荐阅读
- rpmbuild - 使用 Developer Toolset 7 时,RPM 构建无法定位 libelf.so.dts.1
- spring - 将 Spring MVC 转换为 Spring Boot 应用程序。是否可行且值得?
- php - Laravel Routes not working 404 not found
- c# - 如何修复 SCS0018?
- scala - 将 spark rdd 保存到大查询表中
- python - 如何有效地实施这种差异操作?
- jquery - 如何使用 ajax 和 jQuery 上传多个视频。由于内部服务器错误,无法上传
- oop - virtual 应该是默认的还是 final 是默认的?
- python - 意图调用另一个意图(没有后续意图)
- objective-c - 将 Pod 安装的项目放入 Xcode 的另一个项目中。