1 for 1 so far on the posting every day thing.
Yesterday I ran into some pain with my code that I thought was interesting, so today I'll explain how that played out.
class Smarts { then(fn) { fn("Oh no.") } async self() { return this } } const smarts = new Smarts() const result = await smarts.self() // result -> "Oh no."
And now we have a problem. Async functions return a promise which resolves to their return value. When a promise resolves to a promise, the first promise actually keeps waiting for the second promise and resolves to the value of the second promise. And finally, since JavaScript has no types, everything with a .then
looks like a promise. (I'm sure there's a Maslow's Hammer reference that I could make here.)
Instead of the async method resolving to this
, it resolves to the value of whatever this.then
sends to its callback. Because the class looks like a promise.
In this case, instead of .self()
resolving to the same object, as one might expect from the method implementation, it resolves to "Oh no."
.
The solution to this problem? Make your class not look like a promise, or everyone will treat it as one.
This stumped me for an annoyingly long time, because of course my code was not as simple as just a class with then
and self
methods in isolation.
Unrelated to code, the photo of the day is of Sub-Zero Scuffle, a fighting game tournament that I attended last weekend (7-8 March). The events were Smash Ultimate, Tekken 7, Samurai Shodown, Street Fighter 5, Marvel vs Capcom, Mortal Kombat 11, Soul Calibre 6, and Power Rangers: Battle for the Grid. It was a really good time.
— Cadence