Network Error Handling์ ๋ํด ์์๋ณด๋ค๊ฐ ๊ด๋ จ operator๋ค์ ์ ๋ฆฌํด๋ณด๋ ค๊ตฌ ํฉ๋๋ค.
์ฐธ๊ณ : https://okanghoon.medium.com/rxswift-5-error-handling-example-9f15176d11fc
RxSwift์์๋ Error Handling์ ํ๋๋ฐ ๋ค์๊ณผ ๊ฐ์ ๋ฐฉ๋ฒ์ด ์์ต๋๋ค.
1. Catch ํน์ ๊ฐ์ผ๋ก error ๋ณต๊ตฌ
2. Retry ์ฌ์๋
3. materialize / dematerialize : Sequence ๋ฅผ ์ ์ดํด์ ์ฒ๋ฆฌ
1. Catch
Error ๋ฐ์ ์, catch ๋ด์ ํน์ ๊ฐ์ผ๋ก ์ด๋ฒคํธ๋ฅผ ๋ฐ์์ํค๊ณ complete ์ํจ๋ค.
1) catchError
let observable = Observable<Int>
.create { observer -> Disposable in
observer.onNext(1)
observer.onNext(2)
observer.onNext(3)
observer.onError(NSError(domain: "", code: 100, userInfo: nil))
observer.onError(NSError(domain: "", code: 200, userInfo: nil))
return Disposables.create { }
}
observable
.catchError { .just(($0 as NSError).code) }
.subscribe { print($0) }
.disposed(by: disposeBag)
/* Prints:
next(1)
next(2)
next(3)
next(100)
completed
*/
1, 2, 3์ ์ถ๋ ฅ ํ์ code 100 error๊ฐ ๋ฐ์ํ๊ณ catchError์์ Error๊ฐ .just(100)์ผ๋ก ๋ฐ๋์ด ์ถ๋ ฅ๋๊ณ complete๋๋ค.
2) catchErrorJustReturn
let observable = Observable<Int>
.create { observer -> Disposable in
observer.onNext(1)
observer.onNext(2)
observer.onNext(3)
observer.onError(NSError(domain: "", code: 100, userInfo: nil))
observer.onError(NSError(domain: "", code: 200, userInfo: nil))
return Disposables.create { }
}
observable
.catchErrorJustReturn(999)
.subscribe { print($0) }
.disposed(by: disposeBag)
/* Prints:
next(1)
next(2)
next(3)
next(999)
completed
*/
error๊ฐ ๋ฐ์ํ์๋ Error๋ฅผ ๋ฌด์ํ๊ณ ์ง์ ํ element๋ฅผ ๋ฐํํ๋ค.
2. retry
source observable์์ error๊ฐ ๋ฐ์์ ๋ค์ subscribeํ์ฌ error๊ฐ ๋ฐ์ํ์ง ์๊ธธ ๋ฐ๋๋ค. ๋ผ๊ณ ์๊ฐํ๊ณ ์๋ค.
1) retry()
์ฐ์ฐ์ ์ฑ๊ณตํ ๋๊น์ง ๊ณ์ ๋ฐ๋ณตํ๋ค.
let reloadPublisher = PublishSubject<Void>()
reloadPublisher
.flatMap {
Api.getRepositories()
.retry()
}
์ธํฐ๋ท ์ฐ๊ฒฐ์ ๋๊ณ Api๊ฐ ์คํจํ๊ฒ ๋๋ฉด ๊ณ์ Api.getRepositories()์ ํธ์ถ ํ ๊ฒ์ด๋ค.
2) retry(count)
๋ฐ๋ณต ํธ์ถํ count๋ฅผ ์ง์ ํ๋ค.
let reloadPublisher = PublishSubject<Void>()
reloadPublisher
.flatMap {
Api.getRepositories()
.retry(3)
}
let observable = Observable<Int>
.create { observer -> Disposable in
observer.onNext(1)
observer.onNext(2)
observer.onNext(3)
observer.onError(NSError(domain: "", code: 100, userInfo: nil))
observer.onError(NSError(domain: "", code: 200, userInfo: nil))
return Disposables.create { }
}
observable
.retry(2)
.subscribe { print($0) }
.disposed(by: disposeBag)
/* Prints:
next(1)
next(2)
next(3)
next(1)
next(2)
next(3)
error(Error Domain= Code=100 "(null)")
*/
์ฌ์๋ ํ์๋ฅผ ๋์ด์๋ฉด error๋ฅผ ๋ฐฉ์ถํ๋ค.
3) retryWhen()
์ฌ์๋ ํ๋ ์์ ์ ์ง์ ํ ์ ์๊ณ , ํ๋ฒ๋ง ์ํํ๋ค.
retry ์ ๋ค๋ฅด๊ฒ ๋ง์ง๋ง Error๋ฅผ ์ด๋ฒคํธ๋ก ์ ๋ฌํ์ง ์๋๋ค.
let observable = Observable<Int>
.create { observer -> Disposable in
observer.onNext(1)
observer.onNext(2)
observer.onNext(3)
observer.onError(NSError(domain: "", code: 100, userInfo: nil))
observer.onError(NSError(domain: "", code: 200, userInfo: nil))
return Disposables.create { }
}
observable
.retryWhen { err -> Observable<Int> in
return .timer(3, scheduler: MainScheduler.instance)
}
.subscribe { print($0) }
.disposed(by: disposeBag)
/* Prints:
next(1)
next(2)
next(3)
(3 seconds)
next(1)
next(2)
next(3)
completed
*/
3. Materialize / Dematerialize
- RxSwift ์์ ์ฐ์ด๋ Event Sequence๋ฅผ ์ ์ดํ ์ ์๊ฒ ํด์ค๋ค.
- ๋ณดํต Materialize / Dematerialize ๋ ํจ๊ป ์ฌ์ฉํ๋ค.
- Observable์ ๋ถํดํ ์ ์๊ธฐ ๋๋ฌธ์ ์ ์คํ๊ฒ ์ฌ์ฉํด์ผ ํ๋ค.
Materialize
- Sequence ๋ฅผ Event<Element> Sequence๋ก ๋ณํํ๋ค.
Dematerialize
- Event<Element> Sequence ๋ฅผ ๋ค์ Sequence๋ก ๋ณํํ๋ค.
let observable = Observable<Int>
.create { observer -> Disposable in
observer.onNext(1)
observer.onNext(2)
observer.onNext(3)
observer.onError(NSError(domain: "", code: 100, userInfo: nil))
observer.onError(NSError(domain: "", code: 200, userInfo: nil))
return Disposables.create { }
}
observable
.materialize()
.map { event -> Event<Int> in
switch event {
case .error:
return .next(999)
default:
return event
}
}
.dematerialize()
.subscribe { event in
print(event)
}
.disposed(by: disposeBag)
/* Prints
next(1)
next(2)
next(3)
next(999)
completed
*/
'IOS๐ > RxSwift' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
[RxSwift] Transforming Operator (map, flatMap, scan, reduce) (0) | 2022.05.16 |
---|---|
[RxSwift] Filtering Operator (distinctUntilChanged) (0) | 2022.05.10 |
[RxSwift] Schedular๋ (subscribeOn, observeOn) (0) | 2022.04.29 |
[RxSwift] Signal, ControlProperty, ControlEvent ๋ ? (0) | 2022.03.21 |
[RxSwift] Driver๋ ? (feat. bind) (0) | 2022.03.21 |
๋๊ธ