-
-
Notifications
You must be signed in to change notification settings - Fork 204
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
Discussion: How can we type the events supported by a component #424
Comments
The reason why this cannot be implemented easily is that it's a lot harder to collect all possible events than to collect the props. That's also the reason why autocompletion does not work because these are for props. Looking under the hood it's that props are implemented through jsx props. Events are not because of the limitations of collecting them. If the user would explicitly type them this could be changed. We cannot mark the dispatched events as "this does not conform to the definition" though because of the challenges mentioned. Having a reserved interface is likely the way forward. We have thought about this before in the context of generic props. Reserved interface names could be Related #304 |
Getting autocompletion with Two solutions arise from these constraints:
Getting " |
Once sveltejs/svelte#5260 is released we can try to update |
This adds the possibility to use a reserved interface name `ComponentEvents` and define all possible events within it. Also adds autocompletion for these events. Also disables autocompletions from HTMLPlugin on component tags. sveltejs#424 sveltejs#304
#424 - now tries to detect event names from script/template if no typings given - supports typed createEventDispatcher
You can now take advantage of the const dispatch = createEventDispatcher<{foo: string; bar: boolean}>(); You get strong typing for
You'll also get much better autocompletion for events now. Note however that you are still allowed to listen to other events, so type safety in the sense of "only listen to events defined through Related docs: https://github.com/sveltejs/language-tools/blob/master/docs/preprocessors/typescript.md#typing-component-events |
Any ideas on why some listening events for Example: // Component Foo
const dispatchFoo = createEventDispatcher<{foo: string; bar: boolean}>();
const dispatchBar = createEventDispatcher<{bar: string; baz: string}>();
// Component Bar
// e is CustomEvent<any>
on:foo="{(e) => handleFoo(e.detail.bar)}"
// e is CustomEvent<{baz: string}>
on:bar="{(e) => handleBar(e.detail.bar)}" The typescript compiler catches this as expected. Changing the order produces different results. if the // Component Foo
const dispatchBar = createEventDispatcher<{bar: string; baz: string}>();
const dispatchFoo = createEventDispatcher<{foo: string; bar: boolean}>();
// Component Bar
// e is CustomEvent<{bar: boolean}>
on:foo="{(e) => handleFoo(e.detail.bar)}"
// e is CustomEvent<any>
on:bar="{(e) => handleBar(e.detail.bar)}" The typescript compiler does not catch the error since the type is now |
$$Events lets the user define all events that a component can dispatch. If createEventDispatcher is not typed, the $$Events definition is added to it under the hood for type checking. strictEvents can be used when the user is sure that there are no other events besides the one from createEventDispatcher and forwarded events - this removes the custom event fallback typing. sveltejs#442 sveltejs#424 sveltejs/rfcs#38
$$Events lets the user define all events that a component can dispatch. If createEventDispatcher is not typed, the $$Events definition is added to it under the hood for type checking. strictEvents can be used when the user is sure that there are no other events besides the one from createEventDispatcher and forwarded events - this removes the custom event fallback typing. #442 #424 sveltejs/rfcs#38
Experimental support for typing events is now available. See the RFC on how to use it. Please provide feedback in #442 |
The goal is to easily catch typos and help the discovery of all possible events dispatched by a component. After all, there is no reason why the inputs (props) can have a strong contract but the outputs (events) don't. In fact, it's even more important than for props, because the dispatching can occur about anywhere in the file, whereas props are usually neatly bunched together are the top.
Right now I can type
on:qoidfoqidjoiqsjd
just fine.Flex, which also had its compiler used custom annotations for this: https://github.com/apache/flex-sdk/blob/master/frameworks/projects/mx/src/mx/core/Container.as#L97
Perhaps we could have a special, reserved convention like
export type Events = {name: 'eventA', data: number} | ...
Having the TSDoc carry over on the consumer side tooltip would be the icing on the cake.
The text was updated successfully, but these errors were encountered: