首页 文章

使用Angularfire2嵌套Observable(TypeScript)

提问于
浏览
1

我有以下非规范化的Firebase结构:

members
  -memberid1
    -threads
       -threadid1: true,
       -threadid3: true
    -username: "Adam"
    ...

threads
  -threadid1
      -author: memberid3
      -quality: 67
      -participants
         -memberid2: true,
         -memberid3: true
      ...

我在我的组件中列出 quality 排序 threads

featured-threads.component.ts

constructor(af: AngularFire) {
    this.threads = af.database.list('/threads', {
        query: {
            orderByChild: 'quality',
            endAt: 10
    }
});

以下是我的观点摘录:

featured-threads.component.html

<div *ngFor="let thread of threads | async" class="thread-tile">
...
    {{thread.author}} //Renders memberid3
...
</div>

我没有在这里渲染 memberid3 ,而是'd like to get the corresponding member'的用户名属性值 .

解决方案herehere都在构造函数之外获取它们的observable,而不是在Angularfire2 docs中演示的内部 . 他们使用 this.af.database . 当我在构造函数中使用 this 关键字时,TypeScript会警告它不会将 af 识别为组件属性(因为它显然不是) . 我可以通过声明属性 af: Angularfire; 在构造函数之外使用 this ,但后来我得到控制台错误 TypeError: Cannot read property 'database' of undefined ,我认为这与声明属性与注入 AngularFire 服务不同的事实有关 . 我已经尝试过其他一些可能太滑稽而且与这个问题无关的事情 .

我在这里发生了什么 . 这个问题阻止我创建一个方法,我可以简单地从 threads 传递 author 的值作为参数 . 这是因为无法在构造函数中定义方法,并且构造函数 af 之外的方法为null .

我甚至不确定这是否解决了核心问题 . 我希望能够随时加入/嵌套这些可观察对象,而不仅仅是在这个更简单的情况下,当我获得直接路径到 memberid 时 . 关于嵌套可观察量的问题有很多问题,其解决方案无法将它们转换为Angularfire 2解决方案 .

更新

我将组件中的所有逻辑移到了服务上,现在将服务的方法 getFeaturedThreads() 注入到组件中,其中包含以下内容:

ngOnInit() {
    this.threads = this.featuredThreadsService.getFeaturedThreads()
    this.threads.subscribe( 
        allThreads => 
            allThreads.forEach(thisThread => {
                this.featuredThreadsService.getUsername(thisThread.author)
                    .subscribe( 
                        username => console.log(username))
            })
    )
}

getUserName() 看起来像这样:

getUsername(memberKey: string) {
    return this.af.database.object('/members/' + memberKey + '/username')
}

现在,这会将每个 memberusername 属性记录到控制台 . 不幸的是,我只得到钥匙 . 值为空:

enter image description here

...这对我来说很奇怪,因为 getUsername() 成功地将成员id传递到查询路径中 .

enter image description here

这是我的Firebase控制台视图中的抓取,显示路径正确 .

enter image description here

我认识到这是一个使用问题而不是技术问题 .

1 回答

  • 1

    我会像这样实现它,我把它移动到ngOnInit因为你真的不应该在构造函数中这样做 . 只需在构造函数中的af声明之前添加private .

    public ngOnInit() {
        this.threads = this.af.database.list('/threads', {
            query: {
                orderByChild: 'quality',
                endAt: 10
            }
        }).do(threads => {
            threads.forEach(thread => {
                thread.author = this.af.database.getName(thread.author); //actual method to get the username
            });
        });
    }
    

    和你的组件HTML

    <div *ngFor="let thread of threads | async" class="thread-tile">
    ...
        {{thread.author | async}}
    ...
    </div>
    

相关问题