Documentation
¶
Overview ¶
Package matchmaking provides a queue-driven room allocator on top of Adler.
A Matchmaker keeps sessions in an internal main queue and, optionally, a waiting queue when the main queue is full. A background goroutine owns those queues, processes add/remove requests through a command channel, and creates a new Adler room as soon as enough sessions are available.
The room assignment is stored in each session so your application can inspect or clear the current match state later, for example from OnRoomLeave or HandleDisconnect.
Index ¶
Constants ¶
This section is empty.
Variables ¶
var ( // ErrSessionNil is returned when a queue operation receives a nil session. // // The matchmaker cannot enqueue or remove a nil session because the worker // needs a stable pointer to track the session in its internal maps. ErrSessionNil = errors.New("session is nil") // ErrMatchmakerBusy is returned when AddToQueue cannot place a command into // the internal command buffer immediately. // // This means the matchmaker goroutine has not yet consumed previous work, // so the caller can retry later instead of blocking the connect flow. ErrMatchmakerBusy = errors.New("matchmaker busy") )
Functions ¶
This section is empty.
Types ¶
type Matchmaker ¶
type Matchmaker struct {
// contains filtered or unexported fields
}
Matchmaker owns the matchmaking queues and turns sessions into rooms.
Public methods do not modify the queues directly. They send commands to an internal worker goroutine, which serializes all queue mutations. That design keeps queue state consistent while still letting the rest of the application call AddToQueue and RemoveFromQueue from request handlers, connect hooks, or disconnect hooks.
func NewMatchmaker ¶
func NewMatchmaker(a *adler.Adler, opts ...MatchmakingOption) *Matchmaker
NewMatchmaker creates a queue manager that runs in the background and groups sessions into rooms automatically.
Internally it starts a goroutine that receives add/remove commands over a channel. That goroutine owns the queue state, so calls such as AddToQueue and RemoveFromQueue do not mutate the lists directly; they only enqueue commands for the worker to process. When the main queue reaches RoomSize, or when a partial room is allowed by the timeout/min-size rules, the matchmaker creates an Adler room, joins the selected sessions to it, stores the room id in each session, and broadcasts a match_found event.
func (*Matchmaker) AddToQueue ¶
func (m *Matchmaker) AddToQueue(s *adler.Session) error
AddToQueue asks the matchmaker to place a session into the active queue.
The call is non-blocking. It only enqueues a command for the worker goroutine and returns ErrMatchmakerBusy if the command buffer is full. When the worker eventually processes the request, it either places the session into the main queue, moves it to the waiting queue, or leaves it alone if the session is already marked as playing in a room.
func (*Matchmaker) RemoveFromQueue ¶
func (m *Matchmaker) RemoveFromQueue(s *adler.Session)
RemoveFromQueue asks the matchmaker to remove a session from whichever queue currently owns it.
The function is intentionally fire-and-forget because disconnect and leave flows usually care about quick cleanup, not an immediate confirmation. The worker removes the session from the main queue or the waiting queue, updates the session status to "left", and then reprocesses the remaining queue if a main-queue slot was freed.
type MatchmakingConfig ¶
type MatchmakingConfig struct {
MaxQueue int
RoomSize int
MinRoomSize int
PartialRoomTimeout time.Duration
CommandBuffer int
}
MatchmakingConfig controls how the matchmaker buffers sessions and when it turns queued sessions into rooms.
The defaults are chosen to make the queue usable out of the box: a bounded main queue, a room size of 4, and a command buffer large enough for bursty connect/disconnect traffic.
type MatchmakingOption ¶
type MatchmakingOption func(*MatchmakingConfig)
MatchmakingOption customizes the configuration used by NewMatchmaker.
Options are applied before the matchmaker starts, so they only affect the queues and thresholds created during initialization.
func WithCommandBuffer ¶
func WithCommandBuffer(size int) MatchmakingOption
WithCommandBuffer sets the buffer size for the internal command channel.
A larger buffer allows more concurrent AddToQueue and RemoveFromQueue calls to be accepted before the worker catches up.
func WithMinRoomSize ¶
func WithMinRoomSize(minRoomSize int) MatchmakingOption
WithMinRoomSize sets the minimum number of queued sessions needed before the matchmaker may create a partial room.
This only matters when there are not enough sessions to fill a full room. The matchmaker still respects RoomSize as the upper bound for that partial room.
func WithPartialRoomTimeout ¶
func WithPartialRoomTimeout(timeout time.Duration) MatchmakingOption
WithPartialRoomTimeout controls how long the oldest queued session must wait before the matchmaker is allowed to create a room with fewer than RoomSize players.
A zero timeout disables partial-room creation entirely, which means the matchmaker waits for a full room.
func WithQueueLength ¶
func WithQueueLength(queueLength int) MatchmakingOption
WithQueueLength limits how many sessions can stay in the main queue.
When the main queue is full, new sessions are moved to the waiting queue and are promoted automatically later when room creation frees a slot.
func WithRoomSize ¶
func WithRoomSize(roomSize int) MatchmakingOption
WithRoomSize sets how many sessions are placed into each generated room.
If RoomSize is 2, the matchmaker will wait until two queued sessions are available before creating a room, unless partial room creation is permitted by the timeout/min-size rules.