Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Throwing errors inside observer methods in Swift

I'm trying to implement some validation rules inside property observer methods (didSet and willSet) and I am attempting to use throw inside the closure. Here's an illustrative example:

enum SomeClassError: ErrorType {
  case NumberNotPositive
}

class SomeClass {
  var PositiveNumber: Int {
    willSet(value) {
      guard value > 0 else {
        throw SomeClassError.NumberNotPositive
      }
    }
  }
}

Of course, the compiler complains that Error is not handled because the enclosing function is not declared 'throws' and I really don't know where to declare that didSet actually throws.

Do you know if there is a way to throw errors within property observer methods?

like image 576
catalandres Avatar asked Nov 21 '22 17:11

catalandres


1 Answers

You can call a function in your property observersdo-try-catch` clause that throws, e.g.

enum SomeClassError: ErrorType {
    case NumberNotPositive
}

class SomeClass {
    var positiveNumber: Int {
        willSet {
            do {
                try newValueIsPositive(newValue)
            } catch SomeClassError.NumberNotPositive {
                print("Error: Number not positive")
            } catch {
                print("Error: Unknown error")
            }
        }
    }

    init() {
        positiveNumber = 1
    }

    func newValueIsPositive(newValue: Int) throws {
        guard newValue > 0 else {
            throw SomeClassError.NumberNotPositive
        }
    }
}

/* Example */
var a = SomeClass()
a.positiveNumber = 2
a.positiveNumber = -1   // Error: Number not positive
print(a.positiveNumber) // -1

Note that I used the newValue property accessible by default when using the willSet property observer (rather than explicitly defining property name value for the value that will be set after willSet). Also note that, in your current form, the class property positiveNumber still gets assigned -1 (although an ErrorType case is thrown regarding this).

like image 113
dfrib Avatar answered Feb 16 '23 07:02

dfrib