【问题标题】:TypeScript Type 'Promise<void | Object>' is not assignable to type 'Promise<Object>' on Promise.then()TypeScript 类型 'Promise<void | Object>' 不可分配给 Promise.then() 上的类型 'Promise<Object>'
【发布时间】:2020-12-02 15:07:48
【问题描述】:

我目前正在尝试实现以 base64 格式缓存文档的服务。我希望这个服务从 sessionStorage 中获取文档,如果 sessionStorage 中没有文档,则从 IRequestService 中获取它,然后将其保存到 sessionStorage。我尝试了这种方法,但出现类型错误

Type 'Promise<void | GetDocumentResult>' is not assignable to type 'Promise<GetDocumentResult>'.

代码如下所示:

getDocument(requestId: string, documentId: DocumentID, requestService: IRequestService): Promise<GetDocumentResult> {
    if (this.storageKey in sessionStorage) {
      const documentsMap: Map<DocumentID, GetDocumentResult> = new Map(JSON.parse(sessionStorage.getItem(this.storageKey)!))
      if (documentsMap.get(documentId) !== undefined) {
        return new Promise(resolve => resolve(documentsMap.get(documentId)!))
      }
    }

    return requestService.getDocument(requestId, documentId)
      .then(value => {this.setDocument(documentId, value)})
}

我期待 Promise.then 的返回类型是 Promise,但由于某种我不明白的原因,它是 Promise

有人知道为什么会这样吗?

谢谢

【问题讨论】:

    标签: javascript typescript promise


    【解决方案1】:

    如前所述,您的 then 回调确实返回 void 而不是结果。你在寻找

    getDocument(requestId: string, documentId: DocumentID, requestService: IRequestService): Promise<GetDocumentResult> {
      if (this.storageKey in sessionStorage) {
        const documentsMap: Map<DocumentID, GetDocumentResult> = new Map(JSON.parse(sessionStorage.getItem(this.storageKey)!));
        const document = documentsMap.get(documentId);
        if (document !== undefined) {
          return Promise.resolve(document);
        }
      }
    
      return requestService.getDocument(requestId, documentId).then(value => {
        this.setDocument(documentId, value);
        return value;
    //  ^^^^^^^^^^^^
      });
    }
    

    顺便说一句,我建议将缓存查找和存储 (setDocument?) 提取到单独的服务中,并让该服务将 documentsMap 保存在内存中,而不是每次调用 getDocument 时都解析 JSON。

    【讨论】:

    • 您好,谢谢您的好心先生。你确实是对的。祝你有美好的一天。
    • 我不确定如何实现您的建议。我发布的代码是 DocumentSessionStorageService 的一部分,它是 IDocumentStorageService 的实现。提取缓存查找是什么意思?不是每次要检查文档是否缓存都需要解析一个json吗?
    • 为什么不在DocumentSessionStorageService 的构造函数中只使用一次this._documentsMap = new Map(JSON.parse(sessionStorage[this.storageKey]))
    • 愚弄我。再次感谢楼主
    【解决方案2】:

    您很可能遇到问题,因为您没有在 .then()

    中返回任何内容

    这里:

     .then(value => {this.setDocument(documentId, value)})
    

    这使您返回的类型为Promise&lt;void&gt; 而不是Promise&lt;GetDocumentResult&gt;

    最终版本应该是这样的:

    getDocument(requestId: string, documentId: DocumentID, requestService: IRequestService): Promise<GetDocumentResult> {
        if (this.storageKey in sessionStorage) {
          const documentsMap: Map<DocumentID, GetDocumentResult> = new Map(JSON.parse(sessionStorage.getItem(this.storageKey)!))
          if (documentsMap.get(documentId) !== undefined) {
            return new Promise(resolve => resolve(documentsMap.get(documentId)!))
          }
        }
    
        return requestService.getDocument(requestId, documentId)
          .then(value => { return this.setDocument(documentId, value)})
    }
    

    【讨论】:

    • 您好,感谢您的回复。我已经尝试过了,但据我了解,在 .then 方法中没有返回任何内容,因为它只是一个成功回调。当我添加返回时,没有任何变化。 .then 第一个参数的类型是 (value: GetDocumentResult) => void | PromiseLike
    • 您的回答部分正确,但 setDocument 的返回类型为 void,我必须返回值。而且我的评论不正确,我应该在 .then 中返回一个值。祝你有美好的一天
    • @omastik 很高兴它有帮助,没问题 :)
    猜你喜欢
    • 1970-01-01
    • 2018-01-04
    • 1970-01-01
    • 2016-09-18
    • 2017-10-23
    • 1970-01-01
    • 1970-01-01
    • 2017-04-10
    • 2023-01-25
    相关资源
    最近更新 更多