Search code examples
swift2do-catch

How to avoid nesting do/catch statements in Swift2


I keep wanting to do this:

do {
    let result = try getAThing()
} catch {
   //error
}

do {
    let anotherResult = try getAnotherThing(result) //Error - result out of scope
} catch {
    //error
}

But seem only to be able to do this:

do {
     let result = try getAThing()
     do {
          let anotherResult = try getAnotherThing(result) 
     } catch {
          //error
     }
} catch {
     //error
}

Is there a way to keep an immutable result in scope without having to nest do/catch blocks? Is there a way to guard against the error similar to how we use the guard statement as an inverse of if/else blocks?


Solution

  • In Swift 1.2, you can separate the declaration of the constant from the assignment of the constant. (See "Constants are now more powerful and consistent" in the Swift 1.2 Blog Entry.) So, combining that with the Swift 2 error handling, you can do:

    let result: ThingType
    
    do {
        result = try getAThing()
    } catch {
        // error handling, e.g. return or throw
    }
    
    do {
        let anotherResult = try getAnotherThing(result)
    } catch {
        // different error handling
    }
    

    Alternatively, sometimes we don't really need two different do-catch statements and a single catch will handle both potential thrown errors in one block:

    do {
        let result = try getAThing()
        let anotherResult = try getAnotherThing(result)
    } catch {
        // common error handling here
    }
    

    It just depends on what type of handling you need.