iOS/Swift

[Swift] await, async

_Rey 2022. 6. 30. 15:10

동시성 프로그래밍 키워드인 await와 async를 SwiftUI에서 사용하는 법에 대해 알아보려고 한다.

 

await와 async 키워드를 사용하는 코드를 먼저 작성해보자.

아래와 같은 싱글톤 NetworkManager를 만들어보자

class NetworkManager {
    let baseURL = "{URL}"
    static let shared: NetworkManager = NetworkManager()
    
    // async 한다고 꼭 throws/try를 쓸 필요는 없다.
    func requestAsync() async -> [Step] {
        guard let url = URL(string: self.baseURL) else {
            return []
        }
        
        do {
            let urlRequest = URLRequest(url: url)
            let (data, _) = try await URLSession.shared.data(for: urlRequest)
            let stepList = try JSONDecoder().decode([Step].self, from: data)
            return stepList
        } catch (let e) {
        	// Error handling
            print(e)
        }
        
        return []
    }
}

 

비동기처리가 이뤄질(await/async 기능이 있는) 함수는 async 키워를 붙이면 된다.

SwiftUI에서 사용된다고 생각해보자.

struct NetworkView: View {
    @State private var stepList: [Step] = []
    let viewModel: NetworkManager = NetworkManager.shared
    
    var body: some View {
        VStack {
            Button("Get Step await") {
                Task {
                    self.stepList = await self.viewModel.requestAsync()
                }
            }
            
            List(self.stepList, id: \.title) { step in
                Text("\(step.title): \(step.content)")
            }
        }
    }
}

Task라는 것을 사용했다.

priority와 throws가 Optional이다.

위의 코드는 throws 처리가 없지만, 만약 requestAsync에서 do-catch 처리를 하지 않았다면?

func requestAsyncTry() async throws -> [Step] {
    let urlRequest = URLRequest(url: url)
    let (data, _) = try await URLSession.shared.data(for: urlRequest)
    let stepList = try JSONDecoder().decode([Step].self, from: data)
    return stepList
}

함수에는 async뒤에 throws 키워만 붙여주면 된다.

 

그리고 오류를 던지고 있으니, Task에서 사용할 때

Task {
    self.stepList = try await self.viewModel.requestAsyncTry()
}

try를 앞에 붙여주기만 하면된다.

UIKit에서는 아직 안 써봤지만, SwiftUI에서는 쓰는데 그렇게 어렵진 않아보인다!

 

Swift.org에는 Concurrency 페이지에 Task, Actor 등의 키워드들이 있는데, 아직 제대로 사용할 정도로 이해하진 못했다.