2017-10-18 133 views
4

假设我有一个包含一些可选属性的数据模型。这可以是例如具有“名字”,“姓氏”和可选的“网站”属性的用户对象。如何查询云存储Firestore中不存在的文档密钥

在Cloud Firestore中,只有具有已知网站的用户文档才会设置“网站”属性,对于该属性不存在的所有其他用户文档。

我的问题是现在如何查询所有用户文件没有一个“网站”属性。

谢谢。

回答

7

文档可以包含null值数据类型的属性(请参阅data types documentation)。这将允许您构建查询以限制website属性为null的结果。

这与缺少的属性并不完全相同,但如果使用custom objects将数据写入Firestore,则空属性将自动保存为null而非根本不存在。您也可以手动/以编程方式将null值写入数据库。

在Android中,我测试了使用下列内容:

FirebaseFirestore.getInstance().collection("test").whereEqualTo("website", null).get(); 

在哪里我的数据库结构看上去像:

example firestore structure

这仅返回文档inuwlZOvZNTHuBakS6GV,因为文件9Hf7uwORiiToOKz6zcsX包含字符串值在website属性中。

我相信你通常在Swift中开发,不幸的是自定义对象不被支持,但是你可以使用NSNull()来给Firestore写一个null值。例如(我不是斯威夫特精通,所以随时纠正任何问题):

// Writing data 
let docData: [String: Any] = [ 
    "firstname": "Example", 
    "lastname": "User", 
    "website": NSNull() 
] 
db.collection("data").document("one").setData(docData) { err in 
    if let err = err { 
     print("Error writing document: \(err)") 
    } else { 
     print("Document successfully written!") 
    } 
} 

// Querying for null values 
let query = db.collection("test").whereField("website", isEqualTo: NSNull()) 

的文档没有提到的方法来查询不存在的值,因此这似乎是次佳方法。如果任何人都可以改进或建议替代品,请做。

+1

非常感谢你这个精心设计的答案。 – Georg

+0

很高兴,特别是因为这是我第一次接触Swift,所以我也学到了一些东西!感谢接受。 – Grimthorr

+2

考虑到这一点之后,可能需要这种方法才能使索引工作。如果一个属性没有设置,它可能没有被索引,因此不能被查询。将该属性设置为null会将文档添加到属性的相应索引。 对你的代码的一条评论:我稍后会自己尝试,但理论上你的例子还应该使用Swift“nil”而不是NSNull()。 再次感谢。 – Georg