5

There's such a thing as registry symbol in JS ES6 (found in this Mozilla article).

It's different from the Symbol() (relevant question on Stack Overflow), and can be obtained via Symbol.for(data).

Call Symbol.for(string). This accesses a set of existing symbols called the symbol registry. Unlike the unique symbols defined by Symbol(), symbols in the symbol registry are shared. If you call Symbol.for("cat") thirty times, it will return the same symbol each time. The registry is useful when multiple web pages, or multiple modules within the same web page, need to share a symbol.

I've been searching info on this topic, I have read similar questions on Stack Overflow (there's What is 'global symbol registry'? but it doesn't cover the question - why use registry symbols instead of strings).

Although it seems that I have gotten (almost) everything about the unique symbols defined with Symbol(), the registry symbols (Symbol.for()) just don't make much sense at all for me.

I mean, look at the examples there:

Symbol.for('foo'); // create a new global symbol
Symbol.for('foo'); // retrieve the already created symbol

// Same global symbol, but not locally
Symbol.for('bar') === Symbol.for('bar'); // true

//ADDED BY ME
Symbol.for('far') === Symbol.for('bar'); // false

// The key is also used as the description
var sym = Symbol.for('mario');
sym.toString(); // "Symbol(mario)"

As far as I understand, the strings provide exact same functionality, don't they?

All those articles about saving/sharing symbols are unclear since saving and sharing is (at least seems to be!) essentially comparing the strings which are used to build the corresponding symbols.

What's the purpose of the registry symbols and how using them is different from using plain strings (i.e., I would like to see an example which I have failed to find)?

nicael
  • 18,550
  • 13
  • 57
  • 90
  • 1
    Does [this post](https://stackoverflow.com/a/30985314/1048572) answer your question? (The topic is linked from the one you already found) – Bergi Apr 02 '18 at 21:34
  • @Bergi not really - "the non-enumerability" is already covered by the corresponding feature `Object.defineProperty`, and the concept of sharing is still unclear. I don't even see the being useful at least as much as localStorage, as they are not appearing to save anything. – nicael Apr 02 '18 at 21:38
  • The fact of not colliding with the string properties is also not useful that much, @Bergi, (at least it seems so) since they can collide between each other anyway. – nicael Apr 02 '18 at 21:40
  • I don't understand that since there is nothing in `symbol.for` that represents it other than it's string value. – nicael Apr 02 '18 at 21:44
  • 3
    Not colliding with strings is very important when objects are used as dictionaries (like a `Map`) and also for "normal" properties in legacy code. Have a look at the stuff this enabled for the builtin symbols like `Symbol.iterator` (which are also shared between realms). `Symbol.for` is making the same things possible for user code. – Bergi Apr 02 '18 at 21:49
  • I agree that there is no large advantage over "unique-enough" property names, but I think it still is a bit of an advantage. (Also I'd guess it allows for better optimisations than weird property names). – Bergi Apr 02 '18 at 21:52
  • 3
    The purpose is what they are good for - app-wide tokens that are non-enumerable by nature (no defineProperty), don't need magic property names like `__foo__` and don't pollute global namespace (except Symbol itself). It's exactly like was said above - you can create custom global symbols, similar to Symbol.iterator. I believe https://stackoverflow.com/a/30985314/1048572 covers that. *since they can collide between each other anyway* - if there's a possibility that they can collide, it's not a use case for Symbol.for, use Symbol() instead. If the app uses modules, use Symbol() and imports. – Estus Flask Apr 02 '18 at 22:22

0 Answers0