1
0
mirror of https://github.com/mum4k/termdash.git synced 2025-04-27 13:48:49 +08:00

Errors are no longer a special case in the EDS.

And changing event queue so that Pullers don't have to process an error.
This commit is contained in:
Jakub Sobon 2019-02-20 00:20:58 -05:00
parent 36bf99ebc7
commit 286e5abd2f
No known key found for this signature in database
GPG Key ID: F2451A77FB05D3B7
6 changed files with 21 additions and 56 deletions

View File

@ -73,21 +73,8 @@ func newSubscriber(filter []terminalapi.Event, cb Callback) *subscriber {
// Terminates when the context expires.
func (s *subscriber) run(ctx context.Context) {
for {
e, err := s.queue.Pull(ctx)
if err != nil {
e = terminalapi.NewErrorf("failed to pull event off the queue: %v", err)
}
switch ev := e.(type) {
case *terminalapi.Error:
// Don't forward the error if the context is closed.
select {
case <-ctx.Done():
default:
s.cb(ev)
}
default:
ev := s.queue.Pull(ctx)
if ev != nil {
s.cb(ev)
}
@ -105,9 +92,8 @@ func (s *subscriber) event(ev terminalapi.Event) {
s.queue.Push(ev)
}
var errT *terminalapi.Error
t := reflect.TypeOf(ev)
if t == reflect.TypeOf(errT) || s.filter[t] {
if s.filter[t] {
s.queue.Push(ev)
}
}
@ -167,9 +153,6 @@ type StopFunc func()
// all kinds. If the filter is non-empty, only events of the provided type will
// be sent to the subscriber.
// Returns a function that allows the subscriber to unsubscribe.
//
// Subscribers cannot filter out event type terminalapi.Error which is used to
// forward errors to the Callback.
func (eds *DistributionSystem) Subscribe(filter []terminalapi.Event, cb Callback) StopFunc {
eds.mu.Lock()
defer eds.mu.Unlock()

View File

@ -187,7 +187,7 @@ func TestDistributionSystem(t *testing.T) {
},
},
{
desc: "single subscriber, errors are always received",
desc: "single subscriber, wants errors only",
events: []terminalapi.Event{
&terminalapi.Keyboard{Key: keyboard.KeyEnter},
&terminalapi.Mouse{Position: image.Point{1, 1}},
@ -197,14 +197,11 @@ func TestDistributionSystem(t *testing.T) {
subCase: []*subscriberCase{
{
filter: []terminalapi.Event{
&terminalapi.Keyboard{},
&terminalapi.Mouse{},
terminalapi.NewError(""),
},
rec: newReceiver(receiverModeReceive),
want: map[terminalapi.Event]bool{
&terminalapi.Keyboard{Key: keyboard.KeyEnter}: true,
&terminalapi.Mouse{Position: image.Point{1, 1}}: true,
terminalapi.NewError("error"): true,
terminalapi.NewError("error"): true,
},
},
},
@ -230,8 +227,6 @@ func TestDistributionSystem(t *testing.T) {
want: map[terminalapi.Event]bool{
&terminalapi.Keyboard{Key: keyboard.KeyEnter}: true,
&terminalapi.Keyboard{Key: keyboard.KeyEsc}: true,
terminalapi.NewError("error1"): true,
terminalapi.NewError("error2"): true,
},
},
{
@ -245,8 +240,6 @@ func TestDistributionSystem(t *testing.T) {
&terminalapi.Mouse{Position: image.Point{1, 1}}: true,
&terminalapi.Resize{Size: image.Point{1, 1}}: true,
&terminalapi.Resize{Size: image.Point{2, 2}}: true,
terminalapi.NewError("error1"): true,
terminalapi.NewError("error2"): true,
},
},
},
@ -268,8 +261,6 @@ func TestDistributionSystem(t *testing.T) {
want: map[terminalapi.Event]bool{
&terminalapi.Keyboard{Key: keyboard.KeyEnter}: true,
&terminalapi.Keyboard{Key: keyboard.KeyEsc}: true,
terminalapi.NewError("error1"): true,
terminalapi.NewError("error2"): true,
},
},
{
@ -280,8 +271,6 @@ func TestDistributionSystem(t *testing.T) {
want: map[terminalapi.Event]bool{
&terminalapi.Keyboard{Key: keyboard.KeyEnter}: true,
&terminalapi.Keyboard{Key: keyboard.KeyEsc}: true,
terminalapi.NewError("error1"): true,
terminalapi.NewError("error2"): true,
},
wantErr: true,
},

View File

@ -124,10 +124,10 @@ func (u *Unbound) Pop() terminalapi.Event {
}
// Pull is like Pop(), but blocks until an item is available or the context
// expires.
func (u *Unbound) Pull(ctx context.Context) (terminalapi.Event, error) {
// expires. Returns a nil event if the context expired.
func (u *Unbound) Pull(ctx context.Context) terminalapi.Event {
if e := u.Pop(); e != nil {
return e, nil
return e
}
u.cond.L.Lock()
@ -135,12 +135,12 @@ func (u *Unbound) Pull(ctx context.Context) (terminalapi.Event, error) {
for {
select {
case <-ctx.Done():
return nil, ctx.Err()
return nil
default:
}
if e := u.Pop(); e != nil {
return e, nil
return e
}
u.cond.Wait()
}

View File

@ -84,10 +84,7 @@ func TestPullEventAvailable(t *testing.T) {
q.Push(want)
ctx := context.Background()
got, err := q.Pull(ctx)
if err != nil {
t.Fatalf("Pull => unexpected error: %v", err)
}
got := q.Pull(ctx)
if diff := pretty.Compare(want, got); diff != "" {
t.Errorf("Pull => unexpected diff (-want, +got):\n%s", diff)
}
@ -107,16 +104,12 @@ func TestPullBlocksUntilAvailable(t *testing.T) {
ctx, cancel := context.WithTimeout(context.Background(), 1*time.Millisecond)
defer cancel()
if _, err := q.Pull(ctx); err == nil {
t.Fatal("Pull => expected timeout error, got nil")
if got := q.Pull(ctx); got != nil {
t.Fatalf("Pull => %v, want <nil>", got)
}
close(ch)
got, err := q.Pull(context.Background())
if err != nil {
t.Fatalf("Pull => unexpected error: %v", err)
}
got := q.Pull(context.Background())
if diff := pretty.Compare(want, got); diff != "" {
t.Errorf("Pull => unexpected diff (-want, +got):\n%s", diff)
}

View File

@ -195,9 +195,9 @@ func (t *Terminal) Event(ctx context.Context) terminalapi.Event {
return terminalapi.NewErrorf("no event queue provided, use the WithEventQueue option when creating the fake terminal")
}
ev, err := t.events.Pull(ctx)
if err != nil {
return terminalapi.NewErrorf("unable to pull the next event: %v", err)
ev := t.events.Pull(ctx)
if ev == nil {
return terminalapi.NewError("unable to pull the next event")
}
if res, ok := ev.(*terminalapi.Resize); ok {

View File

@ -148,9 +148,9 @@ func (t *Terminal) pollEvents() {
// Event implements terminalapi.Terminal.Event.
func (t *Terminal) Event(ctx context.Context) terminalapi.Event {
ev, err := t.events.Pull(ctx)
if err != nil {
return terminalapi.NewErrorf("unable to pull the next event: %v", err)
ev := t.events.Pull(ctx)
if ev == nil {
return terminalapi.NewError("unable to pull the next event")
}
return ev
}