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

clarify onMount return functions when combined with non-synchronous handlers #5053

Merged
merged 4 commits into from
Jun 23, 2020

Conversation

antony
Copy link
Member

@antony antony commented Jun 23, 2020

Fixes #4927

Before submitting the PR, please make sure you do the following

  • It's really useful if your PR relates to an outstanding issue, so please reference it in your PR, or create an explanatory one for discussion. In many cases features are absent for a reason.
  • This message body should clearly illustrate what problems it solves. If there are related issues, remember to reference them.
  • Ideally, include a test that fails without this PR but passes with it. PRs will only be merged once they pass CI. (Remember to npm run lint!)

Tests

  • Run the tests tests with npm test or yarn test)

@@ -50,6 +50,8 @@ If a function is returned from `onMount`, it will be called when the component i
</script>
```

> Returning a function is only available for *synchronous* onMount functions. If an `async` function or `Promise` is passed to `onMount`, the returned function will **not** be called.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I do think we ought to clarify to people here how this works, but I'm not sold on this particular wording. Maybe instead just saying something about how 'the function passed to onMount needs to synchronously return a function for it to be called when the component is destroyed'? And then maybe a reminder that async functions always actually return promises.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Updated. It's very hard to get the wording right in a concise way without requiring the user to have a very solid grounding in asynchronous functions, anonymous functions, and Promise execution order.

I think I've covered it though.

@@ -50,6 +50,8 @@ If a function is returned from `onMount`, it will be called when the component i
</script>
```

> This behaviour will only work when the function passed to `onMount` *synchronously* returns a value. `async` functions always return a `Promise`, and as such cannot *synchronously* return a function.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we want to maybe say "returns a function" rather than "returns a value"? The only thing I'd worry with about that is the ends of the two sentences sounding a bit repetitive.

Copy link
Member Author

@antony antony Jun 23, 2020

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The reason I've said value in the first instance, is that I wouldn't consider this:

const myOnDestroy = function () { disposeStuff() } 
onMount(async () => new Promise(r => r(myOnDestroy))

as returning a function, more returning a value. I'd want to cover people literally using promises as return values within async functions.

The second sentence refers to a concrete example.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's fair. This seems like a good explanation then, and there'll at least be some place in the docs to point people to about this now.

@Conduitry Conduitry merged commit dc73b73 into sveltejs:master Jun 23, 2020
@antony antony deleted the feature/async-onmount-warning branch June 23, 2020 14:53
taylorzane pushed a commit to taylorzane/svelte that referenced this pull request Dec 17, 2020
@Leftium
Copy link

Leftium commented Mar 25, 2023

The note in the docs finally helped me solve the issue, but it would be nice if Svelte gave some warning when this happens.

This issue took 10+ hours to debug in my project. I did not realize new event handlers were being created without destroying the old ones. So events triggered both the old and new event handlers, causing weird behavior.

I almost attributed the weird behavior to something completely unrelated (my first fix related to Svelte stores turned out to be just a work-around).

This PR also seems like it would have helped: #8136

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

destroy function returned from onMount is not called if onMount is passed an async function
3 participants