簡體   English   中英

如何在Node.js中正確取消http請求?

[英]How to cancel http request properly in Node.js?

我需要在Node.js中實現可取消的客戶端HTTP請求,而不使用外部庫。 我給了一個Promise對象 - cancellationPromise - 在外部請求取消時被拒絕。 這就是我所知道的,我可能需要調用request.abort()

問題是,只有當https.request仍處於掛起且response對象尚未可用時,我才應該調用request.abort()嗎?

或者,即使我已經獲得了response對象並且正在處理響應數據,我是否應該調用它,如下面的代碼中所示? 在這種情況下,是否會阻止任何更多的response.on('data')事件發生?

  async simpleHttpRequest(url, oauthToken, cancellationPromise) {
    let cancelled = null;
    let oncancel = null;

    cancellationPromise.catch(error => { 
      cancelled = error; oncancel && oncancel(error) });

    try {
      const response = await new Promise((resolve, reject) => {
        const request = https.request(
          url.toString(), 
          { 
            method: 'GET', 
            headers: { 'Authorization': `Bearer ${oauthToken}` }        
          }, 
          resolve);

        oncancel = error => request.abort();
        request.on('error', reject);
        request.end();
      });

      if (cancelled) throw cancelled;

      // do I need "oncancel = null" here?
      // or should I still allow to call request.abort() while fetching the response's data?

      // oncancel = null;

      try {
        // read the response 
        const chunks = await new Promise((resolve, reject) => {
          response.on('error', reject);  
          const chunks = [];
          response.on('data', data => chunks.push(data));
          response.on('end', () => resolve(chunks));
        });

        if (cancelled) throw cancelled;
        const data = JSON.parse(chunks.join(''));
        return data;
      }
      finally {
        response.resume();
      }
    }
    finally {
      oncancel = null;
    }
  }

這取決於您希望通過中止請求來實現的目標。

只是一點背景。 HTTP 1無法“取消”它發送的請求,然后等待響應。 您無法“回滾”您所做的請求。 您需要分布式事務才能執行此操作。 進一步閱讀。 )正如MDN開發人員文檔所述

如果請求已經發送,XMLHttpRequest.abort()方法將中止該請求。 請求中止時,其readyState將更改為XMLHttpRequest.UNSENT(0),並且請求的狀態代碼將設置為0。

基本上,您停止應用程序處理響應 另一個應用程序可能(如果你在發送它之后調用abort() )完成它的處理。

從問題的角度來看:

問題是,只有當https.request仍處於掛起且響應對象尚未可用時,我才應該調用request.abort()嗎?

TL.DR。:從您的申請的角度來看,這只是重要的。 當我瀏覽你的代碼時,我認為它會正常工作。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM