Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
169 views
in Technique[技术] by (71.8m points)

javascript - Why are await and async valid variable names?

I was experimenting with how / is interpreted when around different keywords and operators, and found that the following syntax is perfectly legal:

// awaiting something that isn't a Promise is fine, it's just strange to do:
const foo = await /barbaz/
myFn()
See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Reserved keywords cannot be used as identifiers (variable names). Unlike most other special Javascript words (like those listed in the question, let, finally, ...), await is not a reserved keyword, so using it as a variable name does not throw a SyntaxError. Why wasn't it made into a reserved keyword when the new syntax came out?

Backwards compatibility

Back in 2011, when ES5 was still a relatively new thing, code that used await (and async) as variable names was perfectly valid, so you may have seen something like this on a couple sites:

function timeout(ms) {
  var await = $.Deferred();
  setTimeout(await.resolve, ms);
  return await.promise();
};

The choice of that variable name may seem odd, but there was nothing wrong with it. await and async have never been reserved keywords - if the writers of the ES2017 specification made await into a reserved keyword, and browsers implemented that change, people visiting those older sites on newer browsers would not be able to use those sites; they would likely be broken.

So perhaps if they were made into reserved keywords, a few sites which chose a peculiar variable name wouldn't work properly - why should the existence of those sites permanently affect the future evolution of ECMAscript and result in confusing code like in the question?

Because browsers will refuse to implement a feature which breaks existing sites. If a user finds that a site does not work on one browser, but works on another, that will incentivize them to switch browsers - the maker of the first browser would not want that, because that would mean less market share for them, even if it's a feature which makes the language more consistent and understandable. In addition, the editors of the specification do not want to add something that will never be implemented (or will only be implemented sporadically), because then the specification would lose some of its status as a standard - contrary to its main goal.

You could see these interactions in action with Array.prototype.flatten and Array.prototype.contains - when browsers started shipping them, it was found that they broke a few existing sites due to name conflicts, so the browsers backed out of the implementation, and the specification had to be tweaked (the methods were renamed to .flat and .includes).


There actually is a situation in which await cannot be used as an identifier, which is inside of ES6 modules:

<script type="module">
  const await = 'Does it work?';
</script>

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...