Loading server/matchmaker.go +2 −2 Original line number Diff line number Diff line Loading @@ -408,7 +408,7 @@ func (m *LocalMatchmaker) process(batch *index.Batch) { if l := len(sessionTickets); l <= 1 { delete(m.sessionTickets, entry.Presence.SessionId) } else { delete(sessionTickets, ticket) delete(sessionTickets, entry.Ticket) } } if entry.PartyId != "" { Loading @@ -416,7 +416,7 @@ func (m *LocalMatchmaker) process(batch *index.Batch) { if l := len(partyTickets); l <= 1 { delete(m.partyTickets, entry.PartyId) } else { delete(partyTickets, ticket) delete(partyTickets, entry.Ticket) } } } Loading server/matchmaker_test.go +169 −0 Original line number Diff line number Diff line Loading @@ -16,6 +16,7 @@ package server import ( "context" "errors" "io/ioutil" "os" "testing" Loading @@ -24,6 +25,7 @@ import ( "github.com/blugelabs/bluge" "github.com/gofrs/uuid" "github.com/heroiclabs/nakama-common/rtapi" "github.com/heroiclabs/nakama-common/runtime" "go.uber.org/zap" "google.golang.org/protobuf/encoding/protojson" ) Loading Loading @@ -1799,3 +1801,170 @@ var benchmarkPropsFew = map[string]string{ "a7": "foo", "a8": "baz", } func TestMatchmakerMaxPartyTracking(t *testing.T) { consoleLogger := loggerForTest(t) matchesSeen := make(map[string]*rtapi.MatchmakerMatched) matchMaker, cleanup, err := createTestMatchmaker(t, consoleLogger, func(presences []*PresenceID, envelope *rtapi.Envelope) { if len(presences) == 1 { matchesSeen[presences[0].SessionID.String()] = envelope.GetMatchmakerMatched() } }) if err != nil { t.Fatalf("error creating test matchmaker: %v", err) } defer cleanup() createTicketFunc := func(party string) error { sessionID, _ := uuid.NewV4() _, err = matchMaker.Add([]*MatchmakerPresence{ &MatchmakerPresence{ UserId: sessionID.String(), SessionId: sessionID.String(), Username: sessionID.String(), Node: sessionID.String(), SessionID: sessionID, }, }, sessionID.String(), party, "properties.a5:bar", 2, 2, map[string]string{ "a5": "bar", }, map[string]float64{}) if err != nil { return err } return nil } // create max tickets with party-a maxTickets := matchMaker.config.GetMatchmaker().MaxTickets for i := 0; i < maxTickets; i++ { err := createTicketFunc("party-a") if err != nil { t.Fatalf("error adding ticket: %v", err) } } // try to create one more ticket, expect error err = createTicketFunc("party-a") if !errors.Is(err, runtime.ErrMatchmakerTooManyTickets) { t.Fatalf("exected error too many tickets, got: %v", err) } // now create one with a different party, expect no error // also we expect it can match one of the previous // because it has a different party err = createTicketFunc("party-b") if err != nil { t.Fatalf("error adding ticket: %v", err) } // process tickets matchMaker.process(bluge.NewBatch()) // expect 2 matches if len(matchesSeen) !=2 { t.Fatalf("expected 2 matches, got %d", len(matchesSeen)) } // now we expect we should be able to add one more party-a ticket // because one was matched previously err = createTicketFunc("party-a") if err != nil { t.Fatalf("error adding ticket: %v", err) } // expect that adding again should fail, again hitting the max tickets err = createTicketFunc("party-a") if !errors.Is(err, runtime.ErrMatchmakerTooManyTickets) { t.Fatalf("exected error too many tickets, got: %v", err) } } func TestMatchmakerMaxSessionTracking(t *testing.T) { consoleLogger := loggerForTest(t) matchesSeen := make(map[string]*rtapi.MatchmakerMatched) matchMaker, cleanup, err := createTestMatchmaker(t, consoleLogger, func(presences []*PresenceID, envelope *rtapi.Envelope) { if len(presences) == 1 { matchesSeen[presences[0].SessionID.String()] = envelope.GetMatchmakerMatched() } }) if err != nil { t.Fatalf("error creating test matchmaker: %v", err) } defer cleanup() createTicketFunc := func(sessionID uuid.UUID) error { _, err = matchMaker.Add([]*MatchmakerPresence{ &MatchmakerPresence{ UserId: sessionID.String(), SessionId: sessionID.String(), Username: sessionID.String(), Node: sessionID.String(), SessionID: sessionID, }, }, sessionID.String(), "", "properties.a5:bar", 2, 2, map[string]string{ "a5": "bar", }, map[string]float64{}) if err != nil { return err } return nil } sessionID1, _ := uuid.NewV4() // create max tickets with sessionID1 maxTickets := matchMaker.config.GetMatchmaker().MaxTickets for i := 0; i < maxTickets; i++ { err := createTicketFunc(sessionID1) if err != nil { t.Fatalf("error adding ticket: %v", err) } } // try to create one more ticket, expect error err = createTicketFunc(sessionID1) if !errors.Is(err, runtime.ErrMatchmakerTooManyTickets) { t.Fatalf("exected error too many tickets, got: %v", err) } sessionID2, _ := uuid.NewV4() // now create one with a different session, expect no error // also we expect it can match one of the previous // because it has a different session err = createTicketFunc(sessionID2) if err != nil { t.Fatalf("error adding ticket: %v", err) } // process tickets matchMaker.process(bluge.NewBatch()) // expect 2 matches if len(matchesSeen) !=2 { t.Fatalf("expected 2 matches, got %d", len(matchesSeen)) } // now we expect we should be able to add one more sessionID1 ticket // because one was matched previously err = createTicketFunc(sessionID1) if err != nil { t.Fatalf("error adding ticket: %v", err) } // expect that adding again should fail, again hitting the max tickets err = createTicketFunc(sessionID1) if !errors.Is(err, runtime.ErrMatchmakerTooManyTickets) { t.Fatalf("exected error too many tickets, got: %v", err) } } Loading
server/matchmaker.go +2 −2 Original line number Diff line number Diff line Loading @@ -408,7 +408,7 @@ func (m *LocalMatchmaker) process(batch *index.Batch) { if l := len(sessionTickets); l <= 1 { delete(m.sessionTickets, entry.Presence.SessionId) } else { delete(sessionTickets, ticket) delete(sessionTickets, entry.Ticket) } } if entry.PartyId != "" { Loading @@ -416,7 +416,7 @@ func (m *LocalMatchmaker) process(batch *index.Batch) { if l := len(partyTickets); l <= 1 { delete(m.partyTickets, entry.PartyId) } else { delete(partyTickets, ticket) delete(partyTickets, entry.Ticket) } } } Loading
server/matchmaker_test.go +169 −0 Original line number Diff line number Diff line Loading @@ -16,6 +16,7 @@ package server import ( "context" "errors" "io/ioutil" "os" "testing" Loading @@ -24,6 +25,7 @@ import ( "github.com/blugelabs/bluge" "github.com/gofrs/uuid" "github.com/heroiclabs/nakama-common/rtapi" "github.com/heroiclabs/nakama-common/runtime" "go.uber.org/zap" "google.golang.org/protobuf/encoding/protojson" ) Loading Loading @@ -1799,3 +1801,170 @@ var benchmarkPropsFew = map[string]string{ "a7": "foo", "a8": "baz", } func TestMatchmakerMaxPartyTracking(t *testing.T) { consoleLogger := loggerForTest(t) matchesSeen := make(map[string]*rtapi.MatchmakerMatched) matchMaker, cleanup, err := createTestMatchmaker(t, consoleLogger, func(presences []*PresenceID, envelope *rtapi.Envelope) { if len(presences) == 1 { matchesSeen[presences[0].SessionID.String()] = envelope.GetMatchmakerMatched() } }) if err != nil { t.Fatalf("error creating test matchmaker: %v", err) } defer cleanup() createTicketFunc := func(party string) error { sessionID, _ := uuid.NewV4() _, err = matchMaker.Add([]*MatchmakerPresence{ &MatchmakerPresence{ UserId: sessionID.String(), SessionId: sessionID.String(), Username: sessionID.String(), Node: sessionID.String(), SessionID: sessionID, }, }, sessionID.String(), party, "properties.a5:bar", 2, 2, map[string]string{ "a5": "bar", }, map[string]float64{}) if err != nil { return err } return nil } // create max tickets with party-a maxTickets := matchMaker.config.GetMatchmaker().MaxTickets for i := 0; i < maxTickets; i++ { err := createTicketFunc("party-a") if err != nil { t.Fatalf("error adding ticket: %v", err) } } // try to create one more ticket, expect error err = createTicketFunc("party-a") if !errors.Is(err, runtime.ErrMatchmakerTooManyTickets) { t.Fatalf("exected error too many tickets, got: %v", err) } // now create one with a different party, expect no error // also we expect it can match one of the previous // because it has a different party err = createTicketFunc("party-b") if err != nil { t.Fatalf("error adding ticket: %v", err) } // process tickets matchMaker.process(bluge.NewBatch()) // expect 2 matches if len(matchesSeen) !=2 { t.Fatalf("expected 2 matches, got %d", len(matchesSeen)) } // now we expect we should be able to add one more party-a ticket // because one was matched previously err = createTicketFunc("party-a") if err != nil { t.Fatalf("error adding ticket: %v", err) } // expect that adding again should fail, again hitting the max tickets err = createTicketFunc("party-a") if !errors.Is(err, runtime.ErrMatchmakerTooManyTickets) { t.Fatalf("exected error too many tickets, got: %v", err) } } func TestMatchmakerMaxSessionTracking(t *testing.T) { consoleLogger := loggerForTest(t) matchesSeen := make(map[string]*rtapi.MatchmakerMatched) matchMaker, cleanup, err := createTestMatchmaker(t, consoleLogger, func(presences []*PresenceID, envelope *rtapi.Envelope) { if len(presences) == 1 { matchesSeen[presences[0].SessionID.String()] = envelope.GetMatchmakerMatched() } }) if err != nil { t.Fatalf("error creating test matchmaker: %v", err) } defer cleanup() createTicketFunc := func(sessionID uuid.UUID) error { _, err = matchMaker.Add([]*MatchmakerPresence{ &MatchmakerPresence{ UserId: sessionID.String(), SessionId: sessionID.String(), Username: sessionID.String(), Node: sessionID.String(), SessionID: sessionID, }, }, sessionID.String(), "", "properties.a5:bar", 2, 2, map[string]string{ "a5": "bar", }, map[string]float64{}) if err != nil { return err } return nil } sessionID1, _ := uuid.NewV4() // create max tickets with sessionID1 maxTickets := matchMaker.config.GetMatchmaker().MaxTickets for i := 0; i < maxTickets; i++ { err := createTicketFunc(sessionID1) if err != nil { t.Fatalf("error adding ticket: %v", err) } } // try to create one more ticket, expect error err = createTicketFunc(sessionID1) if !errors.Is(err, runtime.ErrMatchmakerTooManyTickets) { t.Fatalf("exected error too many tickets, got: %v", err) } sessionID2, _ := uuid.NewV4() // now create one with a different session, expect no error // also we expect it can match one of the previous // because it has a different session err = createTicketFunc(sessionID2) if err != nil { t.Fatalf("error adding ticket: %v", err) } // process tickets matchMaker.process(bluge.NewBatch()) // expect 2 matches if len(matchesSeen) !=2 { t.Fatalf("expected 2 matches, got %d", len(matchesSeen)) } // now we expect we should be able to add one more sessionID1 ticket // because one was matched previously err = createTicketFunc(sessionID1) if err != nil { t.Fatalf("error adding ticket: %v", err) } // expect that adding again should fail, again hitting the max tickets err = createTicketFunc(sessionID1) if !errors.Is(err, runtime.ErrMatchmakerTooManyTickets) { t.Fatalf("exected error too many tickets, got: %v", err) } }