Skip to content

Conversation

dummdidumm
Copy link
Member

@dummdidumm dummdidumm commented Apr 6, 2023

This is an overhaul of custom elements in Svelte. Instead of compiling to a custom element class, the Svelte component class is mostly preserved as-is. Instead a wrapper is introduced which wraps a Svelte component constructor and returns a HTML element constructor. This has a couple of advantages:

Breaking changes:

Wrapped Svelte component now stays as a regular Svelte component (invokeing it like before with new Component({ target: ..}) won't create a custom element). Its custom element constructor is now a static property named element on the class (Component.element) and should be regularly invoked through setting it in the html.

- const component = new Component({ target: someDiv, props: { foo: 'bar' } });
+ const component = document.createElement('custom-element-tag');
+ component.foo = 'bar';
+ someDiv.appendChild(component);
// or, if you have no attributes or only have simple string attributes:
+ someDiv.innerHTML = '<custom-element-tag foo="bar"></custom-element-tag>';

The timing of mount/destroy/update is different. Mount/destroy/updating a prop all happen after a tick, so shadowRoot.innerHTML won't immediately reflect the change (Lit does this too). If you rely on it, you need to await a promise for example:

const component = someDiv.innerHTML = '<custom-element-tag foo="bar"></custom-element-tag>';
+ await Promise.resolve();
someDiv.querySelector('custom-element-tag').shadowRoot.querySelector('div');
// ...

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

  • It's really useful if your PR references an issue where it is discussed ahead of time. In many cases, features are absent for a reason. For large changes, please create an RFC: https://github.com/sveltejs/rfcs
  • Prefix your PR title with feat:, fix:, chore:, or docs:.
  • This message body should clearly illustrate what problems it solves.
  • Ideally, include a test that fails without this PR but passes with it.

Tests

  • Run the tests with npm test and lint the project with npm run lint

@dummdidumm dummdidumm added this to the 4.x milestone Apr 6, 2023
@vercel
Copy link

vercel bot commented Apr 6, 2023

@dummdidumm is attempting to deploy a commit to the Svelte Team on Vercel.

A member of the Team first needs to authorize it.

prop.key.name === 'reflect' && typeof prop.value.value !== 'boolean' ||
prop.key.name === 'attribute' && typeof prop.value.value !== 'string'
) {
return error();
Copy link
Member

Choose a reason for hiding this comment

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

maybe give specific explanation of why it failed, eg

'cePropsDefinition' must be a statically analyzable object literal of the form '{ prop: { attribute?: string; type?: 'String' | 'Boolean' | 'Number' | 'Array' | 'Object', reflect?: boolean; } }', found key 'xxx'
'cePropsDefinition' must be a statically analyzable object literal of the form '{ prop: { attribute?: string; type?: 'String' | 'Boolean' | 'Number' | 'Array' | 'Object', reflect?: boolean; } }', the value of reflect is not boolean

@dummdidumm dummdidumm changed the base branch from master to version-4 April 11, 2023 13:19
xxkl1 and others added 11 commits April 11, 2023 15:20
Instead of "both", which doesn't make sense at that point.
- upgrade to TypeScript 5
- upgrade @ampproject/remapping
- remove obsolete workarounds

---------

Co-authored-by: Simon Holthausen <[email protected]>
bump to rollup 3. Includes reworking the "treat those imports as external" a bit so that Rollup builds correctly but doesn't bundle some of the (now relative) imports

---------

Co-authored-by: Simon Holthausen <[email protected]>
This was referenced Jul 21, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment