11 ms·
> V8 v7.2 adds support for public class [1] fields. Support for private class [2] fields is planned for a future V8 release. For those who don't know private c
by drinchev 8y ago
> V8 v7.2 adds support for public class [1] fields. Support for private class [2] fields is planned for a future V8 release.
For those who don't know private class fields add the weird "#" character for defining them inside the `class {}` block.
class IncreasingCounter {
#count = 0;
get value() {
console.log('Getting the current value!');
return this.#count;
}
increment() {
this.#count++;
}
}
This looks way worse than having what TypeScript did by introducing `public` / `private` keywords. Is there any body
which votes for es-next features such as this one? I wonder how the "#" private field popped up in Chrome specs.
1 : https://developers.google.com/web/updates/2018/12/class-fields https://developers.google.com/web/updates/2018/12/class-fiel...
2 : https://developers.google.com/web/updates/2018/12/class-fields#private_class_fields https://developers.google.com/web/updates/2018/12/class-fiel...
- Waterluvian 8y agoI can't find it but I remember reading through the rationale. I don't fully recall if I understood or agreed with the reasoning but I recall there was reasoning that was more than just visual preference.
- Shorel 8y agoOf course. That abomination requires as much rationale as they can produce in the given time frame. Good design doesn't require such degree of mental gymnastics.
- Vinnl 8y agoYou can't really do good design if you have to remain backwards compatible with the entire internet.
- Waterluvian 8y agoTry explaining this to my peers who just don't appreciate why JavaScript is such a mess. Is this problem found anywhere else in the programming world at this scale?
- abritinthebay 8y agoYes. Just is different forms. C++ has been through similar compatibility hell.
- adrianN 8y agoThere are similar concerns with C(++) and Java.
- kevincennis 8y agohttps://github.com/tc39/proposal-class-fields/blob/master/PRIVATE_SYNTAX_FAQ.md#why-isnt-access-thisx https://github.com/tc39/proposal-class-fields/blob/master/PR...
- sjroot 8y agoI agree with you and I had this same question when the article discussing private class fields was posted here a few days ago. There has been a lot of discussion regarding public and private keywords here: https://github.com/tc39/proposal-class-fields/blob/master/PRIVATE_SYNTAX_FAQ.md#why-arent-declarations-private-x https://github.com/tc39/proposal-class-fields/blob/master/PR...
- __ryan__ 8y agoThe rationale for the "#" syntax is that it makes it clear that the field is NOT an object property. This is an important distinction because you can do this: class Example { #myVar = 100; getPrivateMyVar() { return this.#myVar; } getLocalMyVar() { return this.myVar(); } } const example = new Example(); example.myVar = 200; console.log(example.getPrivateMyVar()) // 100; console.log(example.getLocalMyVar()) // 200; I agree the syntax is terrible. But you need to be able to distinguish between the own object property myVar and the private field myVar.
- Illniyar 8y agoAccess modifiers, as the name suggest, are an accessibility feature not a scope feature (like let). example.myVar = 500 should throw an access error. You don't need to distinguish because you shouldn't be shadowing private variables.
- __ryan__ 8y agoNot as far as the spec is concerned. They decided that private variables should be completely scoped to the class. "Having a private field named x must not prevent there from being a public field named x, so accessing a private field can't just be a normal lookup. This is only an issue in JavaScript because of its lack of static types. Statically typed languages use type declarations to distinguish the external-public/internal-private cases without the need of a sigil. But a dynamically typed language doesn't have enough static information to differentiate those cases." [0] There are also performance concerns to changing the lookup logic without the sigil. More info in the link. 0: https://github.com/tc39/proposal-class-fields/blob/master/PRIVATE_SYNTAX_FAQ.md#why-isnt-access-thisx https://github.com/tc39/proposal-class-fields/blob/master/PR...
- dotancohen 8y agoI still don't see why this is an issue in Javascript. PHP, the canonical hate-it dynamically-typed language, does not have this issue. Sure, you say, that's because in PHP a public property and a private property cannot have the same name. Correct. Why is this a requirement? What problem is this trying to solve? In e.g. older Python we would use the convention of a leading underscore to indicate that a property is private, even if technically one _could_ access it publicly it was understood that is a bad idea to do in practice. It's not a security issue - in every language one could read the "private" properties by some method or another. Reflection, for instance. Or, back to PHP, by casting the object to an array (I did mention that PHP is the canonical hate-it dynamically-typed language).
- dana321 8y ago#aargh Please roll this back, what a nightmare!
- walki 8y ago> #aargh Many system programmers will think this line is commented out. Indeed what a nightmare!
- jlokier 8y agoYup. The muscle memory is so strong, when writing Javascript/Typescript I type # by accident sometimes. But then, // is one of the most commonly used operators in another language I use, so it's weirdly symmetrical :)
- henrikeh 8y agoCurious: which language?
- madamelic 8y agoPython uses it for integer division. Typically it is meant as "divide and floor" as far as I've seen.
- jlokier 8y agoPerl, the defined-or operator. Like ||, but // tests definedness instead of truthiness. The equivalent in several other languages is ??, which is uglier imho, but it's just syntax. https://en.wikipedia.org/wiki/Null_coalescing_operator https://en.wikipedia.org/wiki/Null_coalescing_operator I use // and ?? often as it's conceptually clean, fast and concise. When available, it arises naturally in logic like caches, memoizations and defaults. //= is pretty useful too, and I'm surprised it's not more widely available.
- Memosyne 8y agoWouldn't most system programmers think it's a macro?
- jbverschoor 8y agoLooks like a comment hash to me.
- SigmundA 8y agoComing from C# which uses public private keywords there is still a convention of naming privates prefixed with a underscore so when reading the code its immediately obvious its a private. Looks like Typescript conventions say not to do that. Either way the compiler should throw an error if trying to access a private incorrectly. In JS I guess it helps reduce runtime errors since there is no compiler to check for you and again very clearly visible in code its a private. Its sort of old school, like Hungarian notation where you would prefix variable with type identifiers except they really mean something.
- romanovcode 8y agoWow, what a shitty syntax choice. Why not just stick with private/public (public by default)?
- gardaani 8y agoIf you think that the # syntax for private fields needs to be improved, then go to JS Committee's GitHub Issues and give feedback about it: https://github.com/tc39/proposal-class-fields/issues https://github.com/tc39/proposal-class-fields/issues There's at least three specifically about the #: https://github.com/tc39/proposal-class-fields/issues/177 https://github.com/tc39/proposal-class-fields/issues/177 https://github.com/tc39/proposal-class-fields/issues/149 https://github.com/tc39/proposal-class-fields/issues/149 https://github.com/tc39/proposal-class-fields/issues/142 https://github.com/tc39/proposal-class-fields/issues/142 Remember to be constructive or just give a thumbs up to comments you like.
- guntars 8y agoThere were hundreds of comments against this, both constructive and otherwise, alas the committee knows better and will do whatever they want.
- deleted 8y ago[deleted]
- Ajedi32 8y agoI think the water is somewhat muddied by the fact that the committee actually _does_ know better than the vast majority of people in opposition, as evidenced by the many uninformed comments in this thread suggesting alternatives that are objectively untenable. This is not to say that there aren't other viable solutions which would avoid the use of the current proposed syntax, but how do you weigh the advantages of avoiding a subjectively "ugly" syntax against the many other, much more concrete concerns that the TC39 has to evaluate when choosing a proposal? Should "the reflexive reaction of many devs when they first see the feature (without taking any time to try it out) is that the syntax is ugly" just be an automatic veto? If not, how strongly should that concern be weighted? Should an otherwise inferior proposal be accepted instead merely because the syntax is slightly prettier? Ultimately, I think you need to have a person or group of people in authority who will look at all available options and make an informed decision, even over the objections of the uninformed majority. Right now, the TC39 _is_ that informed authority.
- bad_user 8y agoThe difference with TypeScript is that TypeScript is able to statically disallow usage of such private values, at compile time. JavaScript is not static, you don't have a compiler that can protect against access, so you need info that is preserved at runtime. `#count` in this case is a different name than `count` and via this naming convention it's able to protect access. I don't get the point though, since people already use underscores as a soft mechanism for protecting access to private stuff and in a dynamic language like JS I don't think you need more. I also think the TC39 proposals are doing more harm then good and they should just stop changing JavaScript. Just leave it the way it is, thanks. "Promise" for example sucks, in spite of receiving early feedback, because TC39 is run by certain individuals that outright reject feedback that doesn't comply to their world view.
- deathanatos 8y agoWhy can't the public/private distinction, if denoted with a "private" keyword instead of a # be preserved and enforced at runtime? The difference between `private count` and `#count` is purely syntactical.
- __ryan__ 8y agoBecause the difference between `object.count` and `object.#count` is NOT purely syntactical. Information is needed at the call site to determine if it is a private field access compared to an object property access. This is because a private field, as defined in the spec, must not interfere with object properties.
- coldtea 8y ago>This is because a private field, as defined in the spec, must not interfere with object properties. Why couldn't it? E.g why not let it interfere...
- deathanatos 8y ago> Information is needed at the call site to determine if it is a private field access compared to an object property access. Is there? The object.#foo syntax tells you it is private, sure… but you still need know if access is permitted or not. For that, you need to look at some information on object and make a decision, but that information could also inform you as to whether or not the access is to a private field at all. Consider for object.foo, the following: 1. look up, internally in the interpreter, the class definition (recorded when parsing the class {} block) 2. Is .foo private? If no, behave "normally" 3. If yes, decide if access should be allowed. What about that doesn't work? If that does work, then, the # is pure syntax. One thing I'm curious about, since you seem adamant that this isn't syntax (particularly since the docs raise the peculiar "SyntaxError" — which implies determining at parse time whether a give obj.#thing is valid): is it only accessible through this.#foo? That is, if I have a class with a member function that takes another instance of the same class, is JavaScript going to tell me that I can't access private fields, despite those being on the current class? (This is fairly different from most languages, and makes some things impossible to express while keeping internals private.)
- skrebbel 8y agoI think that now that Edge is moving to Chromium, they can just push whatever shitty syntax they want and Firefox will be forced to follow suit. I wouldn't be surprised if this here is them giving that dominance a first shot. I'm sure they realize that developers will think it's horrible, but at the same time it's also not a problem. Nothing will break because of this, no company will be disadvantaged by it (barring Mozilla ofc). Perfect opportunity for testing the waters of a newly obtained monopoly position.
- johncolanduoni 8y agoI would be very surprised if a proposal that's at least over a year old (first commit in the GitHub repo was May 14, 2017) was part of some master plan for Google to test their dominance after Microsoft recently decided to kill Chakra. Ignoring timing, it's a pretty terrible way to test their monopoly position since it's obviously not going to help Google's business unless they plan to start manufacturing the "3" key on JavaScript developer keyboards. Why would Mozilla possibly spend the effort push back on this? TC39 comes up with things that are controversial (on GitHub issues at least) all the time.
- burtonator 8y agoWhat's the problem with public/private fields? Language design is hard but is there legitimate criticism besides subjective "I don't like this" ...
- z3t4 8y agoPeople coming to JS from other languages often ask how to create private variables, the answer is to use a local variable and closure. And with ES5 you can also use defineProperty