FireStore查询单个文档

时间:2018-02-01 23:11:34

标签: javascript angular angularfire2 google-cloud-firestore

背景:我试图从一个集合中检索一个文件而不是它的ID。我基本上是想创建一个登录系统。

我尝试了这个解决方案:Firestore : Retrieve a single document

使用flat-map来限制(1)来做但它似乎没有给出任何东西,这就是我的代码现在的样子:

this.user = this.afs.collection('users/', ref => ref.where('username',
      '==', this.username).limit(1)).valueChanges().flatMap(result => result);
    console.log(this.user.username);

输出是未定义的,但如果我只打印用户,我会得到可观察的

1 个答案:

答案 0 :(得分:1)

您应该将this.user设置为Observable参考,然后按以下方式订阅:

this.user = this.afs.collection('users', (ref) => ref.where('username', '==', this.username).limit(1)).valueChanges();

// I removed the slash after 'users' as it isn't necessary

然后像这样订阅Observable:

this.user.subscribe((user) => { console.log(user); });

哪个应该只给你一个结果。控制台记录Observable不会显示数据,而是记录Observable对象。

请注意,您应该拥有与该用户名相关的userId并提取文档,因为它比获取与字段匹配的集合并将其限制为1更安全,更明确。如果这是认证问题,您应该使用Firebase Auth并使用任何形式的身份验证作为用户名,Firebase Auth将处理没有重复登录。如果需要使用用户名而不是电子邮件,您可以请求,但您的方法应该只返回请求的长度,如下所示:

 this.user = this.afs.collection('users', 
  (ref) => {
    return ref.where('username', '==', this.username).limit(1)
  })
  .snapshotChanges()
  .map((users) => {
    return users.length
  });

这样您就不会在请求中返回hte用户对象,而是返回一个数字,如果它大于零,则用户已经拥有该用户名。

由于您使用的是valueChanges()而不是snapshotChanges(),因此在将数据显示在DOM上之前,您不需要操作数据,因此您无需订阅数据,而是订阅在标记中使用ASYNC管道的Observable。这是我前几天解答的一个问题,它解释了您的问题,并在您的标记中使用了ASYNC管道:Angular Observable Array Object Conversion