我的Firestore中有几个文档,并且每个文件中都有一个文件名'date',它是字符串,并且在每个文件中。
这是具有值的三个文档的字段的结构。
date:"2020.01.18" (document 1)
date: "2020.01.19" (document 2)
date: "2020.02.17" (document 3)
我要查询所有日期为“ 2020.01” /“ 2020.02”的文档(忽略日期。仅从年份和月份中选择数据)
这就是我想要做的
this.afs
.collection("orders", ref => ref.where("date", '==', date)) //How should I change the condition ('==') in here to overcome with this problem.
.valueChanges();
}
答案 0 :(得分:2)
由于您的日期采用的是字典顺序与时间顺序相同的格式,因此您可以使用Firestore的范围过滤器查询日期范围。
如果您要在2020年1月或2月查找文档,则为:
ref.where('date', '>=', '2020.01.01').where('date', '<', '2020.03.01')
您甚至可以舍弃值的一天部分,并获得相同的结果:
ref.where('date', '>=', '2020.01.').where('date', '<', '2020.03.')
这是因为Firestore查询对字符串的范围操作进行了前缀匹配。
另一个例子:获取2020年的所有文件:
ref.where('date', '>=', '2020').where('date', '<', '2021')
答案 1 :(得分:1)
一种可能的解决方案是在文档中添加一个仅包含年份和月份的额外字段,如下所示:
date:"2020.01.18" (document 1)
searchDate:"2020.01" (document 1)
date: "2020.01.19" (document 2)
searchDate:"2020.01" (document 2)
date: "2020.02.17" (document 3)
searchDate:"2020.02" (document 3)
然后,您可以轻松地在此字段上查询:
this.afs
.collection("orders", ref => ref.where("searchDate", '==', "2020.02"))
.valueChanges();
}
以这种方式复制数据在NoSQL World中非常经典,以简化/优化查询处理。它遵循与 Denormalization 类似的“哲学”,这也是一种经典方法,如本article中有关NoSQL数据库的“数据建模技术”的解释
另一种解决方法是结合使用orderBy()
,startAt()
和endAt()
(请参见文档here)和字符\uf8ff
,如下所示
var searchString = '2020.02.'
this.afs
.collection("orders", ref => ref.orderBy('searchDate')
.startAt(searchString)
.endAt(searchString + '\uf8ff'))
.valueChanges();
}
事实上,字符\uf8ff
在Unicode中大多数常规字符之后,因此查询匹配所有以searchString
开头的值。
请注意,如果您要构建OR查询(例如,日期为“ 2020.01” OR 为“ 2020.02”的所有文档),则无法在Firestore中使用,如doc。您应该“为每个OR条件创建一个单独的查询,并将查询结果合并到您的应用中”。
答案 2 :(得分:0)
这些查询的工作方式是通过firestore保留的索引来实现的,我认为这是不可能的,但是另一种解决方案是将值存储在本地存储中并将其提供给客户端
在下面查看此炫酷服务:
https://codereview.stackexchange.com/questions/235822/angular-fire-firestore-cached-service