How does Error work in Swift in Xcode 8 beta 4
Asked Answered
M

3

22

Seems like when converting our old code to beta 4, I keep casting Error to NSError. That will even lead sometimes to a warning "conditional cast from 'Error' to 'NSError' always succeeds". I feel like I'm not understanding how best to use Error. I want to get to thinks like error.code, error.localizedDescription... Is there good documentation or tutorials that explains these Error changes?

For example:

func webView(_ webView: UIWebView, didFailLoadWithError error: Error) { 

Right now I'm doing something like:

if let error = error as? NSError {
 if error.code == NSURLErrorCancelled {

But that gives the warning "Conditional cast from 'Error' to 'NSError' always succeeds"

Maddis answered 1/8, 2016 at 21:1 Comment(3)
Error is bridgeable to NSError in the same way that String is bridgeable to NSString. I.e (error as NSError) would work.Lean
Would you mind marking an answer as correct if it ended up helping you?Lean
I don't think these answers are right, and I think it is a beta 4 issue.Maddis
L
35

Error is bridgeable to NSError in the same way that String is bridgeable to NSString. I.e (error as NSError) would work.

if  (error as NSError).code == NSURLErrorCancelled { 
    // code
}
Lean answered 13/8, 2016 at 6:26 Comment(1)
FYI: just tried to cast my own enum MyError : Error { case test }. The result: nsError.code prints 0, nsError.domain prints MyError, nsError.localizedDescription prints The operation couldn’t be completed. (MyError error 0.)Phytogenesis
T
22

Do this:

Swift 3.0 and Swift 4.0

if error._code == NSURLErrorCancelled { }
Tatianna answered 15/12, 2016 at 19:52 Comment(2)
I hate it when a language comes with "features" like thatAnimalize
I wouldn't rely on something undocumented. It could be changed without warning and your app will break.Oriana
S
4

Error catching in Swift 3 has changed. Search for NSError in Release Notes. Quote:

Additionally, error types imported from Cocoa and Cocoa Touch maintain all of the information in the corresponding NSError, so it is no longer necessary to catch let as NSError to extract (for example) the user-info dictionary. Specific error types also contain typed accessors for their common user-info keys. For example:

do {
    let regex = try NSRegularExpression(pattern: "(", options: [])
} catch {
    // error is of type NSError already
    print(error.localizedDescription)
}
Separable answered 2/8, 2016 at 3:42 Comment(3)
How would I deal with this? func webView(_ webView: UIWebView, didFailLoadWithError error: Error) { Right now I'm doing something like if let error = error as? NSError { if error.code == NSURLErrorCancelled { But that gives the warning "Conditional cast from 'Error' to 'NSError' always succeeds"Maddis
I'm not sure if this is accurate. error.code is still not accessible, and alt-clicking error will show you that it's still inferred to be of the Error type.Wyly
@Jason the issue you're having is using error as? NSError instead of error as NSError. Error can always be casted to NSError so you don't need to use a conditional cast (i.e. as?) because it will always succeed (which is exactly what the error is telling you).Intermission

© 2022 - 2024 — McMap. All rights reserved.