diff --git a/packages/svelte/src/compiler/compile/compiler_warnings.js b/packages/svelte/src/compiler/compile/compiler_warnings.js
index acd9409734e6..d5ca047edb87 100644
--- a/packages/svelte/src/compiler/compile/compiler_warnings.js
+++ b/packages/svelte/src/compiler/compile/compiler_warnings.js
@@ -306,5 +306,12 @@ export default {
code: 'illegal-attribute-character',
message:
"Attributes should not contain ':' characters to prevent ambiguity with Svelte directives"
- }
+ },
+ binding_custom_element: /**
+ * @param {string} element
+ * @param {string} binding
+ */ (element, binding) => ({
+ code: 'binding-custom-element',
+ message: `Binding on custom element <${element}> is not checked. You need to ensure '${binding}' is a valid property.`
+ })
};
diff --git a/packages/svelte/src/compiler/compile/nodes/Element.js b/packages/svelte/src/compiler/compile/nodes/Element.js
index 248f831f66ea..387b7b92ee34 100644
--- a/packages/svelte/src/compiler/compile/nodes/Element.js
+++ b/packages/svelte/src/compiler/compile/nodes/Element.js
@@ -1100,7 +1100,12 @@ export default class Element extends Node {
};
this.bindings.forEach((binding) => {
const { name } = binding;
- if (name === 'value') {
+
+ //custom elements (i.e. web components) can be bound to any attribute, we simply emit a warning
+ //to identify a custom element, we check if the element name contains a hyphen
+ if (this.name.includes('-') && name !== 'this') {
+ return component.warn(binding, compiler_warnings.binding_custom_element(this.name, name));
+ } else if (name === 'value') {
if (this.name !== 'input' && this.name !== 'textarea' && this.name !== 'select') {
return component.error(
binding,
diff --git a/packages/svelte/test/validator/samples/binding-custom-element/errors.json b/packages/svelte/test/validator/samples/binding-custom-element/errors.json
new file mode 100644
index 000000000000..fe51488c7066
--- /dev/null
+++ b/packages/svelte/test/validator/samples/binding-custom-element/errors.json
@@ -0,0 +1 @@
+[]
diff --git a/packages/svelte/test/validator/samples/binding-custom-element/input.svelte b/packages/svelte/test/validator/samples/binding-custom-element/input.svelte
new file mode 100644
index 000000000000..c0b64b87f679
--- /dev/null
+++ b/packages/svelte/test/validator/samples/binding-custom-element/input.svelte
@@ -0,0 +1,6 @@
+
+
+
\ No newline at end of file
diff --git a/packages/svelte/test/validator/samples/binding-custom-element/warnings.json b/packages/svelte/test/validator/samples/binding-custom-element/warnings.json
new file mode 100644
index 000000000000..1021d75b66d1
--- /dev/null
+++ b/packages/svelte/test/validator/samples/binding-custom-element/warnings.json
@@ -0,0 +1,14 @@
+[
+ {
+ "code": "binding-custom-element",
+ "message": "Binding on custom element is not checked. You need to ensure 'value' is a valid property.",
+ "start": {
+ "line": 6,
+ "column": 12
+ },
+ "end": {
+ "line": 6,
+ "column": 32
+ }
+ }
+]
diff --git a/packages/svelte/test/validator/samples/binding-dimensions-svg/errors.json b/packages/svelte/test/validator/samples/binding-dimensions-svg/errors.json
index ca4b4515b8e5..3b1fc55c307f 100644
--- a/packages/svelte/test/validator/samples/binding-dimensions-svg/errors.json
+++ b/packages/svelte/test/validator/samples/binding-dimensions-svg/errors.json
@@ -8,7 +8,7 @@
},
"end": {
"line": 5,
- "column": 21
+ "column": 25
}
}
]