Task: EventStream
Parent epic: #4 (M1 — Robot Connection)
Depends on: #16 (ConnectionManager)
What to do
Create internal/brain/event_stream.go — subscribes to the vector-go-sdk's full event stream and fans each event out to registered handlers (the event bridge, state updater, etc.).
type EventHandler func(ctx context.Context, esn string, event *vectorpb.Event)
type EventStream struct { ... }
func NewEventStream(cm *ConnectionManager) *EventStream
func (es *EventStream) Register(handler EventHandler)
func (es *EventStream) Start(ctx context.Context) error // blocking, call in goroutine
Event types to handle (initial set)
RobotState — battery, pose, status flags
RobotObservedFace — face detected with ID and name
RobotObservedObject — cube or custom object
StimulationInfo — internal stimulation level
WakeWord — wake word detected
AttentionTransfer — attention shifted
HeldFillerAudio — robot is "thinking"
Non-blocking contract
The event goroutine must never block. If a handler is slow, it must run in its own goroutine or drop the event. The SDK stream goroutine is sacred — blocking it means missing events.
Notes
- Start the EventStream in a goroutine from
ConnectionManager.Start().
- On SDK connection loss,
Start() should return — the reconnect loop in ConnectionManager will restart it.
- Log unknown event types at DEBUG level (we'll encounter firmware events we haven't seen yet).
Definition of done
EventStream running, at least RobotState events arriving and updating ConnectionManager internal state. Verified with robot connected.
Task: EventStream
Parent epic: #4 (M1 — Robot Connection)
Depends on: #16 (ConnectionManager)
What to do
Create
internal/brain/event_stream.go— subscribes to the vector-go-sdk's full event stream and fans each event out to registered handlers (the event bridge, state updater, etc.).Event types to handle (initial set)
RobotState— battery, pose, status flagsRobotObservedFace— face detected with ID and nameRobotObservedObject— cube or custom objectStimulationInfo— internal stimulation levelWakeWord— wake word detectedAttentionTransfer— attention shiftedHeldFillerAudio— robot is "thinking"Non-blocking contract
The event goroutine must never block. If a handler is slow, it must run in its own goroutine or drop the event. The SDK stream goroutine is sacred — blocking it means missing events.
Notes
ConnectionManager.Start().Start()should return — the reconnect loop in ConnectionManager will restart it.Definition of done
EventStreamrunning, at leastRobotStateevents arriving and updatingConnectionManagerinternal state. Verified with robot connected.