/// <summary> /// Returns <see cref="ApiResponse"/> with string representation of <see cref="ServerInfoJson"/> in body. /// </summary> /// <param name="endpoint"></param> /// <returns></returns> public ApiResponse GetInfo(string endpoint) { using (var context = new GameStatsDbDataContext()) { var server = context.Servers.FirstOrDefault(s => s.endpoint == endpoint); if (server == null) { return(new ApiResponse(System.Net.HttpStatusCode.NotFound)); } int serverId = server.id; var gameModes = (from gmOnServer in context.GameModesOnServers where gmOnServer.server_id == serverId join gameMode in context.GameModes on gmOnServer.gm_id equals gameMode.id select gameMode.name).ToList(); ServerInfoJson serverInfo = new ServerInfoJson { Name = server.name, GameModes = gameModes.ToList() }; return(new ApiResponse( body: JsonConvert.SerializeObject(serverInfo, Formatting.Indented))); } }
/// <summary> /// Returns <see cref="ApiResponse"/> with string representation of List<<see cref="ServersInfoRecordJson"/>> in body. /// </summary> /// <returns></returns> public ApiResponse GetInfo() { using (var context = new GameStatsDbDataContext()) { var servers = context.Servers; List <ServersInfoRecordJson> results = new List <ServersInfoRecordJson>(); foreach (var server in servers) { int serverId = server.id; var gameModes = (from gmOnServer in context.GameModesOnServers where gmOnServer.server_id == serverId join gameMode in context.GameModes on gmOnServer.gm_id equals gameMode.id select gameMode.name).ToList(); ServerInfoJson serverInfo = new ServerInfoJson { Name = server.name, GameModes = gameModes }; results.Add(new ServersInfoRecordJson { Endpoint = server.endpoint, Info = serverInfo }); } return(new ApiResponse( body: JsonConvert.SerializeObject(results))); } }
/// <summary> /// Returns <see cref="ApiResponse"/> with string representation of List<<see cref="RecentMatchJson"/>> in body. /// </summary> /// <param name="count"></param> /// <returns></returns> public ApiResponse GetRecentMatches(int count) { using (var context = new GameStatsDbDataContext()) { var recentMatches = (from match in context.Matches orderby match.timestamp descending select new RecentMatchJson { Server = (from server in context.Servers where server.id == match.server_id select server.endpoint) .First(), Timestamp = DateTime.SpecifyKind(match.timestamp, DateTimeKind.Utc), Results = new MatchJson { FragLimit = match.frag_limit, TimeElapsed = match.time_elapsed, TimeLimit = match.time_limit, GameMode = (from gm in context.GameModes where gm.id == match.gm_id select gm.name) .First(), Map = (from map in context.Maps where map.id == match.map_id select map.name) .First(), Scoreboard = (from scoreboardRecord in context.PlayersInMatches where scoreboardRecord.match_id == match.id orderby scoreboardRecord.player_rank ascending select new ScoreboardRecordJson { Deaths = scoreboardRecord.deaths, Frags = scoreboardRecord.frags, Kills = scoreboardRecord.kills, Name = (from player in context.Players where player.id == scoreboardRecord.player_id select player.name) .First() }) .ToList() } }) .Take(count); return(new ApiResponse( JsonConvert.SerializeObject(recentMatches.ToList(), Formatting.Indented))); } }
/// <summary> /// Returns <see cref="ApiResponse"/> with string representation of <see cref="MatchJson"/> in body. /// </summary> /// <param name="endpoint"></param> /// <param name="timestamp"></param> /// <returns></returns> public ApiResponse GetMatch(string endpoint, DateTime timestamp) { using (var context = new GameStatsDbDataContext()) { var matchRecord = (from server in context.Servers where server.endpoint == endpoint join match in context.Matches on server.id equals match.server_id where match.timestamp == timestamp select match) .FirstOrDefault(); if (matchRecord == null) { return(new ApiResponse(HttpStatusCode.NotFound)); } var scoreboardRecords = (from playerInMatch in context.PlayersInMatches where playerInMatch.match_id == matchRecord.id orderby playerInMatch.player_rank select playerInMatch); List <ScoreboardRecordJson> _scoreboard = scoreboardRecords .Select(record => new ScoreboardRecordJson { Deaths = record.deaths, Frags = record.frags, Kills = record.kills, Name = (from player in context.Players where player.id == record.player_id select player.name) .First() }).ToList(); MatchJson _match = new MatchJson { FragLimit = matchRecord.frag_limit, Scoreboard = _scoreboard, TimeElapsed = matchRecord.time_elapsed, TimeLimit = matchRecord.time_limit, GameMode = (from gm in context.GameModes where gm.id == matchRecord.gm_id select gm.name) .First(), Map = (from map in context.Maps where map.id == matchRecord.map_id select map.name) .First() }; return(new ApiResponse(JsonConvert.SerializeObject(_match, Formatting.Indented))); } }
public void GetNonExistingMatch() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); context.ExecuteCommand("DELETE FROM Matches"); } ApiResponse putServerResponse = new ServerController().PutInfo(staticServerEndpoint, staticServerInfoJson); Assert.AreEqual(HttpStatusCode.OK, putServerResponse.Status); // act // get stats from server having no matches played on it ApiResponse getServerStats = new ServerController().GetStats(staticServerEndpoint); Assert.AreEqual(HttpStatusCode.OK, getServerStats.Status); ServerController.ServerStatsJson expectedStats = ServerController.ServerStatsJson.Trivial(); ServerController.ServerStatsJson actualStats = JsonConvert.DeserializeObject <ServerController.ServerStatsJson>(getServerStats.Body); // assert Assert.AreEqual(expectedStats, actualStats); // act // get match from non-existing server ApiResponse getMatchInfo = new MatchController().GetMatch("non-existing-endpoint", staticTimestamp); // assert Assert.AreEqual(HttpStatusCode.NotFound, getMatchInfo.Status); // act // get non-existing match from existing server ApiResponse getMatchInfoFromExistingServer = new MatchController().GetMatch(staticServerEndpoint, staticTimestamp); // assert Assert.AreEqual(HttpStatusCode.NotFound, getMatchInfoFromExistingServer.Status); // act // get recent matches ApiResponse getRecentMatches = new MatchController().GetRecentMatches(10); var expectedRecentMatches = new List <MatchController.RecentMatchJson>(); var actualRecentMatches = JsonConvert.DeserializeObject <List <MatchController.RecentMatchJson> >(getRecentMatches.Body); Assert.AreEqual(HttpStatusCode.OK, getRecentMatches.Status); CollectionAssert.AreEqual(expectedRecentMatches, actualRecentMatches); }
public void GetNonExistingServer() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); } // act ApiResponse getServerInfoResponse = new ServerController().GetInfo("non-existing-endpoint"); ApiResponse getServerStatsResponse = new ServerController().GetStats("non-existing-endpoint"); // assert Assert.AreEqual(HttpStatusCode.NotFound, getServerInfoResponse.Status); Assert.AreEqual(HttpStatusCode.NotFound, getServerStatsResponse.Status); }
public void PutMatchTest() { // arrange //// using static fields using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Matches"); } PutServerInfoTest(); // act ApiResponse putMatchResponce = new MatchController().PutMatch("123.4.5.6-8080", staticMatchJson, staticTimestamp); // assert Assert.AreEqual(HttpStatusCode.OK, putMatchResponce.Status); }
private GameModes addGameMode(string name, GameStatsDbDataContext context) { var gms = context.GameModes.Where(gm => gm.name == name); if (gms.Count() > 0) { return(gms.First()); } else { var newgm = new GameModes() { name = name }; context.GameModes.InsertOnSubmit(newgm); context.SubmitChanges(); return(newgm); } }
private int addPlayer(string name, GameStatsDbDataContext context) { var player = context.Players.FirstOrDefault(pl => pl.name == name); if (player == null) { // add new player Players newPlayer = new Players { name = name }; context.Players.InsertOnSubmit(newPlayer); context.SubmitChanges(); return(newPlayer.id); } else { return(player.id); } }
private int addMap(string name, GameStatsDbDataContext context) { var map = context.Maps.FirstOrDefault(m => m.name == name); if (map == null) { // add new map Maps newMap = new Maps { name = name }; context.Maps.InsertOnSubmit(newMap); context.SubmitChanges(); return(newMap.id); } else { return(map.id); } }
public ApiResponse PutInfo(string endpoint, string name, List <string> gameModes) { using (var context = new GameStatsDbDataContext()) { var allServers = context.Servers; var servers = allServers.Where(s => s.endpoint == endpoint); Servers newServer; if (servers.Count() > 0) { // rewrite existing info newServer = servers.First(); newServer.name = name; // delete existing game modes links var oldGameModesLinks = from gmLink in context.GameModesOnServers where gmLink.server_id == newServer.id select gmLink; context.GameModesOnServers.DeleteAllOnSubmit(oldGameModesLinks); context.SubmitChanges(); } else { // insert new server with same endpoint newServer = new Servers() { endpoint = endpoint, name = name }; allServers.InsertOnSubmit(newServer); context.SubmitChanges(); } // link game modes and servers foreach (var newgm in gameModes) { var gm = addGameMode(newgm, context); var link = addLinkGameModeOnServer(gm, newServer, context); } context.SubmitChanges(); return(new ApiResponse()); } }
/// <summary> /// Returns <see cref="ApiResponse"/> with string representation of List<<see cref="BestPlayerJson"/>> in body. /// </summary> /// <param name="count"></param> /// <returns><see cref="ApiResponse"/> with string representation of List<<see cref="BestPlayerJson"/>> in body.</returns> public ApiResponse GetBestPlayers(int count) { using (var context = new GameStatsDbDataContext()) { var bestPlayers = (from player in context.Players where player.matches_played >= 10 && player.total_deaths != 0 let kdr = (double)player.total_kills / player.total_deaths orderby kdr descending select new BestPlayerJson { Name = player.name, KDR = kdr }) .Take(count) .ToList(); return(new ApiResponse( body: JsonConvert.SerializeObject(bestPlayers, Formatting.Indented))); } }
public void GetNonExistingPlayerStats() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); context.ExecuteCommand("DELETE FROM Matches"); context.ExecuteCommand("DELETE FROM Players"); } ApiResponse putServerResponse = new ServerController().PutInfo(staticServerEndpoint, staticServerInfoJson); Assert.AreEqual(HttpStatusCode.OK, putServerResponse.Status); ApiResponse putMatchResponse = new MatchController().PutMatch(staticServerEndpoint, staticMatchJson, staticTimestamp); Assert.AreEqual(HttpStatusCode.OK, putMatchResponse.Status); // act ApiResponse getPlayerStats = new PlayerController().GetStats("non_existing_player"); // assert Assert.AreEqual(HttpStatusCode.NotFound, getPlayerStats.Status); }
/// <summary> /// Returns <see cref="ApiResponse"/> with string representation of List<<see cref="PopularServerJson"/>> in body. /// </summary> /// <param name="count"></param> /// <returns></returns> public ApiResponse GetPopularServers(int count) { using (var context = new GameStatsDbDataContext()) { var popularServers = (from serverDay in context.ServersByDay group serverDay by serverDay.server_id into serverGroup let avg = serverGroup.Average(sg => sg.matches_count) orderby avg descending join serverInfo in context.Servers on serverGroup.Key equals serverInfo.id select new PopularServerJson { Endpoint = serverInfo.endpoint, Name = serverInfo.name, avgMatches = avg }) .Take(count) .ToList(); return(new ApiResponse( body: JsonConvert.SerializeObject(popularServers, Formatting.Indented))); } }
public ApiResponse PutMatch(string endpoint, MatchJson match, DateTime timestamp) { using (var context = new GameStatsDbDataContext()) { var server = context.Servers.FirstOrDefault(s => s.endpoint == endpoint); if (server == null) { // there was not advertise-request with such endpoint return(new ApiResponse(endpoint + " server is not announced.", HttpStatusCode.BadRequest)); } // get players' ids to use it later List <int> playersIds = match.Scoreboard.Select(pl => addPlayer(pl.Name, context)).ToList(); // insert new match // check game mode // find its id by name int gm_id; var gm = context.GameModes .FirstOrDefault(gm_ => gm_.name == match.GameMode); if (gm == null) { return(new ApiResponse("Unknown game mode: " + match.GameMode, HttpStatusCode.BadRequest)); } else { gm_id = gm.id; // does the sever support this game mode? bool isBadGm = (from gmOnServer in context.GameModesOnServers where gmOnServer.gm_id == gm_id && gmOnServer.server_id == server.id select gm_id) .Count() == 0; if (isBadGm) { return(new ApiResponse("Game mode " + match.GameMode + " is not supported on server: " + endpoint, HttpStatusCode.BadRequest)); } } Matches newMatch = new Matches { server_id = server.id, timestamp = timestamp, map_id = addMap(match.Map, context), gm_id = gm_id, frag_limit = match.FragLimit, time_limit = match.TimeLimit, time_elapsed = match.TimeElapsed, players_count = playersIds.Count(), winner_id = playersIds.First() }; // save context.Matches.InsertOnSubmit(newMatch); context.SubmitChanges(); // insert scoreboard int matchId = newMatch.id; int rank = 1; var newScoreboardRecords = match.Scoreboard .Zip(playersIds, (player, playerId) => new PlayersInMatches { match_id = matchId, player_id = playerId, player_rank = rank++, frags = player.Frags, kills = player.Kills, deaths = player.Deaths }); // save context.PlayersInMatches.InsertAllOnSubmit(newScoreboardRecords); context.SubmitChanges(); return(new ApiResponse()); } }
public void GetServerStats() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); context.ExecuteCommand("DELETE FROM Matches"); } ServerController.ServerInfoJson server = new ServerController.ServerInfoJson { Name = "test_server", GameModes = new List <string> { "DM", "TDM" } }; string serverJson = JsonConvert.SerializeObject(server); MatchController.MatchJson match1 = new MatchController.MatchJson { FragLimit = 20, GameMode = "DM", Map = "test_map", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "test_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "test_player_2" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "test_player_3" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "test_player_4" } } }; string match1json = JsonConvert.SerializeObject(match1); MatchController.MatchJson match2 = new MatchController.MatchJson { FragLimit = 20, GameMode = "DM", Map = "test_map", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "test_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "test_player_2" } } }; string match2json = JsonConvert.SerializeObject(match2); DateTime timestamp1 = Convert.ToDateTime("2017-01-22T15:11:12Z"); DateTime timestamp2 = timestamp1.AddHours(1); // expected answer var expectedStats = new ServerController.ServerStatsJson { AverageMatchesPerDay = 2, // match1 and match2 played in 1 day AveragePopulation = (match1.Scoreboard.Count + match2.Scoreboard.Count) / 2.0, MaximumMatchesPerDay = 2, MaximumPopulation = Math.Max(match1.Scoreboard.Count, match2.Scoreboard.Count), Top5GameModes = new List <string> { "DM" }, Top5Maps = new List <string> { "test_map" }, TotalMatchesPlayed = 2 }; // act ApiResponse putServerResponse = new ServerController().PutInfo("test-server.com-1337", serverJson); ApiResponse putMatch1Response = new MatchController().PutMatch("test-server.com-1337", match1json, timestamp1); ApiResponse putMatch2Response = new MatchController().PutMatch("test-server.com-1337", match2json, timestamp2); ApiResponse getStatsResponse = new ServerController().GetStats("test-server.com-1337"); var actualStats = JsonConvert.DeserializeObject <ServerController.ServerStatsJson>(getStatsResponse.Body); // assert Assert.AreEqual(HttpStatusCode.OK, putServerResponse.Status); Assert.AreEqual(HttpStatusCode.OK, putMatch1Response.Status); Assert.AreEqual(HttpStatusCode.OK, putMatch2Response.Status); Assert.AreEqual(HttpStatusCode.OK, getStatsResponse.Status); Assert.AreEqual(expectedStats, actualStats); }
public void GetPlayerStats() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); context.ExecuteCommand("DELETE FROM Matches"); context.ExecuteCommand("DELETE FROM Players"); } ServerController.ServerInfoJson server1 = new ServerController.ServerInfoJson { Name = "test_server_1", GameModes = new List <string> { "DM", "TDM" } }; string server1json = JsonConvert.SerializeObject(server1); ServerController.ServerInfoJson server2 = new ServerController.ServerInfoJson { Name = "test_server_2", GameModes = new List <string> { "DM", "TDM" } }; string server2json = JsonConvert.SerializeObject(server2); MatchController.MatchJson match1 = new MatchController.MatchJson { FragLimit = 20, GameMode = "DM", Map = "test_map", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 1, Frags = 10, Kills = 10, Name = "test_player" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_2" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_3" } } }; string match1json = JsonConvert.SerializeObject(match1); MatchController.MatchJson match2 = new MatchController.MatchJson { FragLimit = 20, GameMode = "DM", Map = "test_map", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 1, Frags = 10, Kills = 10, Name = "test_player" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_2" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_3" } } }; string match2json = JsonConvert.SerializeObject(match2); MatchController.MatchJson match3 = new MatchController.MatchJson { FragLimit = 20, GameMode = "TDM", // 1 TDM, 3 others DM Map = "test_map", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 1, Frags = 5, Kills = 15, Name = "dummy_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 2, Frags = 5, Kills = 5, Name = "test_player" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_3" } } }; string match3json = JsonConvert.SerializeObject(match3); MatchController.MatchJson match4 = new MatchController.MatchJson { FragLimit = 20, GameMode = "DM", Map = "test_map", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 1, Frags = 5, Kills = 15, Name = "dummy_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 2, Frags = 5, Kills = 5, Name = "test_player" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_3" } } }; string match4json = JsonConvert.SerializeObject(match4); DateTime day1timestamp = Convert.ToDateTime("2017-01-22T15:11:12Z"); DateTime day2timestamp = day1timestamp.AddDays(1); var expectedStats = new PlayerController.PlayerStatsJson { AverageMatchesPerDay = (3 + 1) / 2, AverageScoreboardPercent = (100 + 100 + 50 + 50) / 4.0, FavoriteGameMode = "DM", FavoriteServer = "test-server-1.com-8080", KillToDeathRatio = (double)(10 + 10 + 5 + 5) / (1 + 1 + 2 + 2), LastMatchPlayed = day2timestamp, MaximumMatchesPerDay = 3, TotalMatchesPlayed = 4, TotalMatchesWon = 2, UniqueServers = 2 }; // act // prepare servers ApiResponse putServer1Response = new ServerController().PutInfo("test-server-1.com-8080", server1json); ApiResponse putServer2Response = new ServerController().PutInfo("test-server-2.com-8080", server2json); Assert.AreEqual(HttpStatusCode.OK, putServer1Response.Status); Assert.AreEqual(HttpStatusCode.OK, putServer2Response.Status); // prepare matches ApiResponse putMatch1Response = new MatchController().PutMatch("test-server-1.com-8080", match1json, day1timestamp); ApiResponse putMatch2Response = new MatchController().PutMatch("test-server-1.com-8080", match2json, day2timestamp); ApiResponse putMatch3Response = new MatchController().PutMatch("test-server-1.com-8080", match3json, day1timestamp.AddHours(1)); ApiResponse putMatch4Response = new MatchController().PutMatch("test-server-2.com-8080", match4json, day1timestamp.AddHours(2)); Assert.AreEqual(HttpStatusCode.OK, putMatch1Response.Status); Assert.AreEqual(HttpStatusCode.OK, putMatch2Response.Status); Assert.AreEqual(HttpStatusCode.OK, putMatch3Response.Status); Assert.AreEqual(HttpStatusCode.OK, putMatch4Response.Status); // get players stats ApiResponse getStatsResponse = new PlayerController().GetStats("test_player"); PlayerController.PlayerStatsJson actualStats = JsonConvert.DeserializeObject <PlayerController.PlayerStatsJson>(getStatsResponse.Body); // assert Assert.AreEqual(expectedStats, actualStats); }
public void GetRecentMatchesTest() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); context.ExecuteCommand("DELETE FROM Matches"); context.ExecuteCommand("DELETE FROM Players"); context.ExecuteCommand("DELETE FROM Maps"); context.ExecuteCommand("DELETE FROM GameModes"); } ServerController.ServerInfoJson server1 = new ServerController.ServerInfoJson { Name = "test_server_1", GameModes = new List <string> { "DM", "TDM" } }; string server1json = JsonConvert.SerializeObject(server1); ServerController.ServerInfoJson server2 = new ServerController.ServerInfoJson { Name = "test_server_2", GameModes = new List <string> { "DM", "TDM" } }; string server2json = JsonConvert.SerializeObject(server2); MatchController.MatchJson match1 = new MatchController.MatchJson { FragLimit = 20, GameMode = "DM", Map = "test_map_1", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_2" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_3" } } }; string match1json = JsonConvert.SerializeObject(match1); MatchController.MatchJson match2 = new MatchController.MatchJson { FragLimit = 20, GameMode = "TDM", Map = "test_map_2", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_4" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_5" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_6" } } }; string match2json = JsonConvert.SerializeObject(match2); // act // put servers ApiResponse putServer1response = new ServerController().PutInfo("test-1.com-8080", server1json); Assert.AreEqual(HttpStatusCode.OK, putServer1response.Status); ApiResponse putServer2response = new ServerController().PutInfo("test-2.com-8080", server2json); Assert.AreEqual(HttpStatusCode.OK, putServer1response.Status); // put matches const int totalMatches = 20; const int requiredCount = 10; string[] endpoints = new string[] { "test-1.com-8080", "test-2.com-8080" }; MatchController.MatchJson[] matches = new MatchController.MatchJson[] { match1, match2 }; string[] matchJsons = new string[] { match1json, match2json }; DateTime timestamp = Convert.ToDateTime("2017-01-22T15:11:12Z"); // these matches will be not shown in recent matches for (int i = 0; i < totalMatches - requiredCount; i++) { ApiResponse putMatchResponse = new MatchController().PutMatch(endpoints[i % 2], matchJsons[i % 2], timestamp); Assert.AreEqual(HttpStatusCode.OK, putMatchResponse.Status); timestamp = timestamp.AddHours(1); } // and these will be var expectedMatches = new List <MatchController.RecentMatchJson>(); for (int i = 0; i < requiredCount; i++) { var recentMatch = new MatchController.RecentMatchJson { Results = matches[i % 2], Server = endpoints[i % 2], Timestamp = timestamp }; expectedMatches.Add(recentMatch); ApiResponse putMatchResponse = new MatchController().PutMatch(endpoints[i % 2], matchJsons[i % 2], timestamp); Assert.AreEqual(HttpStatusCode.OK, putMatchResponse.Status); timestamp = timestamp.AddHours(1); } // reverse expected matches to order by timestamp as in response expectedMatches.Reverse(); ApiResponse getRecentMatchesResponse = new MatchController().GetRecentMatches(requiredCount); Assert.AreEqual(HttpStatusCode.OK, getRecentMatchesResponse.Status); var actualMatches = JsonConvert.DeserializeObject <List <MatchController.RecentMatchJson> >(getRecentMatchesResponse.Body); // assert CollectionAssert.AreEqual(expectedMatches, actualMatches); }
public void GetPopularServersTest() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); context.ExecuteCommand("DELETE FROM Matches"); context.ExecuteCommand("DELETE FROM Players"); context.ExecuteCommand("DELETE FROM Maps"); context.ExecuteCommand("DELETE FROM GameModes"); context.ExecuteCommand("DELETE FROM ServersByDay"); } const int serversCount = 5; for (int i = 0; i < serversCount; i++) { var server = new ServerController.ServerInfoJson { GameModes = new List <string> { "DM" }, Name = "test_server_" + i.ToString() }; ApiResponse putServerResponse = new ServerController().PutInfo( endpoint: String.Format("test-server-{0}.com-8080", i), json: JsonConvert.SerializeObject(server)); Assert.AreEqual(HttpStatusCode.OK, putServerResponse.Status); } var match = new MatchController.MatchJson { FragLimit = 20, GameMode = "DM", Map = "test_map", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 5, Frags = 5, Kills = 5, Name = "dummy_player_2" } } }; string matchJson = JsonConvert.SerializeObject(match); const int daysCount = 5; int[,] matrix = new int[serversCount, daysCount]; matrix = new int[, ] { { 1, 1, 1, 1, 1 }, // 5/5 = 1 { 2, 2, 2, 2, 2 }, // 10/5 = 2 { 10, 10, 3, 2, 1 }, // 25/5 = 5 { 6, 3, 7, 2, 4 }, // 20/5 = 4 { 3, 3, 3, 3, 3 }, // 15/5 = 3 }; int[] answerVector = { 2, 3, 4, 1, 0 }; // put matches DateTime startTimestamp = Convert.ToDateTime("2017-01-22T15:11:12Z"); for (int i = 0; i < serversCount; i++) { for (int j = 0; j < daysCount; j++) { for (int c = 0; c < matrix[i, j]; c++) { ApiResponse putMatchResponse = new MatchController().PutMatch( endpoint: String.Format("test-server-{0}.com-8080", i), json: matchJson, timestamp: startTimestamp.AddDays(j).AddMinutes(c)); // add minutes to do unique (server, timestamp) Assert.AreEqual(HttpStatusCode.OK, putMatchResponse.Status); } } } // act ApiResponse getPopularServersResponse = new ServerController().GetPopularServers(3); Assert.AreEqual(HttpStatusCode.OK, getPopularServersResponse.Status); List <ServerController.PopularServerJson> actualPopularServers = JsonConvert.DeserializeObject <List <ServerController.PopularServerJson> >(getPopularServersResponse.Body); var expectesPopularServers = new List <ServerController.PopularServerJson> { new ServerController.PopularServerJson { avgMatches = 5, Endpoint = "test-server-2.com-8080", Name = "test_server_2" }, new ServerController.PopularServerJson { avgMatches = 4, Endpoint = "test-server-3.com-8080", Name = "test_server_3" }, new ServerController.PopularServerJson { avgMatches = 3, Endpoint = "test-server-4.com-8080", Name = "test_server_4" } }; // assert CollectionAssert.AreEqual(expectesPopularServers, actualPopularServers); }
/// <summary> /// Returns <see cref="ApiResponse"/> with string representation of <see cref="PlayerStatsJson"/> in body. /// </summary> /// <param name="name"></param> /// <returns><see cref="ApiResponse"/> with string representation of <see cref="PlayerStatsJson"/> in body.</returns> public ApiResponse GetStats(string name) { using (var context = new GameStatsDbDataContext()) { var currPlayer = context.Players.Where(pl => pl.name == name).FirstOrDefault(); if (currPlayer == null) { return(new ApiResponse(HttpStatusCode.NotFound)); } int currPlayerId = currPlayer.id; PlayerStatsJson playerStats = new PlayerStatsJson(); /*totalMatchesPlayed*/ playerStats.TotalMatchesPlayed = context.PlayersInMatches .Where(m => m.player_id == currPlayerId) .Count(); /*totalMatchesWon*/ playerStats.TotalMatchesWon = context.Matches .Where(m => m.winner_id == currPlayerId) .Count(); // join player's row in match with info about match var playerMatches = (from playerInMatch in context.PlayersInMatches where playerInMatch.player_id == currPlayerId join match in context.Matches on playerInMatch.match_id equals match.id select new { matchInfo = match, playerInfo = playerInMatch }); // group by server_id, then count it // use it in follow queries var orderedUniqueServers = (from p in playerMatches group p.matchInfo.server_id by p.matchInfo.server_id into serverGroup orderby serverGroup.Count() descending select serverGroup); /*favoriteServer*/ // take top1 server endpoint int top1serverId = orderedUniqueServers.First().Key; playerStats.FavoriteServer = context.Servers .Where(s => s.id == top1serverId) // top1 server .First() .endpoint; /*uniqueServers*/ // count all unqiue servers playerStats.UniqueServers = orderedUniqueServers.Count(); /*favoriteGM*/ int favGMid = (from p in playerMatches group p.matchInfo by p.matchInfo.gm_id into gmGroup orderby gmGroup.Count() descending select gmGroup) .First().Key; playerStats.FavoriteGameMode = context.GameModes .Where(gm => gm.id == favGMid) .First().name; /*averageScoreboardPercent*/ playerStats.AverageScoreboardPercent = (from p in playerMatches let players_count = p.matchInfo.players_count select(players_count == 1 ? 100 : (players_count - p.playerInfo.player_rank) * 100.0 / (players_count - 1) ) ) .Average(); /*matchesPerDay*/ var matchesPerDays = (from p in playerMatches group p.matchInfo by p.matchInfo.timestamp_day into matchGroup //group by constant to use 2 aggregates group matchGroup by 1 into matchGroup select new { maximum = matchGroup.Max (m => m.Count()), average = matchGroup.Average (m => m.Count()) }).First(); /*maximumMatchesPerDay*/ playerStats.MaximumMatchesPerDay = matchesPerDays.maximum; /*averageMatchesPerDay*/ playerStats.AverageMatchesPerDay = matchesPerDays.average; /*lastMatchPlayed*/ playerStats.LastMatchPlayed = (from p in playerMatches orderby p.matchInfo.timestamp descending select p.matchInfo.timestamp) .First(); // add "Z" to date playerStats.LastMatchPlayed = DateTime.SpecifyKind(playerStats.LastMatchPlayed, DateTimeKind.Utc); /*killToDeathRatio*/ playerStats.KillToDeathRatio = (from p in playerMatches //group by constant to use 2 aggregates group p.playerInfo by 1 into gr select(double) gr.Sum(x => x.kills) / gr.Sum(x => x.deaths)) .First(); return(new ApiResponse( body: JsonConvert.SerializeObject(playerStats))); } }
public void GetBestPlayersTest() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); context.ExecuteCommand("DELETE FROM Matches"); context.ExecuteCommand("DELETE FROM Players"); context.ExecuteCommand("DELETE FROM Maps"); context.ExecuteCommand("DELETE FROM GameModes"); context.ExecuteCommand("DELETE FROM ServersByDay"); context.ExecuteCommand("DELETE FROM PlayersInMatches"); } // put server ServerController.ServerInfoJson server = new ServerController.ServerInfoJson { Name = "test_server_1", GameModes = new List <string> { "DM", "TDM" } }; string serverJson = JsonConvert.SerializeObject(server); ApiResponse putServerResponse = new ServerController().PutInfo("test-server.com-8080", serverJson); Assert.AreEqual(HttpStatusCode.OK, putServerResponse.Status); // put some matches var match = new MatchController.MatchJson { FragLimit = 100, GameMode = "DM", Map = "test_map", TimeElapsed = 10, TimeLimit = 20, Scoreboard = new List <MatchController.ScoreboardRecordJson> { new MatchController.ScoreboardRecordJson { Deaths = 0, Frags = 100, Kills = 100, Name = "test_player_1" }, new MatchController.ScoreboardRecordJson { Deaths = 1, Frags = 10, Kills = 10, Name = "test_player_2" }, new MatchController.ScoreboardRecordJson { Deaths = 10, Frags = 1, Kills = 1, Name = "test_player_3" }, new MatchController.ScoreboardRecordJson { Deaths = 1, Frags = 0, Kills = 0, Name = "test_player_4" } } }; string matchJson = JsonConvert.SerializeObject(match); DateTime timestamp = Convert.ToDateTime("2017-01-22T15:11:12Z"); for (int i = 0; i < 10; i++) { ApiResponse putMatchResponse = new MatchController().PutMatch("test-server.com-8080", matchJson, timestamp.AddMinutes(i)); Assert.AreEqual(HttpStatusCode.OK, putMatchResponse.Status); } // act // ignore test_player_1 with 0 deaths var expectedBestPlayers = new List <PlayerController.BestPlayerJson> { new PlayerController.BestPlayerJson { Name = "test_player_2", KDR = 10 }, new PlayerController.BestPlayerJson { Name = "test_player_3", KDR = 0.1 }, new PlayerController.BestPlayerJson { Name = "test_player_4", KDR = 0 }, }; ApiResponse getBestPlayersResponse = new PlayerController().GetBestPlayers(5); Assert.AreEqual(HttpStatusCode.OK, getBestPlayersResponse.Status); List <PlayerController.BestPlayerJson> actualBestPlayers = JsonConvert.DeserializeObject <List <PlayerController.BestPlayerJson> >(getBestPlayersResponse.Body); // assert CollectionAssert.AreEqual(expectedBestPlayers, actualBestPlayers); }
private GameModesOnServers addLinkGameModeOnServer(GameModes gm, Servers server, GameStatsDbDataContext context) { var links = context.GameModesOnServers .Where(gmOnserv => gmOnserv.gm_id == gm.id && gmOnserv.server_id == server.id); if (links.Count() > 0) { // link is created already return(links.First()); } else { // create link var link = new GameModesOnServers() { gm_id = gm.id, server_id = server.id }; context.GameModesOnServers.InsertOnSubmit(link); context.SubmitChanges(); return(link); } }
public void GetServersInfo() { // arrange using (var context = new GameStatsDbDataContext()) { context.ExecuteCommand("DELETE FROM Servers"); } ServerController.ServerInfoJson server1 = new ServerController.ServerInfoJson { Name = "test_server_1", GameModes = new List <string> { "DM", "TDM" } }; string server1json = JsonConvert.SerializeObject(server1); ServerController.ServerInfoJson server2 = new ServerController.ServerInfoJson { Name = "test_server_2", GameModes = new List <string> { "DM", "TDM", "CTF" } }; string server2json = JsonConvert.SerializeObject(server2); ServerController.ServerInfoJson server3 = new ServerController.ServerInfoJson { Name = "test_server_3", GameModes = new List <string> { "CTF", "TDM" } }; string server3json = JsonConvert.SerializeObject(server3); ServerController.ServersInfoRecordJson server1record = new ServerController.ServersInfoRecordJson { Endpoint = "server1.com-8080", Info = server1 }; ServerController.ServersInfoRecordJson server2record = new ServerController.ServersInfoRecordJson { Endpoint = "server2.com-8080", Info = server2 }; ServerController.ServersInfoRecordJson server3record = new ServerController.ServersInfoRecordJson { Endpoint = "server3.com-8080", Info = server3 }; // act ApiResponse putResponse1 = new ServerController().PutInfo("server1.com-8080", server1json); ApiResponse putResponse2 = new ServerController().PutInfo("server2.com-8080", server2json); ApiResponse putResponse3 = new ServerController().PutInfo("server3.com-8080", server3json); Assert.AreEqual(HttpStatusCode.OK, putResponse1.Status); Assert.AreEqual(HttpStatusCode.OK, putResponse2.Status); Assert.AreEqual(HttpStatusCode.OK, putResponse3.Status); ApiResponse getResponse = new ServerController().GetInfo(); List <ServerController.ServersInfoRecordJson> servers = JsonConvert.DeserializeObject <List <ServerController.ServersInfoRecordJson> >(getResponse.Body); Assert.AreEqual(3, servers.Count); CollectionAssert.AreEqual( new List <ServerController.ServersInfoRecordJson> { server1record, server2record, server3record }, servers.OrderBy(s => s.Endpoint).ToList()); // assert Assert.AreEqual(HttpStatusCode.OK, getResponse.Status); }
/// <summary> /// Returns <see cref="ApiResponse"/> with string representation of <see cref="ServerStatsJson"/> in body. /// </summary> /// <param name="endpoint"></param> /// <returns></returns> public ApiResponse GetStats(string endpoint) { using (var context = new GameStatsDbDataContext()) { int server_id = (from server in context.Servers where server.endpoint == endpoint select server.id).FirstOrDefault(); // server_id is identity (1,1), so if server_id is 0 <=> there is no server with such endpoint if (server_id == 0) { return(new ApiResponse(System.Net.HttpStatusCode.NotFound)); } var matchesOnCurrentServer = context.Matches .Where(match => match.server_id == server_id); ServerStatsJson result = new ServerStatsJson(); result.TotalMatchesPlayed = matchesOnCurrentServer.Count(); if (result.TotalMatchesPlayed == 0) { // trivial stats return(new ApiResponse( body: JsonConvert.SerializeObject(ServerStatsJson.Trivial()))); } var matchesPerDay = (from match in matchesOnCurrentServer group match by match.timestamp_day into matchGroup //group by constant to use 2 aggregates group matchGroup by 1 into matchGroup select new { maximum = matchGroup.Max (m => m.Count()), average = matchGroup.Average (m => m.Count()) }) .First(); result.MaximumMatchesPerDay = matchesPerDay.maximum; result.AverageMatchesPerDay = matchesPerDay.average; result.MaximumPopulation = matchesOnCurrentServer .Select(match => match.players_count) .Max(); result.AveragePopulation = matchesOnCurrentServer .Select(match => match.players_count) .Average(); result.Top5GameModes = (from match in matchesOnCurrentServer group match by match.gm_id into matchGroup orderby matchGroup.Count() descending join gm in context.GameModes on matchGroup.Key equals gm.id select gm.name) .Take(5).ToList(); result.Top5Maps = (from match in matchesOnCurrentServer group match by match.map_id into matchGroup orderby matchGroup.Count() descending join map in context.Maps on matchGroup.Key equals map.id select map.name) .Take(5).ToList(); return(new ApiResponse( body: JsonConvert.SerializeObject(result))); } }