我有一个充满用户的基于文档的数据结构。有关用户的信息将包括每周议程(一周内进行的活动,例如:星期一运行10分钟,星期二购物),以及其他基本信息,例如名字,性别,年龄等。用户可以每周有多个议程(例如,本周一个,下周另一个,等等。)
但是我不知道如何构造这些数据。
用户目录中应该有两个子目录,一个子目录名为“ weekly_agendas”(包含所有用户每周议程的文档),另一个子目录名为“ user_data”,其中包含个人信息,例如姓名,性别,年龄等。本质上,正在创建嵌套数据。
OR:
是否应将“ weekly_agendas”目录移到用户目录之外?
我到处都有Google搜索,所有文档通常都建议防止嵌套数据结构,但是这种嵌套数据结构怎么可能不好呢?
这可以帮助说明我要达到的目标:
Structure #1
users
|
+--user_id
|
+--user_data
|
+--username
+--age
+--gender
+--weekly_agenda
|
+--weekly_agenda_number
|
+--1: walk the dog on Monday
+--2: Go shopping on Tuesday
Structure #2:
users
|
+--user_id
|
+--username
+--age
+--gender
+--weekly_agenda
|
+--user_id
|
+--weekly_agenda_number
|
+--1: walk the dog on Monday
+--2: Go shopping on Tuesday
答案 0 :(得分:0)
(供以后参考,这种“最佳实践”问题比堆栈溢出更适合Firebase Google Group)
首先,我不确定这是故意的还是您的图中的错误,但我只想指出,在结构1中,您应该有username
,age
和gender
作为用户文档中的字段,而不是如图所示的子集合。 (根据您的描述,我想这就是您的意思,但是请确定,因为用户数据对子集合的使用不佳。)
现在是您的主要问题:
当在 flat 数据结构上运行时,Firestore会大大受益,即,该结构具有大量的小文档,而不是少量的大文档。这是人们在谈论反嵌套做法时所指的要点之一。
数据的结构方式完全取决于计划与之交互的方式,而不仅取决于如何看待。
如果您计划用户能够看到其他用户的议程,那么 Structure #1
的效果将不如Structure #2
。仍然可以,但是查询会更麻烦。
话虽如此,如果议程仅对其所有者可见,则考虑到组织对于该目标更为直观的事实,Structure #1
可能更有意义。使用Structure #1
也可能会稍微加快查询响应速度。
Structure #2
没有任何问题。如果现在或将来用户都可以查看其他用户的议程,那么Structure #2
是您最好的选择。如果您计划根据多个用户之一搜索议程,那么Structure #2
也会更好。例如,如果您想通过其timestamp
字段查找最近的20个应用程序范围的议程文件。
我的项目有非常相似的情况,但上下文不同。我们的应用程序包含Posts
和Content
。每个Post
包含一个或多个Content
。我们可以将Content
设为每个Post
的子集合(例如您的Structure #1
),但是我们改为使Content
成为根级别的集合(例如您的Structure #2
),因为我们需要根据用户的其中一个字段来查询Content
个文档。
最后,Structure #2
更加灵活,但是如果您确定不想在多个用户之间查询议程(collection group query),那么Structure #1
可能更有利
我通常默认使用Structure #2
,除非那些罕见但合法的情况下,将数据隔离到特定文档确实更有意义。
答案 1 :(得分:0)
没有用于构建Cloud Firestore数据库的“完美”,“最佳”或"the correct"解决方案。
我到处都有Google搜索,所有文档通常都建议防止嵌套数据结构,但是这种嵌套数据结构怎么可能不好呢?
与在Firebase实时数据库中显示每周议程的列表不同,您将已经下载了整个用户对象,在Cloud Firestore中,这不再是问题。因此,在每个用户文档下嵌套名为weekly_agenda
的子集合不会有问题。第一种方法的缺点是您无法查询数据库以显示所有用户的所有议程。因此,可能是您的解决方案混合在一起的模式可能是:
Firestore-root
|
--- users (collection)
| |
| --- uid (document)
| |
| --- username: "John"
| |
| --- age: 22
| |
| --- gender: "male"
|
--- weeklyAgenda (collection)
|
--- weeklyAgendaId (document)
|
--- uid: "UidOfTheUser"
|
--- //Weekly Agenda Properties
使用此架构,您可以简单地:
users
集合上附加侦听器,从整个数据库中查询所有用户。weeklyAgenda
集合上附加侦听器来查询所有用户的议程。使用Android中的查询来查询属于单个用户的所有议程,
FirebaseFirestore rootRef = FirebaseFirestore.getInstance();
Query query = productsRef.whereEqualTo("uid", uid);
此查询也可以用其他编程语言编写。