Using Result type with async/await

The syntax is not great now, but if you want to make async calls one by one, try this:

func doSomething() async {
  let productsResult = await fetchProducts()

  let products: [Product]
  switch productsResult {
    case .success(let success): products = success
    case .failure(let error): return await handleError(error)
  }
  
  let productImagesResult = await fetchProductImages(products)
  // ...
}

There ere some discussions about improving of syntax:

guard-catch with typed throws can make such things easier.
Result can be easily transformed to typed throw, if these features come into play. So may be in future soothing like this can be possible:

extension Result {
  func getValueOrThrow() throws Failure -> Success {
    switch self {
    case .success(let success): return success
    case .failure(let error): throw error
    }
  }
}

func doSomething() async {
  guard let products: [Product] = await fetchProducts().getValueOrThrow() catch {
    return await handleError(error) // the error here is of concrete type, the same as in Result
  }  
  let productImagesResult = await fetchProductImages(products)
  // ...
}
1 Like