Thus, I can point directly to E and friends as leading us to make such a successful, _correct_, asynchronous task engine.
It's funny to think about now. Promises and coroutines and promise pipelining and async are now well-explored, but at the time there wasn't much prior art to draw from, and everyone was figuring it out as they went. Do you synchronously block on futures? Should .then calls run on the calling thread if data was already available? How does cancellation work?
Once you have answers to those questions, you reach the higher-level ones: how do you structure your program so that asynchronous components can communicate? How do you unit test these interactions? What abstractions avoid needing to unit test every possible sequence of events?
We did a pretty good job and I feel blessed that we stumbled upon the E papers, leading us to create abstractions that stood the test of time.
Thanks Mark!