지난 포스트에서 옵저버블 에러를 처리하는 세 단계를 이야기했습니다. 이번 포스트에서 에러를 catch 하고 난 후에 어떤 처리를 할 수 있는지 에러 처리 전략에 대해 이야기해 보도록 하겠습니다.
옵저버블 에러 처리 전략
http request를 할 때는 에러가 발생할 수 있는 여러 상황이 있습니다. 예를 들어 url이 잘못됐거나, 권한이 없거나 연결 문제가 발생할 수 있습니다. 따라서 HTTP request를 발행할 때마다 에러 처리를 추가하는 것이 좋습니다.
지난 포스트에서 다뤘던 옵저버블 에러를 처리하기 위한 단계를 기억하시나요?
- 첫 번째로 에러를 catch합니다.
- 두 번째로 선택적으로 에러를 throw 합니다.
- 세 번째로 에러가 난 옵저버블을 새 옵저버블로 바꿔줍니다.
에러를 잡기 위해 파이프라인에 catchError 연산자를 추가한 모습이 아래와 같습니다.
catchError 안에서 뭘 어떻게 처리해 주어야 할까요? 위에서 말한 에러 단계에 따르면 에러를 throw 하고, 에러가 있는 옵저버블을 새 옵저버블로 바꿔줘야 합니다.
에러 난 옵저버블 교체하기
에러가 난 옵저버블을 새 옵저버블로 교체할 때는 경우에 따라 아래 같은 전략을 선택할 수 있습니다.
첫 번째 전략은 에러가 발생한 옵저버블를 하드 코딩된 데이터나 로컬에 저장된 데이터를 이용해서 새 옵저버블로 만들어 교체하여 반환하는 것입니다.
catchError의 함수에서 of로 옵저버블을 만들어 하드 코딩된 데이터를 방출하게 하고 있습니다. 서비스에서 http request가 실패해서 데이터를 가져올 수 없을 때 하드 코딩된 제품의 배열을 반환해서 보여주는 게 경우에 따라서는 좋은 해결책이 될 수 있습니다. 다시 한번 언급하자면 새 옵저버블로 교체하는 이유는 에러가 있는 옵저버블은 더 이상 방출을 하지 않기 때문입니다.
두 번째 전략은 단순히 빈 값이나 빈 배열을 반환하는 옵저버블 객체를 반환하기입니다.
마지막 전략은 항목을 방출하지 않고 즉시 complete 되는 RxJS상수인 EMPTY를 사용해서 에러가 난 옵저버블을 대체할 수 있습니다.
에러를 다시 던지기(throw)
옵저버블 에러 처리를 할 때 선택적으로 에러를 다시 던져서 책임을 위임할 수 있습니다.
위 예는 throwError 생성 함수를 사용하여 문자열 값으로 새 에러를 발생시키고 있습니다. 이전 포스트에서 말했듯이 throwError 대신에 아래와 같이 throw를 사용할 수 있습니다.
throwError, throw 두 가지 모두 http 서비스를 호출하는 컴포넌트에서 에러 메시지가 포함된 에러가 발생하므로 해당 컴포넌트에서 에러를 처리해 줘야 합니다.
언급한 것처럼 컴포넌트로 에러가 전달되는 경우에는 컴포넌트 쪽에서도 적절히 에러 처리하는 로직이 포함되어 있어야 합니다. 컴포넌트 쪽에서는 에러를 catch 해서 화면에 에러 메시지를 출력하는 케이스가 많이 있습니다. 서비스에서 throw 한 에러 메시지를 단순히 화면에 출력시키고 다시 에러를 throw 하고 싶지 않을 경우는 아래와 같이 서비스를 호출하는 컴포넌트에서 catch를 한 후에 EMPTY를 리턴해 줄 수 있습니다.
위 예는 http 서비스를 이용하고 있는 컴포넌트에서 에러를 catch 하고 에러가 발생했을 때 서비스 쪽에서 설정한 에러 메시지를 화면에 출력할 프로퍼티에 할당한 후 EMPTY를 리턴해 주므로 에러를 처리하고 있습니다. 이 예에서도 알 수 있듯이 옵저버블 에러 처리에 있어서 에러를 던지는 건 선택사항이지만 새 옵저버블을 만들지 않고선 옵저버블 에러를 완결 지울 수 없습니다.
만약 컴포넌트에서도 throw를 통해 에러를 던져야 하는 상황일 때는 어떻게 해야 할까요? 이런 경우는 글로벌 에러 핸들러를 만들어서 모든 컴포넌트의 에러를 처리해주는 서비스를 만들어 줘야 합니다. 그리고 글로벌 에러 핸들러에서는 에러 화면으로 전환하는 등의 처리가 필요하게 될 것입니다. 글로벌 에러 핸들러는 RxJS영역을 넘어선 앵귤러 처리의 과정이므로 다른 포스트에서 다뤄 보도록 하겠습니다.
여기까지 수고하셨습니다.
'프로그래밍 > Angular' 카테고리의 다른 글
[RxJS / angular] 13. 옵저버블 데이터 스트림 결합, 결합 연산자 유형 (0) | 2022.07.14 |
---|---|
[RxJS / angular] 12. http response 매핑하기(포멧 바꾸기) (0) | 2022.07.13 |
[RxJS / angular] 10. 옵저버블 에러 처리 (catchError, throwError, EMPTY) (0) | 2022.07.08 |
[RxJS / angular] 9. http 절차적 조회 패턴과 Async 파이프 사용하기 (0) | 2022.07.06 |
[RxJS / angular] 8. take 연산자 (0) | 2022.07.05 |
댓글