In a word... wow. You've got me thinking hard here. Those are some peculiar use cases, and they do a great job of highlighting why someone might forego using `class`. One thing both proposal-class-fields and proposal-object-members have in common is that the focus is on producing instance-private fields. All 3 of the scenarios you presented lay outside of that focus for one reason or another.
> Adding the same “slot” to multiple classes which don’t inherit from each other I'm a little confused by this one. Are you saying you want multiple non-hierarchally related classes to have an instance private field with shared name, such that the same private field name refers to a distinct and separate field on each instance of every such class, but where any such instance can have that field referenced by that shared name from any member function of the corresponding classes? (Wow that was wordy to write out...) If this is what you meant, you're describing friend classes. The top-down processing nature of ES makes this a difficult thing to create a clean syntax for without risking leaking the private state or fundamentally altering how ES is processed. Mutual friendship is even harder. ... and yet I just thought of a way to do it. By telling you this I'm leaving myself to consider writing a proposal containing 2 new keywords: `befriend` and `friendly`. I don't know if this can be done with the existing proposal being what it is. However, with my proposal, there's a chance. The `friendly` keyword would declare that an object is prepared to share select information with any object that befriends it. The `befriend` keyword would allow an object to request friendship with an existing friendly object. I'm not sure this is a good idea, though. This means that any object declared 'friendly' is automatically insecure as all it takes to gain access to the selected members of its private space would be to 'befriend' it. > Selectively sharing access to private state through functions declared outside the class body The example you gave above still declares the functions in question inside the `class` body, so that's not really a solution. If the example you gave actually solves your use case, then what you're asking for here isn't even needed. If, however, that was a bad example, then it sounds like you're looking for friend functions. See the previous section. > Adding slots dynamically, e.g. when adding mix-in methods that may initialize a new slot if necessary when called, since subclassing is not always appropriate Sounds to me like you'd love for `class` syntax to look like this: ```js class [<identifierName1>] [extends <identifierName2>] [mixes <identifierName3>[, <identifierName3>[, ...]]] { ... } ``` so that the private fields of the objects in the `mixes` list are added to the set of private fields provided by the `class` definition directly. That would also require another proposal, but I think that can be done regardless of which instance-private fields proposal gets accepted. On Sat, Jul 28, 2018 at 12:49 PM Darien Valentine <valentin...@gmail.com> wrote: > To put this another, much briefer way, here’s a hypothetical model for > associating private state with objects that would cover me. Privacy would > be provided... > > 1. in the form of symbolic keys whose presence cannot be observed (i.e., > they would not be exposed by `getOwnPropertySymbols`) > 2. and which have a syntactic declaration so that one can be sure they are > really getting private keys (i.e., an api like `Symbol.private()` wouldn’t > work) > > ``` > const bar = private(); > > // alternatively: const #bar; could be anything so long as it’s syntactic > > class Foo { > constructor() { > this[bar] = 1; > } > } > > // etc > ``` > > The keys would be typeof 'symbol'; the only difference being that they are > symbols which are flagged as private when created. They would be permitted > only in syntactic property assignments and accesses. Existing reflection > utilities would disallow the use or appearance of such symbols both to > ensure privacy and to maintain the invariant that they are always simple > data properties: > > ```js > Reflect.defineProperty({}, #bar, { ... }); // throws type error > Object.getOwnPropertyDescriptors(someObjWithAPrivateSlot); // does not > include it > foo[bar] = 2; // fine > ``` > > This is significantly simpler than what’s in flight both in terms of > syntax and mechanics, which makes me suspicious that I’m probably ignoring > things that other people find important. However it would bring parity to > ES objects wrt being able to implement genuinely private slots in userland > with the same flexibility as what is done internally. > > In total, this entails a new primary expression, a boolean flag associated > with symbol values, and an extra step added to several algorithms > associated with Object and Reflect. > _______________________________________________ > es-discuss mailing list > es-discuss@mozilla.org > https://mail.mozilla.org/listinfo/es-discuss >
_______________________________________________ es-discuss mailing list es-discuss@mozilla.org https://mail.mozilla.org/listinfo/es-discuss