如何根据另一个可观察对象获取检索 firebase 列表
How to get retrieve firebase list based on another observable
我对 observables 还是很困惑。它们非常复杂。
我正在尝试编写一项服务 class,该服务可用于将登录用户的地址作为可观察列表进行监视。问题是我猜列表引用本身会在用户登录或注销时发生变化。
export class AddressService {
user: any;
addresses$: FirebaseListObservable<Address[]>;
constructor(private db: AngularFireDatabase, private authService: AuthService) {
authService.user$.subscribe((user) => {
this.user = user;
if (this.user) {
this.addresses$ = this.db.list(`/users/${this.user.uid}/addresses`);
} else {
this.addresses$ = undefined;
}
});
}
}
当我尝试将订户添加到列表时,我得到的是空值,因为我猜 addresses$
在添加时未定义,因为它取决于登录用户首先解析。
// in a UI component
ngOnInit() {
this.addresses = this.addressService.addresses$;
}
这就像我需要一个新的 observable,它在用户登录时发出一个新的 observable 列表!正在查看 http://reactivex.io/documentation/operators/switch.html - 也许这能以某种方式起作用?
在此处编辑更新
这是我想出的(刚从 class 中提取)
// users can monitor this to get the latest address book.
addresses$: Observable<FirebaseListObservable<any>>;
// keeps a reference to the address subject.
private addressSubject = new BehaviorSubject<any>(Observable.empty());
constructor(private db: AngularFireDatabase, private authService: AuthService) {
this.addresses$ = this.addressSubject.asObservable();
authService.user$.subscribe((user) => {
this.user = user;
if (this.user) {
this.addressSubject.next(this.db.list(`/users/${this.user.uid}/addresses`));
} else {
this.addressSubject.next(Observable.empty());
}
});
}
所以你想要做的,在伪代码中,是这样的:
首先调用 authService
检索用户 ID。
如果用户存在,去数据库中检索地址。
如果没有,就return没什么。
将结果分配给 addresses$
,将其作为可观察对象公开。
如果您像这样分解步骤,那么您将不会Observables
感到困惑。只要您知道执行列出的每个任务的方法,您就很好。
代码如下:
export class AddressService {
user: any;
addresses$: FirebaseListObservable<Address[]>;
constructor(private db: AngularFireDatabase, private authService: AuthService) {
//Step 4: assign the observable back to addresses$
this.addresses$ =
//Step 1: first call the auth service
this.authService.user$.switchMap(user => {
this.user = user;
//Step 2: if user exist, call DB service
if (this.user) {
return this.db.list(`/users/${this.user.uid}/addresses`);
}
//Step 3: else just return nothing
else {
return Obsevable.empty()
}
})
}
}
我在代码中做了一些内联注释,以便您可以与伪代码进行比较。
我对 observables 还是很困惑。它们非常复杂。
我正在尝试编写一项服务 class,该服务可用于将登录用户的地址作为可观察列表进行监视。问题是我猜列表引用本身会在用户登录或注销时发生变化。
export class AddressService {
user: any;
addresses$: FirebaseListObservable<Address[]>;
constructor(private db: AngularFireDatabase, private authService: AuthService) {
authService.user$.subscribe((user) => {
this.user = user;
if (this.user) {
this.addresses$ = this.db.list(`/users/${this.user.uid}/addresses`);
} else {
this.addresses$ = undefined;
}
});
}
}
当我尝试将订户添加到列表时,我得到的是空值,因为我猜 addresses$
在添加时未定义,因为它取决于登录用户首先解析。
// in a UI component
ngOnInit() {
this.addresses = this.addressService.addresses$;
}
这就像我需要一个新的 observable,它在用户登录时发出一个新的 observable 列表!正在查看 http://reactivex.io/documentation/operators/switch.html - 也许这能以某种方式起作用?
在此处编辑更新 这是我想出的(刚从 class 中提取)
// users can monitor this to get the latest address book.
addresses$: Observable<FirebaseListObservable<any>>;
// keeps a reference to the address subject.
private addressSubject = new BehaviorSubject<any>(Observable.empty());
constructor(private db: AngularFireDatabase, private authService: AuthService) {
this.addresses$ = this.addressSubject.asObservable();
authService.user$.subscribe((user) => {
this.user = user;
if (this.user) {
this.addressSubject.next(this.db.list(`/users/${this.user.uid}/addresses`));
} else {
this.addressSubject.next(Observable.empty());
}
});
}
所以你想要做的,在伪代码中,是这样的:
首先调用
authService
检索用户 ID。如果用户存在,去数据库中检索地址。
如果没有,就return没什么。
将结果分配给
addresses$
,将其作为可观察对象公开。
如果您像这样分解步骤,那么您将不会Observables
感到困惑。只要您知道执行列出的每个任务的方法,您就很好。
代码如下:
export class AddressService {
user: any;
addresses$: FirebaseListObservable<Address[]>;
constructor(private db: AngularFireDatabase, private authService: AuthService) {
//Step 4: assign the observable back to addresses$
this.addresses$ =
//Step 1: first call the auth service
this.authService.user$.switchMap(user => {
this.user = user;
//Step 2: if user exist, call DB service
if (this.user) {
return this.db.list(`/users/${this.user.uid}/addresses`);
}
//Step 3: else just return nothing
else {
return Obsevable.empty()
}
})
}
}
我在代码中做了一些内联注释,以便您可以与伪代码进行比较。