4

In Swift 5 Apple introduced Result type. It's generic enum with two cases:

public enum Result<Success, Failure: Error> {
    case success(Success), failure(Failure)
}

Personally I used to two separate completions in network calls success: Completion and failure: Completion, but from what I see now, Apple pushing us to use single completion with Result type and then inside perform switch. So what are advantages of this approach with Result? Because in a lot of cases I can just omit error handling and don't write this switch. Thanks.

Bohdan Savych
  • 3,310
  • 4
  • 28
  • 47
  • Imo switching everywhere will be painful. I'd still stick to the two completions handler. Flow of control is a lot clearer that way. – Rakesha Shastri Apr 08 '19 at 12:34
  • 3
    It's not mandatory to use `Result`. You can do what you want. But I'm sure many, many people (like myself) will appreciate it and take advantage of it. – vadian Apr 08 '19 at 12:46
  • Not being compatible with Objective-C can be an issue. Rewriting all your code, that's useless. Advantage: When you are doing same code and not factorize it elsewhere, like "reshowing some stuff, enabling user interaction, etc." in case of failure AND success. – Larme Aug 07 '20 at 16:31

2 Answers2

4

You shouldn’t omit cases when Result is failure. You shouldn’t do it with Result and you shouldn’t do it with your closure for failure. You should handle errors.

Anyway, Result type was introduced for simplifing completion handlers. You can have single closure for handling success or failure (primary-opinion based if two separate closures are better or not). Also Result is designed for error handling. You can simply create your own enum conforming to Error and then you can create your own error cases.

Robert Dresler
  • 10,580
  • 2
  • 22
  • 40
-1

Swift 5 introduced Result<Success, Failure> associated value enumeration[About] It means that your result can be either success or failure with additional info(success result or error object). Good practice is to manage error case and success case as atomic task.

Advantages:

  • Result is a single/general(generic)/full type which can be used for all yes/no cases
  • Not optional type
  • Forces consumers to check all cases
public enum Result<Success, Failure>  {
    case success(Success)
    case failure(Failure)
}

To use it

//create
func foo() -> Result<String, Error> {
    //logic
    if ok {
        return .success("Hello World")
    } else {
        return .failure(.someError)
    }
}

//read
func bar() {
    let result = foo()
    switch result {
    case .success(let someString):
        //success logic
    case .failure(let error):
        //fail logic
    }
}
yoAlex5
  • 29,217
  • 8
  • 193
  • 205