[swift-evolution] Enums and Source Compatibility
clattner at nondot.org
Sun Sep 10 00:36:42 CDT 2017
> On Sep 6, 2017, at 10:37 PM, Rod Brown <rodney.brown6 at icloud.com> wrote:
>> We’ve talked about enums many times across years, and it seems like the appropriate model follows the generally understood resilience model. Specifically, there should be three different kinds of enums, and the kind should affect users outside their module in different ways:
>> 1. private/fileprivate/internal enum: cases can be added freely. All clients are in the same module, so the enum is implicitly fragile, and all switches within the current module may therefore be exhaustive.
>> 2. public enum (i.e., one that isn’t marked fragile): cases may be added freely. Within the module that defines the enum, switches may be exhaustive. However, because the enum is public and non-fragile, clients outside the current module must be prepared for the enum to add additional cases in future revisions of the API, and therefore they cannot exhaustively match the cases of the enum.
>> 3. fragile public enum: cases may not be added, because that would break the fragility guarantee. As such, clients within or outside of hte current module may exhaustively match against the enum.
>> This approach gives a very natural user model: app developers don’t have to care about enum resilience until they mark an enum as public, and even then they only have to care about it when/if they mark an enum as public. This also builds on the notion of fragility - something we need for other nominal types like structs and classes - so it doesn’t introduce new language complexity. Also such an approach is entirely source compatible with Swift 3/4, which require defaults (this isn’t an accident, it follows from the anticipated design).
>> This approach doesn’t address the problem of what to do with C though, because C doesn’t have a reasonable notion of “extensible” vs “nonextensible” enum. As such, we definitely do need an attribute (or something) to add to Clang. I think that your proposal for defaulting to “extensible” and using __attribute__((enum_extensibility(closed))) override this is perfectly sensible.
> Hi Chris,
> I think I agree with you in general, with 1 exception:
> I think the wording “fragile”, while technically correct, implies the exact opposite of the promise contract, namely that it will not change between releases of your framework. Perhaps a term like “concrete” would be more appropriate? It would be fragile in that it is a fragile interface, but it would be concrete as a promise to external dependencies. If you are exhaustively enumerating, you’re basing it on the notion that it won’t change, not that it’s "easy to break” (which fragile as a word would seem to imply).
Just to clarify, I wasn’t intending to make a syntax proposal here. I was talking about the semantic model that we should provide. The bikeshed should be painted in a color that aligns best with the rest of the resilience model.
-------------- next part --------------
An HTML attachment was scrubbed...
More information about the swift-evolution