diff --git a/src/component/component.ts b/src/component/component.ts index 7fcfe885..0a66b4b4 100644 --- a/src/component/component.ts +++ b/src/component/component.ts @@ -10,6 +10,7 @@ interface StaticComponentProperties { template: string; defaultProps?: any; props?: any; + components?: { [componentName: string]: ComponentConstructor }; } export type ComponentConstructor

= (new ( diff --git a/src/component/component_node.ts b/src/component/component_node.ts index ba3ab568..b990d7e9 100644 --- a/src/component/component_node.ts +++ b/src/component/component_node.ts @@ -107,6 +107,8 @@ export function component

( C = parent.constructor.components[name as any]; if (!C) { throw new Error(`Cannot find the definition of component "${name}"`); + } else if (!(C.prototype instanceof Component)) { + throw new Error(`"${name}" is not a Component. It must inherit from the Component class`); } } node = new ComponentNode(C, props, ctx.app, ctx, key); diff --git a/tests/components/__snapshots__/error_handling.test.ts.snap b/tests/components/__snapshots__/error_handling.test.ts.snap index 1c96ad70..bf4ce897 100644 --- a/tests/components/__snapshots__/error_handling.test.ts.snap +++ b/tests/components/__snapshots__/error_handling.test.ts.snap @@ -1,5 +1,16 @@ // Jest Snapshot v1, https://goo.gl/fbAQLP +exports[`basics display a nice error if a component is not a component 1`] = ` +"function anonymous(bdom, helpers +) { + let { text, createBlock, list, multi, html, toggler, component, comment } = bdom; + + return function template(ctx, node, key = \\"\\") { + return component(\`SomeComponent\`, {}, key + \`__1\`, node, ctx); + } +}" +`; + exports[`basics display a nice error if it cannot find component (in dev mode) 1`] = ` "function anonymous(bdom, helpers ) { diff --git a/tests/components/error_handling.test.ts b/tests/components/error_handling.test.ts index 659b099d..d1d2aec1 100644 --- a/tests/components/error_handling.test.ts +++ b/tests/components/error_handling.test.ts @@ -102,6 +102,25 @@ describe("basics", () => { expect(mockConsoleWarn).toBeCalledTimes(1); }); + test("display a nice error if a component is not a component", async () => { + function notAComponentConstructor() {} + class Parent extends Component { + static template = xml``; + static components = { SomeComponent: notAComponentConstructor }; + } + let error: Error; + try { + // @ts-expect-error + await mount(Parent, fixture); + } catch (e) { + error = e as Error; + } + expect(error!).toBeDefined(); + expect(error!.message).toBe( + '"SomeComponent" is not a Component. It must inherit from the Component class' + ); + }); + test("simple catchError", async () => { class Boom extends Component { static template = xml`

`;