fix poll/send race condition and panic on errors instead of ignoring

This commit is contained in:
Lobo 2025-10-11 23:29:58 -03:00
parent 221cbab51a
commit f5ebd3b5f1
3 changed files with 37 additions and 8 deletions

View file

@ -38,6 +38,10 @@ func (app *App) Poll(since int) (num int, err error) {
}
func (app *App) Last(n int) (err error) {
if n == 0 {
return nil
}
if _, err := fmt.Fprintf(app.conn, "LAST %d\n", n); err != nil {
return err
}
@ -52,6 +56,10 @@ func (app *App) Last(n int) (err error) {
return err
}
if nsrv == 0 {
goto count
}
for range nsrv {
if !app.scanner.Scan() {
return app.scanner.Err()
@ -59,6 +67,7 @@ func (app *App) Last(n int) (err error) {
app.incoming <- Message(app.scanner.Text())
}
count:
var last int
if !app.scanner.Scan() {
return app.scanner.Err()

View file

@ -4,25 +4,37 @@ type IncomingEvent interface {
HandleIncoming(*App)
}
type OutgoingEvent interface {
HandleOutgoing(*App)
HandleOutgoing(*App) error
}
type Message string
func (m Message) HandleIncoming(app *App) {
app.AppendMessage(string(m))
}
func (m Message) HandleOutgoing(app *App) error {
num, err := app.Send(string(m))
if err != nil {
return err
}
func (m Message) HandleOutgoing(app *App) {
num, _ := app.Send(string(m))
app.incoming <- SetLast(num)
return nil
}
type Poll int
func (p Poll) HandleOutgoing(app *App) {
num, _ := app.Poll(int(p))
go app.Last(num)
func (p Poll) HandleOutgoing(app *App) error {
num, err := app.Poll(int(p))
if err != nil {
return err
}
err = app.Last(num)
if err != nil {
return err
}
return nil
}
type SetLast int

12
main.go
View file

@ -59,6 +59,7 @@ type App struct {
incoming chan IncomingEvent
outgoing chan OutgoingEvent
error chan error
vx *vaxis.Vaxis
w struct {
@ -82,14 +83,18 @@ func (app *App) Connect(host, port string) (err error) {
app.scanner = bufio.NewScanner(app.conn)
app.incoming = make(chan IncomingEvent)
app.outgoing = make(chan OutgoingEvent)
app.ticker = time.NewTicker(2 * time.Second)
app.error = make(chan error)
app.ticker = time.NewTicker(1 * time.Second)
go func() {
app.Last(50)
for {
select {
case ev := <-app.outgoing:
ev.HandleOutgoing(app)
if err := ev.HandleOutgoing(app); err != nil {
app.error <- err
return
}
case <-app.ctx.Done():
return
}
@ -179,6 +184,9 @@ func main() {
ev.HandleIncoming(&app)
case <-app.ticker.C:
app.outgoing <- Poll(app.last)
case err := <-app.error:
app.FinishUI()
panic(err)
case <-app.ctx.Done():
return
}