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

get/set/hasContext doesn't work in production code outside a component #429

Closed
ciscoheat opened this issue Sep 1, 2022 · 19 comments
Closed
Labels
bug Something isn't working

Comments

@ciscoheat
Copy link

ciscoheat commented Sep 1, 2022

Describe the bug

I'm trying to use the context functions in library code. They work when using both vite dev and vite preview when linking to the library directly. But when publishing to npm and including the library from there, an exception is thrown (see the logs).

Reproduction

  1. Create a new sveltekit todo app
  2. Add this code to +layout.svelte:
import { Flash } from "sveltekit-flash-message/client"
import { page } from '$app/stores'

const flash = new Flash(page)
const message = flash.message

Explanation

new Flash(page) calls hasContext in its constructor, throwing the error since hasContext cannot find current_component at that point. Code:
https://github.com/ciscoheat/sveltekit-flash-message/blob/c5198a35b724d53e0eab780e16d09c7c5c1499fb/src/lib/client.ts#L61-L66

Stackblitz reproduction

https://stackblitz.com/edit/sveltejs-kit-template-default-ask2u7?file=src%2Froutes%2F%2Blayout.svelte&terminal=dev

Logs

Error: Function called outside component initialization
    at get_current_component (file:///E:/Projects/TEST/svelte-next/node_modules/.pnpm/[email protected]/node_modules/svelte/internal/index.mjs:953:15)
    at hasContext (file:///E:/Projects/TEST/svelte-next/node_modules/.pnpm/[email protected]/node_modules/svelte/internal/index.mjs:995:12)
    at debugflash (file:///E:/Projects/TEST/svelte-next/node_modules/.pnpm/[email protected]/node_modules/sveltekit-flash-message/client.js:52:7)
    at file:///E:/Projects/TEST/svelte-next/.svelte-kit/output/server/entries/pages/_layout.svelte.js:16:3
    at Object.$$render (file:///E:/Projects/TEST/svelte-next/.svelte-kit/output/server/chunks/index.js:89:18)
    at file:///E:/Projects/TEST/svelte-next/.svelte-kit/output/server/index.js:36:97
    at $$render (file:///E:/Projects/TEST/svelte-next/.svelte-kit/output/server/chunks/index.js:89:18)
    at Object.render (file:///E:/Projects/TEST/svelte-next/.svelte-kit/output/server/chunks/index.js:97:20)
    at render_response (file:///E:/Projects/TEST/svelte-next/.svelte-kit/output/server/index.js:938:29)
    at processTicksAndRejections (node:internal/process/task_queues:96:5)

System Info

System:
    OS: Windows 10 10.0.19043
    CPU: (16) x64 Intel(R) Core(TM) i9-9900K CPU @ 3.60GHz
    Memory: 43.25 GB / 63.93 GB
  Binaries:
    Node: 16.16.0 - C:\Program Files\nodejs\node.EXE
    npm: 8.11.0 - C:\Program Files\nodejs\npm.CMD
  Browsers:
    Edge: Spartan (44.19041.1266.0), Chromium (104.0.1293.70)
    Internet Explorer: 11.0.19041.1566
  npmPackages:
    @sveltejs/adapter-auto: next => 1.0.0-next.71
    @sveltejs/kit: next => 1.0.0-next.460
    svelte: ^3.49.0 => 3.49.0
    vite: ^3.1.0-beta.1 => 3.1.0-beta.1

Severity

blocking all usage of SvelteKit

Additional Information

No response

@dummdidumm
Copy link
Member

This sounds like Vite does somehow create a separate Svelte runtime instance for the library. Your package is using @sveltejs/package which rules one source of errors out, which is good. I wonder if it's because your package doesn't contain Svelte components, yet it uses functions from it, so vite-plugin-svelte doesn't detect it's related to Svelte and doesn't handle it specifically or something. cc @dominikg @bluwy

@ciscoheat
Copy link
Author

If you need more information, or can point me in some direction for testing this in more depth, let me know!

@bluwy
Copy link
Member

bluwy commented Sep 1, 2022

I thought this was already fixed via #360. A workaround for now is to add this in vite.config.js:

	ssr: {
		noExternal: ['sveltekit-flash-message']
	}

@ciscoheat
Copy link
Author

ciscoheat commented Sep 1, 2022

Tested right away, confirmed that it works with that addition! Can this be fixed (added automatically/programatically?), so I don't have to ask library users to add this to their config, thereby increasing the friction?

@bluwy
Copy link
Member

bluwy commented Sep 4, 2022

It should be added automatically but it's not, which sounds like a bug. I'll transfer this over to vite-plugin-svelte to track there onwards.

@bluwy bluwy transferred this issue from sveltejs/kit Sep 4, 2022
@dominikg dominikg added the bug Something isn't working label Oct 2, 2022
@benmccann
Copy link
Member

When I run your example I don't see the log message you provided. Can you provide an actual reproduction of this issue?

@ciscoheat
Copy link
Author

Strange, I got it immediately using the latest sveltekit, both locally and on stackblitz. Here it is on stackblitz again: https://stackblitz.com/edit/sveltejs-kit-template-default-qwph8i?file=vite.config.js,src%2Froutes%2FHeader.svelte&terminal=dev

@pilcrowonpaper
Copy link

Having the same issue and the only way to resolve it is to add the package in noExternal. I remember external libraries being able to use contexts in July/August, not sure which version though.

@dummdidumm
Copy link
Member

dummdidumm commented Oct 28, 2022

Are you using the latest SvelteKit? What happens if you set vitePlugin.prebundleSvelteLibraries to false in svelte.config.js? I have a hunch this is related to prebundleSvelteLibraries being true by default now (PR: sveltejs/kit#7388).

@pilcrowonpaper
Copy link

pilcrowonpaper commented Oct 28, 2022

Is this correct?

const config = {
	kit: {
		adapter: adapter(),
		
	},
	vitePlugin: {
		prebundleSvelteLibraries: false
	}
};

It's still causing errors. Something interesting is that my package works inside a monorepo (imported via "lucia-auth": "workspace:*") when using pnpm, but breaks when using a published version using npm.

@dominikg
Copy link
Member

unfortunately prebundleSvelteLibraries is forced true in sveltekit right now as it is passed as an inline option. these have precedence over options specified in the config file.

https://github.com/sveltejs/kit/blob/edd815ed7bba7ab88461f9291f924c05a01d1328/packages/kit/src/exports/vite/index.js#L64
introduced here:
sveltejs/kit@e25074c#diff-beef34c36ed87d7835d0166655010910fba9949a6ef95042cb468d7d73423816R64

The only workaround for that i see is using something like pnpm patch to change the value provided inline in svelte-kit.

cc @benmccann

@benmccann
Copy link
Member

@pilcrowonpaper can you provide a repository with a reproduction?.

@dominikg
Copy link
Member

vite-plugin-svelte 1.2.0 improved how prebundleSvelteLibraries works and i cannot reproduce the stacktrace from the original post with that. Unfortunately i'm not sure what is supposed to happen instead of that error so i would appreciate if @ciscoheat could confirm it works now.

And @pilcrowonpaper if you still find issues with 1.2.0 and prebundleSvelteLibraries, a reproduction would be greatly appreciated. thanks (:

@ciscoheat
Copy link
Author

@dominikg I just tested it with the latest sveltekit, but still the same "Function called outside component initialization" problem. It works immediately when I add this to vite.config.js:

ssr: {
  noExternal: ['sveltekit-flash-message']
}

@dominikg
Copy link
Member

@ciscoheat looking at https://publint.bjornlu.com/[email protected] , there is no peerDependency on svelte.
This completely relies on the users project setup having deduplication for svelte and pulling it in anyways, potentially causing problems after svelte-4 release if the apis differ there. You should declare the peerDependency and vite-plugin-svelte is going to add the noExternal entry automatically.

This peerDependency declaration is not needed for ui libraries the only distribute .svelte source code, but it is needed if you make use of svelte apis in the library itself.

@dominikg
Copy link
Member

If that still doesn't help, please create an updated reproduction with step-by-step instructions on how to produce the error message (preferably from scratch with the sveltekit skeleton or vite+svelte template, not the sveltekit demo app)

@dominikg
Copy link
Member

update, seems you're using sveltekit directly too, so that also needs to be a peerDependency https://github.com/ciscoheat/sveltekit-flash-message/blob/master/src/lib/server.ts#L2

@ciscoheat
Copy link
Author

Thank you, the peer dependency fixes solved the issue. It's quite intricate, so I appreciate your help!

@pilcrowonpaper
Copy link

@dominikg
Just updated my library and can confirm the issue has been resolved by adding svelte to peerDependencies. Thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

6 participants