【问题标题】:Is it possible somehow call async Ionic Storage synchronously?是否有可能以某种方式同步调用异步离子存储?
【发布时间】:2017-04-28 10:43:49
【问题描述】:

我正在尝试在 Angular2 HTTP 类之上创建一个用于使用 API 的类。主要的是我需要添加用户授权后可用的自定义身份验证标头。

主要问题是token存储在Ionic Storage模块中,只能异步获取,但我需要返回具体的类型......

export class APIRequest extends Http {

    private storage : Storage;

    constructor (backend: XHRBackend, options: RequestOptions) {
        super(backend, options);

        this.storage = new Storage;
    }

    request(url: string|Request, options?: RequestOptionsArgs): Observable<Response> {
        if (typeof url === 'string') {
            url = AppConfig.API_SERVER + url
        } else {
            url.url = AppConfig.API_SERVER + url.url
        }

        this.storage.get('authToken').then(token => {
            if (typeof url === 'string') {
                if (!options) {
                    options = {headers: new Headers()};
                }

                options.headers.set('Authorization', `Bearer ${token}`);
            } else {
                url.headers.set('Authorization', `Bearer ${token}`);
            }
            // Here I need to return 
        }, err => {
            // throw some error
        })

        return super.request(url, options).catch(this.catchAuthError(this));
    }
}

所以基本上我需要以某种方式将return super.request(url, options)... 放入存储的承诺中,并在我获得该令牌时返回。

【问题讨论】:

  • 为什么不能使用return storage.get().then(fn).then( token =&gt; { return super.request() })
  • @raj 因为: Observable&lt;Response&gt;
  • 不是Observables 方面的专家,但是如何使用fromPromise 做出一个不符合承诺的可观察对象,然后使用flatMap 返回request observale。
  • @raj 可以提供任何例子吗?
  • 猜你有答案:)

标签: angular typescript ionic-framework ionic2 angular2-http


【解决方案1】:

几乎是重复的。 (没找到)

至少,答案可以应用于同一个问题。如果您想保留返回的Observable,则可以将您的Promise (this.storage.get) 转换为Observable

之后,您可以使用flapMap 之类的运算符来返回super.request 的值。

注意:编译器不明白它现在返回的是Response,所以将返回类型更改为Observable&lt;any&gt;(仍将返回Response))

export class APIRequest extends Http {

    private storage : Storage;

    constructor (backend: XHRBackend, options: RequestOptions) {
        super(backend, options);

        this.storage = new Storage;
    }
    // any return type (will return Response object but compiler doesn't understand that)
    request(url: string|Request, options?: RequestOptionsArgs): Observable<any> {
        if (typeof url === 'string') {
            url = AppConfig.API_SERVER + url
        } else {
            url.url = AppConfig.API_SERVER + url.url
        }

        //convert the Promise to an Observable
        val storageObservable = Observable.fromPromise(this.sotrage.get('authToken'));

        // rxjs/add/operator/mergeMap
        return storageObservable.flatMap(token => {
            if (typeof url === 'string') {
                if (!options) {
                    options = {headers: new Headers()};
                }

                options.headers.set('Authorization', `Bearer ${token}`);
            } else {
                url.headers.set('Authorization', `Bearer ${token}`);
            }
            // the value that will be returned
            return super.request(url, options).catch(this.catchAuthError(this));
        }, err => {
            // throw some error
        })


    }
}

有用的链接:

【讨论】:

  • 我认为return 不见了?
  • @raj 感谢您的指出!你是对的,编辑了答案
  • 最后成功了吗?目前正在调试哈哈
  • @Ivaro18 抱歉耽搁了,但刚刚测试过...尝试执行请求时出现错误TypeError: Cannot read property 'json' of undefined(…)。我想是因为它返回的不是Response
猜你喜欢
  • 1970-01-01
  • 2017-10-21
  • 2011-08-22
  • 1970-01-01
  • 1970-01-01
  • 2019-05-26
  • 1970-01-01
  • 2015-12-07
  • 1970-01-01
相关资源
最近更新 更多