Почему невозможно вернуть Obeservable.of(false) в блоке catch в методе canActivate?

Я использую функцию canActivate для защиты некоторых маршрутов (администратор). Для этого случая я использую authGuard класс / функции:

Проблема в том, когда я пытаюсь вернуть наблюдаемое логическое значение как: return Observable.of(false); не работает должным образом и выдает следующее сообщение об ошибке:

Аргумент типа '(err: any) => Наблюдаемый | Observable'нельзя назначить параметру типа'(err: any, catch: Observable) => ObservableInput'. Тип 'Наблюдаемый | Observable "нельзя назначить типу" ObservableInput ". Тип Observable не может быть назначен типу ObservableInput. Тип "Наблюдаемый" не может быть назначен типу "ArrayLike". Свойство length отсутствует в типе Observable.

Я искал и нашел вид этой проблемы, но не совсем то же самое. И предоставленная подсказка / решение было использовать .throw(err);

Когда я изменяю возврат на: return Observable.throw(err);, то ошибка исчезает, но не возвращается false как и положено для того, чтобы защитить мой маршрут.

Я считаю, что это проблема типа и т. Д., Но я просто не могу это исправить, так что я продолжаю возвращаться observable.of(false)

canActivate( next: ActivatedRouteSnapshot, state: RouterStateSnapshot ): Observable<boolean> | Promise<boolean> | boolean {
        return this.userService.getAdminAuth()
        .map( (res) => {
            if ( res === true) {
                return true;
            } else {
                ......
                return false;
            }
        })
        .catch( (err) => {
            if ( err.status === 403 ) {
                console.log(`403:  ${err.status}`);
                return this.userService.refreshToken()
                    .map( (res) => {
                        console.log(`Res RefreshToken: ${res}`);
                    });
            }
            return Observable.of(false); // protect route!
        });
}

Функции в user.service.ts:

....

isAdminAuthenticated = false;

public getAdminAuth() {
    console.log('Saved token: ' + localStorage.getItem('ac_token') );
    if ( this.isAdminAuthenticated === true ) {
        return Observable.of(true);
    } else {
        return this.http.get(
           'URL', { 
              headers: new HttpHeaders({"Accept": "application/json"}), 
              withCredentials: true, 
              observe: "response" 
           }
        )
        .map((res) => {
            if (res.status === 200) {
                this.isAdminAuthenticated = true;
                return true;
            } else {
                return false;
            }
        }, (err) => {
            console.log('Error: ' + err);
            return false;
        });
    }
}


refreshToken() {
    return this.http.get(
        'URL', 
        { 
            headers: new HttpHeaders(
                {
                    "Accept": "application/json",
                    "Authorization" : "Bearer " + localStorage.getItem('ac_token')
                }
            ), 
            withCredentials: true, 
            observe: "response" 
        }
    )
}

С другой стороны, если я изменю refreshToken функция для:

refreshToken() {
        return this._http.get(
            'URL', 
            { 
                headers: new HttpHeaders(
                    {
                        "Accept": "application/json",
                        "Authorization" : "Bearer " + localStorage.getItem('ac_token')
                    }
                ), 
                withCredentials: true, 
                observe: "response" 
            }
        ).map( (res) => {
            console.log(`Res: ${JSON.stringify(res)}` );
        }), (err) => {
            console.log(`Err: ${JSON.stringify(err)}` );
        };
}

Тогда ошибка говорит:

ОШИБКА в src/app/admin.guard.ts(38,9): ошибка TS2322: тип "Наблюдаемый" не может быть назначен типу "логический | Обещание | Наблюдаемое. Тип "Наблюдаемый" не может быть назначен типу "Наблюдаемый". Тип 'логическое значение | {}'нельзя назначить типу' логический '. Тип "{}" нельзя назначить типу "логический". src/app/service.guard.ts: ошибка TS2339: Свойство 'map' не существует для типа '(err: any) => boolean'.

1 ответ

Потому что вы должны использовать return Observable.throw(false), of это успех, throw это ошибка.

Другие вопросы по тегам