Javascript API 호출 취소하기

shelly·2022년 4월 4일
0

문제

다운로드 로직을 작성하고 있었다. 요구사항은 다음과 같았다.
1. 다운로드중 임을 나타내라.
2. 다운로드가 완료되면 알림을 띄워라.
3. 다운로드에 실패하면 실패알림을 띄워라.
4. 다운로드 취소 버튼을 추가하여, 다운로드 중단을 가능하게 해라.

1 - 3 은 비동기 동작과 try catch로 자주 사용한 방식이다.

download()

const download = async () => {
	try {
    	openAlert(1, '다운로드 중입니다.')
    	await api.post( ... ) // 다운로드 api 요청
        closeAlert(1)
        openAlert(2, '다운로드가 완료되었습니다.')
    } catch(e) {
    	openAlert(3, '다운로드가 실패했습니다.')
    }
	
}

그런데, 4의 요구사항은 api의 response가 도착하기 전에 네트워크 연결을 끊어야하는 것이다. 지금까지 이러한 요구사항을 처리해본 적이 없기 때문에, 정리하면서 방법을 찾아보려한다.

탐색

AbortController

MDN : AbortController

  • AbortController 인터페이스는 하나 혹은 그 이상의 요청을 중단시킨다.
  • 예시 코드
let controller;
const url = "video.mp4";

const downloadBtn = document.querySelector('.download');
const abortBtn = document.querySelector('.abort');

downloadBtn.addEventListener('click', fetchVideo);

abortBtn.addEventListener('click', function() {
  
  // 4. controller의 abort함수를 실행시키면, fetch요청이 중단된다.
  if (controller) controller.abort();
  console.log('Download aborted');
});

function fetchVideo() {
  // 1. abortController를 생성한다.
  controller = new AbortController();
  
  // 2. controller의 시그널을 추출(?)한다.
  const signal = controller.signal;
  
  // 3. fetch에 signal을 연결한다.
  fetch(url, { signal })
    .then(function(response) {
      console.log('Download complete', response);
    })
    .catch(function(e) {
      console.log('Download error: ' + e.message);
    });
}

Axios Cancellation : AbortController

공식문서
axios도 마찬가지로 AbortController를 생성하여 signal을 연결하면 된다.

// 1. controller 생성
const controller = new AbortController();

// 2. axios에 signal 연결
axios.get('/foo/bar', {
   signal: controller.signal
}).then(function(response) {
   //...
});

// 3. 중지
controller.abort()

AbortController는 axios 버전 0.22.0 이상부터 지원한다.


하지만 현재 나의 axios 버전은 0.19.x 이기 때문에, 위의 방식이 정상동작하지 않는다.

따라서 axios 버전을 업데이트하거나, cancelToken을 사용해야한다.

Axios Cancellation : CancelToken

cancelToken방식을 사용해보자.

// cancel token 생성
const CancelToken = axios.CancelToken;
const source = CancelToken.source();

axios.post('/user/12345', {
  name: 'new name'
}, {
  // cancel token 설정
  cancelToken: source.token
})

// cancel token과 연결된 호출 취소
source.cancel('Operation canceled by the user.');

검색 키워드

  • axios cancel
  • axios cancellation
  • axios api 중단
  • axios api 취소
  • AbortController
  • Axios CancelToken

0개의 댓글