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

getContext on a child component returns undefined when HMR is triggered with context in the parent's context="module" exports #8655

Open
space-nuko opened this issue May 28, 2023 · 3 comments

Comments

@space-nuko
Copy link

Describe the bug

I tried to edit a child component that uses getContext where the context key is imported from the parent svelte component's context="module". When I edit the child component and save, HMR is triggered and I get an error in the console. I have to refresh the page to be able to keep working

It's just getContext returning undefined. But I do setContext in the parent and it works until the HMR happens.

Reproduction

https://github.com/space-nuko/svelte-context-hmr-issue

  1. Click the buttons a few times
  2. Edit the child component that's currently being displayed and save
  3. Watch the console for errors

Logs

One.svelte?t=1685287937140:91 Uncaught (in promise) TypeError: Cannot destructure property 'func' of 'getContext(...)' as it is undefined.
    at instance (One.svelte?t=1685287937140:91:10)
    at init (chunk-UVEMIUTC.js?v=45af3e07:1890:23)
    at new One (One.svelte?t=1685287937140:105:3)
    at createProxiedComponent (svelte-hooks.js?v=45af3e07:341:9)
    at new ProxyComponent (proxy.js?v=45af3e07:242:7)
    at new Proxy<One> (proxy.js?v=45af3e07:349:11)
    at Array.create_if_block (Child.svelte?t=1685287888134:114:8)
    at Object.update [as p] (Child.svelte?t=1685287888134:198:98)
    at update (chunk-UVEMIUTC.js?v=45af3e07:1140:32)
    at flush (chunk-UVEMIUTC.js?v=45af3e07:1106:9)

System Info

Version 110.0.5481.177 (Official Build, ungoogled-chromium) (64-bit)

devDependencies:
@fontsource/fira-mono 4.5.10
@neoconfetti/svelte 1.0.0
@sveltejs/adapter-auto 2.1.0
@sveltejs/kit 1.20.0
@types/cookie 0.5.1
svelte 3.59.1
svelte-check 3.4.3
tslib 2.5.2
typescript 5.0.4
vite 4.3.9

Severity

annoyance

@rixo
Copy link
Contributor

rixo commented May 30, 2023

You're pushing the HMR engine to its limits with this kind of cyclical dependencies.

I am not sure this can be fixed in a reasonable way on the Svelte side. On Vite side, it is debatable whether this could / should be fixed, or if it is like it is. The only thing I'm sure for now is that we're in a pretty gray area 😅

Currently, you can work around this limitation either by explicitly breaking the import loop, by extracting the context=module part to its own module:

Parent.js

export const CONTEXT = {}

This is probably the cleanest and more solid approach.

Alternatively, you can make your precise use case work with a sprinkle of HMR incantations:

<script context="module" lang="ts">
-  export const CONTEXT = {}
+  export const CONTEXT = import.meta.hot?.data?.CONTEXT || {}
+  if (import.meta.hot?.data) {
+    import.meta.hot.data.CONTEXT = CONTEXT
+  }
</script>

(This makes sure the identity of your CONTEXT object is preserved across HMR updates.)

@space-nuko
Copy link
Author

Understood but I wasn't aware it was an HMR limitation since the repro was so minimal. Thanks for the example by the way, I think it would be worth putting in the docs for getContext/setContext

@rixo
Copy link
Contributor

rixo commented May 31, 2023

After further investigation, it turns out it is a known bug in Vite, and it is in the process of being fixed in this PR. So I think we just need to wait it out.

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

No branches or pull requests

2 participants