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

When using Ionic from CDN: SvelteKit doesn't work with Ionic while Svelte works well. #5143

Closed
MarianDabrowski opened this issue Jun 2, 2022 · 4 comments

Comments

@MarianDabrowski
Copy link

Describe the bug

I have tried sveltekit and I love it. The performance is awesome. So I have decided to migrate my site from (Next.js, React.js, Ionic) to (SvelteKit, Svelte, Ionic).
Ionic provides the styling and components that are the building blocks of my app.
Next.js provides SSR and SSG.

Even though Ionic team provide React support, I decided to move my project to Svelte (the reason are well known).

I have tried Svelte and it worked well with Ionic (Please check it even here: svelte dev example)

So Svelte works well with Ionic and the last thing I need is SSR or SSG & SSG which svelte kit provides.

Unfortunately, Sveltekit does not handle Ionic.
image

When I refresh the page, the button (ion-button) is there and after it disappears .

Reproduction

Please clone the repo repo

npm install

npm run dev

Try refreshing the page to see the behaviour.

Logs

Error with Permissions-Policy header: Origin trial controlled feature not enabled: 'interest-cohort'.
client.ts:16 [vite] connecting...
client.ts:53 [vite] connected.

System Info

System:
    OS: macOS 12.0.1
    CPU: (12) x64 Intel(R) Core(TM) i7-9750H CPU @ 2.60GHz
    Memory: 72.97 MB / 16.00 GB
    Shell: 5.8 - /bin/zsh
  Binaries:
    Node: 17.8.0 - /usr/local/bin/node
    npm: 8.5.5 - /usr/local/bin/npm
  Browsers:
    Brave Browser: 99.1.36.119
    Chrome: 102.0.5005.61
    Firefox: 100.0
    Safari: 15.1
  npmPackages:
    @sveltejs/adapter-auto: 1.0.0-next.50 => 1.0.0-next.50 
    @sveltejs/kit: 1.0.0-next.347 => 1.0.0-next.347 
    svelte: 3.48.0 => 3.48.0

Severity

blocking all usage of SvelteKit

Additional Information

In app.html is Ionic CDN included.

There is version 6.1.8 used in the example. Version 5.9.4 in commented out purposely. If you need to check a previous major version you can try it.

@benmccann
Copy link
Member

Duplicate of #2272

@benmccann benmccann marked this as a duplicate of #2272 Jun 7, 2022
@MarianDabrowski
Copy link
Author

@benmccann can you provide any context on this one. I have searched the discord channel, yet have not found anything that would point to this issue.

@MathiasWP
Copy link
Contributor

@benmccann can you provide any context on this one. I have searched the discord channel, yet have not found anything that would point to this issue.

Reason:

Hydration is removing them because they're not rendered by Svelte. Svelte expects to control the DOM. This isn't really a bug, but a usage issue, so would probably be a better question for Discord. I haven't tried to do something like what you're attempting before, so you'd be more likely to find someone with ideas on Discord

Originally posted by @benmccann in #2272 (comment)

One solution:

svelte starter template doesn't do SSR or hydration. you can turn SSR off in SvelteKit if you want behavior more similar to svelte starter template

Originally posted by @benmccann in #2272 (comment)

@Rich-Harris
Copy link
Member

This is happening because Ionic adds a bunch of classnames when the custom element is upgraded. The markup says this...

<ion-button>Click me</ion-button>

...but when the element upgrades, it looks like this in the DOM:

<ion-button class="md button button-solid ion-activatable ion-focusable hydrated">Click me</ion-button>

Svelte's job (indeed, any framework's job) during hydration is to ensure that the DOM at the end of the process matches the authored components. When custom elements start futzing around with the markup willy-nilly, all bets are off. This is a bug in Ionic: their elements are incompatible with frameworks that use hydration. Those classnames are implementation details that should not be visible in light DOM (though I suspect the reason they are visible is because putting that stuff in shadow DOM would make it prohibitively difficult to share common styles between elements — one of the reasons I generally advise people not to use shadow DOM).

Unfortunately there's very little SvelteKit can do about this. Your options are:

  1. Don't load ionic.esm.js until you know the page has hydrated (the easiest way to do this, until we get round to adding some sort of hooks/client.js, would be to create a script inside onMount in your root __layout)
  2. Don't use SSR (so that there's no hydration step). This could also mean 'use Svelte without SvelteKit'
  3. Use a custom element library that works with hydration

As an aside, I'd strongly recommend against loading ionic.esm.js from a public CDN. Your site will be more reliable and performant if you self-host.

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

4 participants