[swift-evolution] [Pitch] Consistent bridging for NSErrors at the language boundary

Jon Shier jon at jonshier.com
Sat May 14 01:45:39 CDT 2016


Charles:
	Foundation error reporting is based on NSError, nothing else. In none of my apps have I used my own NSError’s and in the few frameworks I use or maintain, few use NSError, and then only to avoid having to declare a custom error type, to make the API perhaps a bit more familiar to consumers. All your concern about conversion to and from NSErrors is largely irrelevant to anyone who isn’t using Swift from Objective-C on a regular basis. It’s utterly irrelevant to the native Swift programmer. I’m not sure where your issue about presenting non-NSError’s come from, since the mechanisms to present an error would have to be custom written no matter the error type. The drawbacks I see with exposing NSError’s properties on every ErrorType is that those properties are only there as a hack to interoperate with NSError. Really they’d go away as Swift evolves it’s own default error representation, or language leaves it to developer to build their own. 
	Essentially, I think that if you want to improve ErrorType, formalizing its relationship to NSError is the wrong way. NSErrors are not good error representations, especially in Swift, and we should move away from them as soon as possible.


Jon
 
> On May 14, 2016, at 1:46 AM, Charles Srstka <cocoadev at charlessoft.com> wrote:
> 
> On May 14, 2016, at 12:19 AM, Jon Shier via swift-evolution <swift-evolution at swift.org> wrote:
>> 
>> Charles:
>> 	I appreciate the attempt to minimize a current pain point and I agree on most of your analysis of the current NSError bridging but I think your proposal is fundamentally flawed. By forcing the core error type to have properties from NSError, you’re essentially finalizing what all error types in Swift should look like. Error domains, codes, and info dictionaries are not Swift, and forcing every error produced in Swift to have those properties is a regression from the freedom ErrorType has given us. No native Swift error type I’ve seen so far has chosen to replicate those properties, and for good reason: they are a relic of C which have no place in Swift. There are far better error designs out there. If you want to propose a strong type of error for Swift, go ahead, but it should be thoroughly inspired by Swift, not driven by a desire to ease bridging to NSError.
> 
> Nothing is forced at all, any more than they are currently. The thing to remember is that ErrorProtocol *already* defines properties for error domains and codes:
> 
> public protocol ErrorProtocol {
>  var _domain: String { get }
>  var _code: Int { get }
> }
> 
> Thus, the statement that no native Swift error type has these properties could not be farther from the truth, as in fact, *every* Swift error type has these two properties (and several prominent error types in the standard library provide specific values for these properties as well; POSIXError and NSCocoaError come to mind). The reason many Swift developers haven’t noticed this fact is because the properties have default implementations, which means that if you don’t have a specific need to override them, you never have to deal with them. Adding a userInfo property, which also has a default implementation (returning an empty dictionary), will therefore not take away any of the freedom of ErrorType, or really cause any difference at all to a developer who is not interested in providing userInfo values on his/her errors.
> 
> What the proposal will do, on the other hand, is give a lot of that freedom *back*. The fact of the matter is that the entire error-reporting mechanism is currently based on NSError. If you have a method which can return an error, and you want that error to be presentable to the user in a form more expressive than “MyApp.MyErrorType error 2”, you currently have only two choices: 1) create some home-grown mechanism to convert your errors to NSErrors, and be sure to invoke that mechanism when throwing from any method that could conceivably be called from Objective-C, or 2) just use NSErrors all the way down, foregoing the use of native Swift errors at all. My proposal would allow the free and unlimited use of Swift native errors everywhere errors are a possibility with no drawbacks, since if an error needed to be made into a human-readable form, this would only be a simple matter of defining a userInfo property on the error type, even if much later down the line, and would not necessitate adding an NSError conversion at every throw-site in the program. Indeed, this proposal will actually *remove* a lot of NSError-based thinking from the actual code, and localize all such considerations to a relatively small area, to such extent as they are needed.
> 
> Charles
> 



More information about the swift-evolution mailing list