it('should notify about delete button',async()=>{consttodo={id:'e2bb892a-844a-47fb-a2b3-47f491af9d88',name:'Demo',completed:false};const{component,getByTestId,container}=render(Item,{todo});letwasCalled=false;component.$on("remove",()=>{wasCalled=true;});fireEvent.click(getByTestId('todo-remove'));expect(wasCalled).toBeTruthy();});
Whether or not you’d want to do this is another question. Svelte gives you a lot of rope... dispatch is an example of that. That fact that testing is hard is a sign that there may be a better approach with the design.
(Note--a better approach with the design, not a better approach with testing. An important difference!)
The question in my mind is does Item need to know that it exists within a List? It feels like List and Item can’t exist without one another, and each has a lot of knowledge about the other one. Is there a way to reduce the coupling? For example --- can remove functionality be moved entirely to List somehow?
You could also use stores to introduce shared state between the two, and remove the need for dispatch entirely.
In my opinion events (or function props) and props mean loose coupling as they only know each others interface and shared state is a strong coupling. Why do you think they know about each other? Yes, they know each other's interface, but it's necessary to communicate.
With other frameworks (Vue, Angular, React) I've found it easy to test events or function props, what I was missing is the $on method.
Item knows about a remove operation, which means it "knows" that it exists in some kind of container (List or otherwise).
Not saying I know of a better solution or that I wouldn’t write it that way myself... just that I’m a little wary of dispatch and I’d keep my eyes open for opportunities to design it differently.
Another point: unless I’m mistaken, $on is part of the internal Svelte API so if you use it, you have to be prepared to figure out a new solution if/when the maintainers break this one 🤣
Not sure about getContext. I vaguely recall looking into it and figuring out that getContext expects to be called as part of a render cycle of a component tree, which you can’t easily fake.
If you’re comfortable with relying on internal APIs like $on then one thing you could do is use the tutorial view for context (svelte.dev/tutorial/context-api). Choose JS output and explore the JS code that Svelte products for your component. Dig through to learn how setContext and getContext work. It might give you a solution. Failing that, use the Svelte source on GitHub. Let me know if you figure something out--I’d be interested to know.
For further actions, you may consider blocking this person and/or reporting abuse
We're a place where coders share, stay up-to-date and grow their careers.
Hey Gábor,
You can do it by using
component.$on
:Whether or not you’d want to do this is another question. Svelte gives you a lot of rope...
dispatch
is an example of that. That fact that testing is hard is a sign that there may be a better approach with the design.(Note--a better approach with the design, not a better approach with testing. An important difference!)
The question in my mind is does
Item
need to know that it exists within aList
? It feels likeList
andItem
can’t exist without one another, and each has a lot of knowledge about the other one. Is there a way to reduce the coupling? For example --- can remove functionality be moved entirely toList
somehow?You could also use stores to introduce shared state between the two, and remove the need for
dispatch
entirely.Let me know your thoughts :)
Thanks for the example, I'll try it out tomorrow.
In my opinion events (or function props) and props mean loose coupling as they only know each others interface and shared state is a strong coupling. Why do you think they know about each other? Yes, they know each other's interface, but it's necessary to communicate.
With other frameworks (Vue, Angular, React) I've found it easy to test events or function props, what I was missing is the
$on
method.Item
knows about aremove
operation, which means it "knows" that it exists in some kind of container (List
or otherwise).Not saying I know of a better solution or that I wouldn’t write it that way myself... just that I’m a little wary of
dispatch
and I’d keep my eyes open for opportunities to design it differently.Another point: unless I’m mistaken,
$on
is part of the internal Svelte API so if you use it, you have to be prepared to figure out a new solution if/when the maintainers break this one 🤣I've tried it out, works like a charm!
One more question: is it possible to test a component with
getContext
without a wrapper component?Here is an example: github.com/blacksonic/todoapp-svel...
Glad to hear it worked! 🎉
Not sure about
getContext
. I vaguely recall looking into it and figuring out thatgetContext
expects to be called as part of a render cycle of a component tree, which you can’t easily fake.If you’re comfortable with relying on internal APIs like
$on
then one thing you could do is use the tutorial view for context (svelte.dev/tutorial/context-api). ChooseJS output
and explore the JS code that Svelte products for your component. Dig through to learn howsetContext
andgetContext
work. It might give you a solution. Failing that, use the Svelte source on GitHub. Let me know if you figure something out--I’d be interested to know.