[swift] Swift에서 비동기 작업을 위한 타임아웃 처리 방법

비동기 작업은 애플리케이션에서 많이 사용되는 기능 중 하나입니다. 하지만 때로는 비동기 작업이 지연되거나 무한히 실행되는 문제가 발생할 수 있습니다. 이러한 상황에서는 타임아웃 처리를 통해 작업을 제한하고 예외 처리를 할 수 있습니다.

DispatchWorkItem을 사용한 타임아웃 처리

Swift에서는 GCD(Grand Central Dispatch)를 통해 비동기 작업을 처리할 수 있습니다. DispatchWorkItem을 사용하여 타임아웃 처리를 할 수 있습니다.

let timeoutValue: DispatchTime = .now() + .seconds(10)

let workItem = DispatchWorkItem {
    // 비동기 작업 수행
}

DispatchQueue.global().async(execute: workItem)

let result = workItem.wait(timeout: timeoutValue)

if result == .success {
    // 작업이 성공적으로 완료됨
} else {
    // 타임아웃이나 예외 발생
}

DispatchWorkItem의 wait 메서드를 사용하여 작업의 완료를 대기할 수 있습니다. wait 메서드는 작업이 완료되거나 지정된 시간이 경과할 때까지 대기합니다. 작업이 성공적으로 완료되면 result는 .success를 반환하고, 타임아웃이나 예외 발생 시 result는 .timedOut 또는 .interrupted를 반환합니다.

PromiseKit을 사용한 타임아웃 처리

PromiseKit은 Swift에서 비동기 작업을 더 편리하게 처리할 수 있는 라이브러리입니다. PromiseKit을 사용하여 타임아웃 처리를 할 수 있습니다.

func performAsyncTask() -> Promise<Void> {
    return Promise { seal in
        // 비동기 작업 수행
    }
}

let timeoutPromise = after(seconds: 10).done {
    // 타임아웃 발생
}

let taskPromise = performAsyncTask()

race([taskPromise, timeoutPromise]).done { result in
    if result == taskPromise {
        // 작업이 성공적으로 완료됨
    } else {
        // 타임아웃 발생
    }
}.catch { error in
    // 예외 처리
}

PromiseKit의 race 메서드를 사용하면 비동기 작업과 타임아웃 Promise을 동시에 실행하고, 먼저 완료되는 작업 결과를 반환할 수 있습니다. race 메서드의 결과로 얻은 Promise를 통해 결과를 처리할 수 있습니다. 작업이 성공적으로 완료되면 taskPromise가, 타임아웃이 발생하면 timeoutPromise가 반환됩니다. 작업이 완료되지 않거나 예외가 발생할 경우 catch 블록에서 예외 처리를 할 수 있습니다.

결론

Swift에서 비동기 작업을 수행할 때 타임아웃 처리는 중요한 요소입니다. DispatchWorkItem과 PromiseKit을 사용하여 비동기 작업의 타임아웃을 처리할 수 있습니다. 이를 통해 애플리케이션에서 비동기 작업의 예외 상황을 처리할 수 있고, 안정적인 프로그래밍 환경을 구축할 수 있습니다.

참고 자료