IMO this is still too large of a hammer for this problem.

This whole “unexpected case” thing is only a problem when you’re linking 
libraries that are external to/shipped independently of your app. Right now, 
the *only* case where this might exist is Swift on the server. We *might* run 
in to this in the future once the ABI stabilizes and we have the Swift 
libraries shipping as part of iOS/macOS/Linux. Other than this, unexpected enum 
cases won’t really be a problem developers have to deal with.

Because this will be such a relatively rare problem, I feel like a syntax 
change like what’s being proposed is a too-massive hammer for such a small nail.

What feels far more appropriate is:

🅰️ Teaching the compiler/checker/whatever about the linking semantics of 
modules. For modules that are packaged inside the final built product, there is 
no need to deal with any unexpected cases, because we already have the 
exhaustiveness check appropriate for that scenario (regardless of whether the 
module is shipped as a binary or compiled from source). The app author decides 
when to update their dependencies, and updating those dependencies will produce 
new warnings/errors as the compiler notices new or deprecated cases. This is 
the current state of things and is completely orthogonal to the entire 
discussion.

and

🅱️ Adding an attribute (@frozen, @tangled, @moana, @whatever) that can be used 
to decorate an enum declaration. This attribute would only need to be consulted 
on enums where the compiler can determine that the module will *not* be part of 
the final built product. (Ie, it’s an “external” module, in my nomenclature). 
This, then, is a module that can update independently of the final app, and 
therefore there are two possible cases:

        1️⃣ If the enum is decorated with @frozen, then I, as an app author, 
have the assurance that the enum case will not change in future releases of the 
library, and I can safely switch on all known cases and not have to provide a 
default case. 

        2️⃣ If the enum is NOT decorated with @frozen, then I, as an app 
author, have to account for the possibility that the module may update from 
underneath my app, and I have to handle an unknown case. This is simple: the 
compiler should require me to add a “default:” case to my switch statement. 
This warning is produced IFF: the enum is coming from an external module, and 
the enum is not decorated with @frozen.


==========

With this proposal, we only have one thing to consider: the spelling of 
@frozen/@moana/@whatever that we decorate enums in external modules with. Other 
than that, the existing behavior we currently have is completely capable of 
covering the possibilities: we just keep using a “default:” case whenever the 
compiler can’t guarantee that we can be exhaustive in our switching.

Where the real work would be is teaching the compiler about 
internally-vs-externally linked modules.

Dave

> On Jan 2, 2018, at 7:07 PM, Jordan Rose via swift-evolution 
> <swift-evolution@swift.org> wrote:
> 
> [Proposal: 
> https://github.com/apple/swift-evolution/blob/master/proposals/0192-non-exhaustive-enums.md
>  
> <https://github.com/apple/swift-evolution/blob/master/proposals/0192-non-exhaustive-enums.md>]
> 
> Whew! Thanks for your feedback, everyone. On the lighter side of 
> feedback—naming things—it seems that most people seem to like '@frozen', and 
> that does in fact have the connotations we want it to have. I like it too.
> 
> More seriously, this discussion has convinced me that it's worth including 
> what the proposal discusses as a 'future' case. The key point that swayed me 
> is that this can produce a warning when the switch is missing a case rather 
> than an error, which both provides the necessary compiler feedback to update 
> your code and allows your dependencies to continue compiling when you update 
> to a newer SDK. I know people on both sides won't be 100% satisfied with 
> this, but does it seem like a reasonable compromise?
> 
> The next question is how to spell it. I'm leaning towards `unexpected case:`, 
> which (a) is backwards-compatible, and (b) also handles "private cases", 
> either the fake kind that you can do in C (as described in the proposal), or 
> some real feature we might add to Swift some day. `unknown case:` isn't bad 
> either.
> 
> I too would like to just do `unknown:` or `unexpected:` but that's 
> technically a source-breaking change:
> 
> switch foo {
> case bar:
>   unknown:
>   while baz() {
>     while garply() {
>       if quux() {
>         break unknown
>       }
>     }
>   }
> }
> 
> Another downside of the `unexpected case:` spelling is that it doesn't work 
> as part of a larger pattern. I don't have a good answer for that one, but 
> perhaps it's acceptable for now.
> 
> I'll write up a revision of the proposal soon and make sure the core team 
> gets my recommendation when they discuss the results of the review.
> 
> ---
> 
> I'll respond to a few of the more intricate discussions tomorrow, including 
> the syntax of putting a new declaration inside the enum rather than outside. 
> Thank you again, everyone, and happy new year!
> 
> Jordan
> 
> _______________________________________________
> swift-evolution mailing list
> swift-evolution@swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
swift-evolution@swift.org
https://lists.swift.org/mailman/listinfo/swift-evolution

Reply via email to