Closed
Description
Key points from discussion from this morning:
- Assume all non-ambient members of non-
const
enums are computed (even those initialized with literals), both for inlining purposes and for .d.ts generation purposes - Continue to aggressively compute initializer expressions in both
const
and non-const
enums - Ambient non-const enums preserve existing behavior (computed iff there is no initializer)
- Continue to have --preserveConstEnums flag, which causes emit of the lookup object for
const
enums but does not change inlining
Tag @ahejlsberg
Metadata
Metadata
Assignees
Type
Projects
Relationships
Development
No branches or pull requests
Activity
danquirk commentedon Mar 2, 2015
Note this would likely be a breaking change
RyanCavanaugh commentedon Mar 2, 2015
A retelling of how we got here (note: using "1.0" here as a stand-in for all behavior prior to Vlad's proposed PR which does more aggressive initializer folding)
For regular enums, in 1.0, we would only inline constant members, and a member was only constant if its initializer was a literal. This led to a "workaround" (or "design feature", depending) that you could use an equivalent syntactic form to get a computed enum member, e.g.
enum X { Y = (3) }
. This is an important scenario for when you don't want to ship a .d.ts file that hardcodes in enum values because you intend to change those enum values in the future.Vlad's change more aggressively resolves computational expressions in enum member initializers, so the member
Y = (3)
orY = 3+0
now looks like a constant initializer rather than a computed one. This is an important breaking change for the aforementioned people who want to have a "constancy not guaranteed" .d.ts file, or who are doing wacky separate compilation (e.g. Monaco) and don't want referring implementation files to have their enum references inlined.One proposed workaround was that you would initialize your "should not be inlined" enum members via a function call (e.g.
enum X = Math.min(3)
), but this is obviously weird.The cleanest place to land is that we treat all non-
const
enum members as computed. This is a breaking change, but only in one scenario -- where a non-ambient enum is declared with constant members, consumed only at inlined sites, and the emitted JS (of the lookup object) is excluded from the script context. This scenario is easily fixed, though, because any enum fitting this profile can have theconst
keyword added to its declaration to force inlining at all consumption sites (which obviously must work, if all the non-const enum consumption sites were originally inlined).RyanCavanaugh commentedon Apr 3, 2015
Ref #2594