[teatest] Testing a model with goroutines
Closed this issue · 6 comments
Hi,
Inside my model I have a goroutine fired after the user chooses a file in a list. This goroutine uses Program.Send()
to communicate with the program. The problem I'm facing is that i can fake this program and build my model, but there is no way to check the results since the program my goroutine is communicating with is different from that fired by teatest.NewTestModel()
.
I don't have a specific solution, but it would be nice if I could run NewTestModel
more granulary, maybe some new TestOption to specify the program to run.
Thanks for the good work, teatest really improves the bubbletea apps testability.
hey, not sure I understand your problem, can you provide a minimal reproducible?
type Cli struct {
p *tea.Program
str string
}
func (c *Cli) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
switch msg := msg.(type) {
case tea.KeyMsg:
switch {
case "enter":
go c.updFunc()
return c, nil
default:
return c, nil
}
case string:
c.str = msg
}
func (c *Cli) updFunc() {
c.p.Send("update")
}
It was something like that. The fact is after posting here I realized how to update my view without the need of Send()
and that keeping the program inside my model was a shit implementation, but still, I think it would be good to have a way to manipulate the *tea.Program
during the tests 'cause there are certainly other app using tea.Program.Send()
out there and they might be untestable with teatest
. Maybe a more "bootstrapped" setup where you could build your own tea.Program and just pass it to teatest
. I'm probably just thinking out loud here.
If I could think of a more structured solution and you agree with my suggestion I could open a PR.
yeah generally I would say it's not a good idea to have a reference of the program in the model itself...
the use for program.Send was intended (if I'm remembering correctly) to have multiple programs talk to each other, e.g. on a wish server
In that case, you'll indeed need to tea.Program... maybe we can then make it public in teatest.TestModel, so you can get the program from one test model and add it it to another, so they can talk to each other 🤔
In that case, you'll indeed need to tea.Program... maybe we can then make it public in teatest.TestModel, so you can get the program from one test model and add it it to another, so they can talk to each other 🤔
My idea is to add a new function to teatest
like this:
func BootstrapTestModel(tb testing.TB, m tea.Model, options ...TestOption) (*TestModel, *tea.Program) {
tm := NewTestModel(tb, m, options...)
return tm, tm.program
}
So it wont break the current usage of NewTestModel
and opens the possibility to access the program. What do you think? (The function name is totally open for suggestions)