我正在通过DynamoDB设计一个新表。我已经阅读了一些文档,但无法弄清楚应该遵循哪种设计方案,以免将来出现问题。
当前方法
表格-事件
- eventId (HashKey)
- userId
- createdAt
- some other attributes...
表格-用户
- userId (HashKey)
- name
- birth
- address
事件表将具有大量条目,例如数百万。目前,用户数量约为20。
我将需要执行以下查询:
- GET paginated events from specific userId ordered by createdAt
- GET paginated events from specific userId between some range of dates and ordered by createdAt
- GET specific event entry by eventId
所以我想使用以下设置在事件表上创建一个GSI(全局二级索引):
- userId (HashKey)
- createdAt (RangeKey)
但是我的问题是: 我的初始设计有意义吗?我以某种方式可以使用以下设置来设计事件表:
- userId (HashKey)
- eventId (SortKey)
但是我认为按照这种方法,我会遇到热分区陷阱。
我们将不胜感激。
谢谢。
答案 0 :(得分:0)
您的方法对我来说似乎很好。牢记最佳实践https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/bp-partition-key-design.html,尤其是
通常来说,您应该设计应用程序以使其在表及其辅助索引中的所有逻辑分区键上具有统一的活动。您可以确定应用程序所需的访问模式,并估算每个表和二级索引所需的RCU和WCU总数。
意思是,数据突变必须在所有分区中尽可能均匀地分布。在您的情况下,将会有很多事件,并且用户数量有限,这表明每个用户必须拥有大量事件。
如果选择基于eventid
对表进行分区,最终将有数百万个分区,每个分区都有相同的用户ID。假设您需要按用户查询事件,则读取最终将在所有分区之间平均分配。每个事件的写入次数也将平均分配。
但是,如果您选择userid
作为分区键,则与其他情况相比,更多请求将最终位于同一分区。因此,我建议使用前者(eventid
是分区键)。
那是我的2美分。