Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Refactor settled to avoid triggering a new run-loop. #263

Merged

Conversation

rwjblue
Copy link
Member

@rwjblue rwjblue commented Dec 13, 2017

The code that was added to ensure that all promise.then or promise.catch callbacks are "flushed" before decrementing the counter (which fixed a number of bugs where settled would accidentally become true before the promise callbacks themselves could have a chance to run), caused an issue when using the legacy moduleForComponent system to render a template that itself kicked off an async request.

Prior to the changes made in this commit, when rendering would kick off async (e.g. rendering a {{parent.child}} style path referencing an ember-data async relationship) there would already be an existing Ember.run.backburner.currentInstance (which was created by the RSVP.Promise.resolve().then(...) being removed in this commit) which ultimately forced us down the path that meant adapter.asyncStart() / adapter.asyncEnd() would not be called (see here).

This change works around that (admittedly niche) scenario by always assuming that a Promise.resolve() will execute before the next setTimeout(cb, 0) (which is true in both Ember.RSVP land and native Promise land).

Fixes ember-cli/ember-cli-mocha#233
Fixes #259

The code that was added to ensure that all `promise.then` or
`promise.catch` callbacks are "flushed" before decrementing the counter
(which fixed a number of bugs where `settled` would accidentally become
`true` before the promise callbacks themselves could have a chance to
run), caused an issue when using the legacy `moduleForComponent` system
to render a template that itself kicked off an async request.

Prior to the changes made in this commit, when rendering would kick off
async (e.g. rendering a `{{parent.child}}` style path referencing an
ember-data async relationship) there would _already_ be an existing
`Ember.run.backburner.currentInstance` (which was created by the
`RSVP.Promise.resolve().then(...)` being removed in this commit) which
ultimately forced us down the path that meant `adapter.asyncStart()` /
`adapter.asyncEnd()` would not be called ([see
here](https://github.com/emberjs/ember.js/blob/v2.17.0/packages/ember-testing/lib/ext/rsvp.js#L11)).

This change works around that (admittedly niche) scenario by always
assuming that a `Promise.resolve()` will execute before the next
`setTimeout(cb, 0)` (which is true in both Ember.RSVP land and native
Promise land).
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
1 participant