2017-07-01 39 views
0

我正在使用@ angular/http進行http調用(Observable)和NativeStorage庫,這是Promise的存儲機制。這就是爲什麼我使用FromPromise將Promise funtion「NativeStorage.getItem(」xxx「)」轉換爲Observable。Observable中的Promise Error not calling catch

我甚至不確定這是否是一種很好的做法,並且鏈條在行「console.log(」HIT SUCCESSFULLY「);」並停止執行代碼。

由於存儲中沒有名爲「externalAccessToken」的項,因此在Promise中捕獲異常爲null是正常的,但我不明白爲什麼它在此之後會停止執行。直到現在,我試圖返回除null以外的其他內容,並使用導致「未處理的Promise拒絕」錯誤的「Promise.reject()」。

我如何才能讓執行的代碼,然後點擊可觀測

public getExternalAccessTokenFromStorage(): Observable<any> { 
    let externalAccessTokenPromise = NativeStorage.getItem('externalAccessToken'); 
    let getExternalAccessTokenFromStorage: Observable<any> = Observable.fromPromise(externalAccessTokenPromise.then(x => x) 
    .catch(() => { 
     console.log("HIT SUCCESSFULLY"); 
     return null 
    })); 

    return getExternalAccessTokenFromStorage.map(x => { 
     console.log("NOT HIT AT ALL"); 
     return x; 
    }).catch(() => { 
     console.log("NOT HIT AT ALL"); 
     return null; 
    }); 
} 



public getUserInfo(): Observable<StoredUserModel> {   
    //Get External Access Token From LocalStorage   

    return this.getExternalAccessTokenFromStorage().flatMap((x: IExternalAccessTokenBindingModel) => { 
     return this.getAccessTokenFromStorage().flatMap((accessToken: AccessTokenModel) => { 
      console.log("NOT HIT AT ALL"); 
      let headers = new Headers(); 
      headers.append("Authorization", "Bearer " + accessToken.access_token); 
      headers.append("Content-Type", "application/json"); 
      let options = new RequestOptions({ headers: headers }); 
      var externalBindingModel = JSON.stringify(x); 
      return this.http.post(this.baseUrl + '/api/Account/ExternalUserInfo', externalBindingModel, options).map((res: Response) => { 
       //ADD USER INTO NATIVESTORAGE 
       this.addUserIntoStorage(res.json()); 
       return res.json(); 
      }); 
     }); 
    }).catch(x => { 
     return this.getAccessTokenFromStorage().flatMap((accessToken: AccessTokenModel) => { 
      console.log("NOT HIT AT ALL"); 
      let headers = new Headers(); 
      headers.append("Authorization", "Bearer " + accessToken.access_token); 
      let options = new RequestOptions({ headers: headers }); 
      return this.http.get(this.baseUrl + '/api/Account/UserInfo', options).map((res: Response) => { 
       //ADD USER INTO NATIVESTORAGE 
       let user: StoredUserModel = res.json(); 
       this.addUserIntoStorage(res.json()); 
       return user; 
      }); 
     }).catch(error => { 
      return null; 
     }); 
    }); 
} 

修訂問題的捕捉功能:

我已刪除Promise.catch並保持Observable.catch爲了趕未處理的異常在可觀察;

public getExternalAccessTokenFromStorage(): Observable<any> { 
    let externalAccessTokenPromise = NativeStorage.getItem('externalAccessToken'); 
    let getExternalAccessTokenFromStorage: Observable<any> = Observable.fromPromise(externalAccessTokenPromise); 

    return getExternalAccessTokenFromStorage.map(x => { 
     return x; 
    }).catch(() => { 
     return null; 
    }); 
} 

我得到以下錯誤;

enter image description here

+0

爲什麼不使用'Observable.catch'而不是'Promise.catch',即將錯誤處理移出'fromPromise'? – jonrsharpe

+0

我試過了,它會拋出類似「未處理的錯誤」:item null異常。如果你想我可以產生並寫出確切的錯誤 – mctuna

+0

是的,請給出一個[mcve]沒有任何多餘的細節。 – jonrsharpe

回答

2

Catch作品完全一樣,在編程try/catch clasues。

給下面的例子:

try { 
    throw new Error('bang'); 
} catch(ex) { 
    // do nothing 
} 

console.log('I'm still reachable'); 

我們可以複製上述與觀察到的是這樣的:

let o = Observable.create((observer)=>{ 
    observer.error(new Error('bang')); 
}).catch(()=>{ 
    // do nothing 
}); 

o.subscribe(()=>{ 
    console.log('I'm still reachable'); 
}); 

如果你想抓取和處理錯誤,但隨後防止下面的代碼從執行使用try/catch你會這樣做:

try { 
    throw new Error('bang'); 
} catch(ex) { 
    // do some logic here 
    throw ex; 
} 

console.log('I cannot be reached'); 

這是sa我在觀察。你必須重新拋出錯誤或產生一個也失敗的觀察值。

let o = Observable.create((observer)=>{ 
    observer.error(new Error('bang')); 
}).catch((ex)=>{ 
    // do some logic here 
    return Observable.throw(ex); 
}); 

o.subscribe(()=>{ 
    console.log('I cannot be reached'); 
}); 
+0

感謝您的詳細信息;返回Observable.throw(前)工作 – mctuna

1

的問題是,你正在追趕,但不處理錯誤。你會想把這個錯誤當成一個Observable。

public getExternalAccessTokenFromStorage(): Observable<any> { 
    let externalAccessTokenPromise = NativeStorage.getItem('externalAccessToken'); 
    let getExternalAccessTokenFromStorage: Observable<any> = Observable.fromPromise(externalAccessTokenPromise); 

    return getExternalAccessTokenFromStorage.map(x => { 
     return x; 
    }).catch((error: any) => 
     Observable.throw(error.json().error || 'Server error'); 
    ); 
} 

然後,您可以處理你在一個承諾的形式響應和錯誤:

this.getExternalAccessTokenFromStorage().subscribe(
    res => console.log(res), 
    error => console.log(error)); 
+0

你需要返回' Observable.throw'否則什麼都不會發生。 – cgTag

+0

這是錯誤的回報旁邊,謝謝 – mctuna