Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/angular/27.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Facebook 可观察开关/平面图立即启动_Facebook_Angular_Rxjs - Fatal编程技术网

Facebook 可观察开关/平面图立即启动

Facebook 可观察开关/平面图立即启动,facebook,angular,rxjs,Facebook,Angular,Rxjs,我的服务中有以下代码: public loginWithFacebook():可观察{ log('Login'); 返回Observable.fromPromise(this.fb.login()).flatMap((userData)=>{ 返回这个.http.post(authFacebook,{access_-token:userData.authResponse.accessToken},{observe:'response'}); }).do((响应:HttpResponse)=>{

我的服务中有以下代码:

public loginWithFacebook():可观察{
log('Login');
返回Observable.fromPromise(this.fb.login()).flatMap((userData)=>{
返回这个.http.post(authFacebook,{access_-token:userData.authResponse.accessToken},{observe:'response'});
}).do((响应:HttpResponse)=>{
const-token=response.headers.get('x-auth-token');
如果(令牌){
setItem('id_token',token);
}
});
}
getFacebookProfile():可观察{
log(“获取配置文件”);
返回Observable.fromPromise(this.fb.getLoginStatus())
.filter((状态)=>state.status=='connected')
.switchMapTo(Observable.fromPromise(this.fb.api('/me')));
}
之后,我在我的组件中使用它来获取成功登录后的配置文件信息

this.profileData = this.usersService.loginWithFacebook()
    .flatMapTo(this.usersService.getFacebookProfile());
但是,由于某些原因,getFacebookProfile()甚至在登录过程完成之前立即激发。我得到了一个身份验证错误。此外,我必须登录两次才能显示个人资料信息

我一直认为,switchMap和flatMap只有在前一个观测值发出值时才会切换到下一个观测值。 我做错了什么

--编辑--


如果订阅第一个可观察对象并在订阅中调用getFacebookProfile(),则一切正常。但我觉得这并不是一个非常优雅的解决方案。

问题在于承诺是急切的。当您编写observable时,您正在调用
this.fb.login()
,并将返回的承诺传递给
fromPromise

这意味着登录是在调用
loginWithFacebook
时启动的,而不是在它返回的可观察对象上调用
subscribe
时启动的

如果要将
登录
延迟到调用
订阅
,可以使用:


public loginWithFacebook():可观察的

多亏了@cartant的回答,它终于起作用了。然而,由于某种原因,我不得不用defer操作符包装它两次。如果有人能解释为什么有必要这样做,我将不胜感激。这有点奇怪

public loginWithFacebook():可观察{
返回可观察的延迟(()=>
Observable.defer(()=>this.fb.login()).flatMap((userData)=>
{
返回这个.http.post(authFacebook,{access_-token:userData.authResponse.accessToken},{observe:'response'});
}).do((响应:HttpResponse)=>{
const-token=response.headers.get('x-auth-token');
如果(令牌){
setItem('id_token',token);
}
})
);
}
getFacebookProfile():可观察{
返回可观察的延迟(()=>
Observable.defer(()=>this.fb.getLoginStatus())
.filter((状态)=>state.status=='connected')
.switchMapTo(Observable.fromPromise(this.fb.api('/me')))
);
}

听起来应该能用。但是当我刚刚尝试的时候,我得到了同样的结果。由于某些原因,仍然会立即触发。在组成可观察链时,您需要在传递承诺的所有位置使用
延迟