aboutsummaryrefslogtreecommitdiff
path: root/backend/controllers/mapController.go
diff options
context:
space:
mode:
authorNidboj132 <lol2s@vp.plm>2023-07-12 17:58:23 +0200
committerNidboj132 <lol2s@vp.plm>2023-07-12 17:58:23 +0200
commit781289455037431d8adbaa0b293b755c88169747 (patch)
tree773824f97c3b21d353b9066afdbde30bee2da4c5 /backend/controllers/mapController.go
parentsummary (diff)
parentfix: 0 score count / showcase not required (#47) (diff)
downloadlphub-781289455037431d8adbaa0b293b755c88169747.tar.gz
lphub-781289455037431d8adbaa0b293b755c88169747.tar.bz2
lphub-781289455037431d8adbaa0b293b755c88169747.zip
Merge branch 'main' of https://github.com/pektezol/LeastPortals
Former-commit-id: af8d8680aafc3d662f8b53a4f50f0ea356b26c26
Diffstat (limited to 'backend/controllers/mapController.go')
-rw-r--r--backend/controllers/mapController.go146
1 files changed, 58 insertions, 88 deletions
diff --git a/backend/controllers/mapController.go b/backend/controllers/mapController.go
index d8783b7..e7c5566 100644
--- a/backend/controllers/mapController.go
+++ b/backend/controllers/mapController.go
@@ -3,111 +3,81 @@ package controllers
3import ( 3import (
4 "net/http" 4 "net/http"
5 "strconv" 5 "strconv"
6 "time"
7 6
8 "github.com/gin-gonic/gin" 7 "github.com/gin-gonic/gin"
9 "github.com/lib/pq"
10 "github.com/pektezol/leastportals/backend/database" 8 "github.com/pektezol/leastportals/backend/database"
11 "github.com/pektezol/leastportals/backend/models" 9 "github.com/pektezol/leastportals/backend/models"
12) 10)
13 11
14// GET Map Summary 12// GET Map Summary
15// 13//
16// @Summary Get map summary with specified id. 14// @Description Get map summary with specified id.
17// @Tags maps 15// @Tags maps
18// @Produce json 16// @Produce json
19// @Param id path int true "Map ID" 17// @Param id path int true "Map ID"
20// @Success 200 {object} models.Response{data=models.Map{data=models.MapSummary}} 18// @Success 200 {object} models.Response{data=models.MapSummaryResponse}
21// @Failure 400 {object} models.Response 19// @Failure 400 {object} models.Response
22// @Router /maps/{id}/summary [get] 20// @Router /maps/{id}/summary [get]
23func FetchMapSummary(c *gin.Context) { 21func FetchMapSummary(c *gin.Context) {
24 id := c.Param("id") 22 id := c.Param("id")
25 // Get map data 23 response := models.MapSummaryResponse{Map: models.Map{}, Summary: models.MapSummary{Routes: []models.MapRoute{}}}
26 var mapData models.Map
27 var mapSummaryData models.MapSummary
28 var mapHistoryData []models.MapHistory
29 intID, err := strconv.Atoi(id) 24 intID, err := strconv.Atoi(id)
30 if err != nil { 25 if err != nil {
31 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error())) 26 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error()))
32 return 27 return
33 } 28 }
34 mapData.ID = intID 29 // Get map data
35 var routers pq.StringArray 30 response.Map.ID = intID
36 sql := `SELECT g.name, c.name, m.name, m.description, m.showcase, 31 sql := `SELECT m.id, g.name, c.name, m.name, m.image, g.is_coop
37 (
38 SELECT array_agg(user_name)
39 FROM map_routers
40 WHERE map_id = $1
41 AND score_count = (
42 SELECT score_count
43 FROM map_history
44 WHERE map_id = $1
45 ORDER BY score_count
46 LIMIT 1
47 )
48 GROUP BY map_routers.user_name
49 ORDER BY user_name
50 ),
51 (
52 SELECT COALESCE(avg(rating), 0.0)
53 FROM map_ratings
54 WHERE map_id = $1
55 )
56 FROM maps m 32 FROM maps m
57 INNER JOIN games g ON m.game_id = g.id 33 INNER JOIN games g ON m.game_id = g.id
58 INNER JOIN chapters c ON m.chapter_id = c.id 34 INNER JOIN chapters c ON m.chapter_id = c.id
59 WHERE m.id = $1` 35 WHERE m.id = $1`
60 // TODO: CategoryScores 36 err = database.DB.QueryRow(sql, id).Scan(&response.Map.ID, &response.Map.GameName, &response.Map.ChapterName, &response.Map.MapName, &response.Map.Image, &response.Map.IsCoop)
61 err = database.DB.QueryRow(sql, id).Scan(&mapData.GameName, &mapData.ChapterName, &mapData.MapName, &mapSummaryData.Description, &mapSummaryData.Showcase, &routers, &mapSummaryData.Rating)
62 if err != nil { 37 if err != nil {
63 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error())) 38 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error()))
64 return 39 return
65 } 40 }
66 var historyNames pq.StringArray 41 // Get map routes and histories
67 var historyScores pq.Int32Array 42 sql = `SELECT r.id, c.id, c.name, h.user_name, h.score_count, h.record_date, r.description, r.showcase, COALESCE(avg(rating), 0.0) FROM map_routes r
68 var historyDates pq.StringArray 43 INNER JOIN categories c ON r.category_id = c.id
69 sql = `SELECT array_agg(user_name), array_agg(score_count), array_agg(record_date) 44 INNER JOIN map_history h ON r.map_id = h.map_id AND r.category_id = h.category_id
70 FROM map_history 45 LEFT JOIN map_ratings rt ON r.map_id = rt.map_id AND r.category_id = rt.category_id
71 WHERE map_id = $1` 46 WHERE r.map_id = $1 AND h.score_count = r.score_count GROUP BY r.id, c.id, h.user_name, h.score_count, h.record_date, r.description, r.showcase
72 err = database.DB.QueryRow(sql, id).Scan(&historyNames, &historyScores, &historyDates) 47 ORDER BY h.record_date ASC;`
48 rows, err := database.DB.Query(sql, id)
73 if err != nil { 49 if err != nil {
74 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error())) 50 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error()))
75 return 51 return
76 } 52 }
77 for i := 0; i < len(historyNames); i++ { 53 for rows.Next() {
78 var history models.MapHistory 54 route := models.MapRoute{Category: models.Category{}, History: models.MapHistory{}}
79 history.RunnerName = historyNames[i] 55 err = rows.Scan(&route.RouteID, &route.Category.ID, &route.Category.Name, &route.History.RunnerName, &route.History.ScoreCount, &route.History.Date, &route.Description, &route.Showcase, &route.Rating)
80 history.ScoreCount = int(historyScores[i])
81 layout := "2006-01-02 15:04:05"
82 date, err := time.Parse(layout, historyDates[i])
83 if err != nil { 56 if err != nil {
84 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error())) 57 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error()))
85 return 58 return
86 } 59 }
87 history.Date = date 60 response.Summary.Routes = append(response.Summary.Routes, route)
88 mapHistoryData = append(mapHistoryData, history)
89 } 61 }
90 mapSummaryData.History = mapHistoryData
91 mapSummaryData.Routers = routers
92 mapData.Data = mapSummaryData
93 // Return response 62 // Return response
94 c.JSON(http.StatusOK, models.Response{ 63 c.JSON(http.StatusOK, models.Response{
95 Success: true, 64 Success: true,
96 Message: "Successfully retrieved map summary.", 65 Message: "Successfully retrieved map summary.",
97 Data: mapData, 66 Data: response,
98 }) 67 })
99} 68}
100 69
101// GET Map Leaderboards 70// GET Map Leaderboards
102// 71//
103// @Summary Get map leaderboards with specified id. 72// @Description Get map leaderboards with specified id.
104// @Tags maps 73// @Tags maps
105// @Produce json 74// @Produce json
106// @Param id path int true "Map ID" 75// @Param id path int true "Map ID"
107// @Success 200 {object} models.Response{data=models.Map{data=models.MapRecords}} 76// @Success 200 {object} models.Response{data=models.Map{data=models.MapRecords}}
108// @Failure 400 {object} models.Response 77// @Failure 400 {object} models.Response
109// @Router /maps/{id}/leaderboards [get] 78// @Router /maps/{id}/leaderboards [get]
110func FetchMapLeaderboards(c *gin.Context) { 79func FetchMapLeaderboards(c *gin.Context) {
80 // TODO: make new response type
111 id := c.Param("id") 81 id := c.Param("id")
112 // Get map data 82 // Get map data
113 var mapData models.Map 83 var mapData models.Map
@@ -119,12 +89,12 @@ func FetchMapLeaderboards(c *gin.Context) {
119 return 89 return
120 } 90 }
121 mapData.ID = intID 91 mapData.ID = intID
122 sql := `SELECT g.name, c.name, m.name, is_disabled 92 sql := `SELECT g.name, c.name, m.name, is_disabled, m.image
123 FROM maps m 93 FROM maps m
124 INNER JOIN games g ON m.game_id = g.id 94 INNER JOIN games g ON m.game_id = g.id
125 INNER JOIN chapters c ON m.chapter_id = c.id 95 INNER JOIN chapters c ON m.chapter_id = c.id
126 WHERE m.id = $1` 96 WHERE m.id = $1`
127 err = database.DB.QueryRow(sql, id).Scan(&mapData.GameName, &mapData.ChapterName, &mapData.MapName, &isDisabled) 97 err = database.DB.QueryRow(sql, id).Scan(&mapData.GameName, &mapData.ChapterName, &mapData.MapName, &isDisabled, &mapData.Image)
128 if err != nil { 98 if err != nil {
129 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error())) 99 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error()))
130 return 100 return
@@ -205,7 +175,7 @@ func FetchMapLeaderboards(c *gin.Context) {
205 } 175 }
206 mapRecordsData.Records = records 176 mapRecordsData.Records = records
207 } 177 }
208 mapData.Data = mapRecordsData 178 // mapData.Data = mapRecordsData
209 // Return response 179 // Return response
210 c.JSON(http.StatusOK, models.Response{ 180 c.JSON(http.StatusOK, models.Response{
211 Success: true, 181 Success: true,
@@ -216,14 +186,14 @@ func FetchMapLeaderboards(c *gin.Context) {
216 186
217// GET Games 187// GET Games
218// 188//
219// @Summary Get games from the leaderboards. 189// @Description Get games from the leaderboards.
220// @Tags games & chapters 190// @Tags games & chapters
221// @Produce json 191// @Produce json
222// @Success 200 {object} models.Response{data=[]models.Game} 192// @Success 200 {object} models.Response{data=[]models.Game}
223// @Failure 400 {object} models.Response 193// @Failure 400 {object} models.Response
224// @Router /games [get] 194// @Router /games [get]
225func FetchGames(c *gin.Context) { 195func FetchGames(c *gin.Context) {
226 rows, err := database.DB.Query(`SELECT id, name FROM games`) 196 rows, err := database.DB.Query(`SELECT id, name, is_coop FROM games`)
227 if err != nil { 197 if err != nil {
228 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error())) 198 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error()))
229 return 199 return
@@ -231,7 +201,7 @@ func FetchGames(c *gin.Context) {
231 var games []models.Game 201 var games []models.Game
232 for rows.Next() { 202 for rows.Next() {
233 var game models.Game 203 var game models.Game
234 if err := rows.Scan(&game.ID, &game.Name); err != nil { 204 if err := rows.Scan(&game.ID, &game.Name, &game.IsCoop); err != nil {
235 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error())) 205 c.JSON(http.StatusBadRequest, models.ErrorResponse(err.Error()))
236 return 206 return
237 } 207 }
@@ -246,13 +216,13 @@ func FetchGames(c *gin.Context) {
246 216
247// GET Chapters of a Game 217// GET Chapters of a Game
248// 218//
249// @Summary Get chapters from the specified game id. 219// @Description Get chapters from the specified game id.
250// @Tags games & chapters 220// @Tags games & chapters
251// @Produce json 221// @Produce json
252// @Param id path int true "Game ID" 222// @Param id path int true "Game ID"
253// @Success 200 {object} models.Response{data=models.ChaptersResponse} 223// @Success 200 {object} models.Response{data=models.ChaptersResponse}
254// @Failure 400 {object} models.Response 224// @Failure 400 {object} models.Response
255// @Router /games/{id} [get] 225// @Router /games/{id} [get]
256func FetchChapters(c *gin.Context) { 226func FetchChapters(c *gin.Context) {
257 gameID := c.Param("id") 227 gameID := c.Param("id")
258 intID, err := strconv.Atoi(gameID) 228 intID, err := strconv.Atoi(gameID)
@@ -288,13 +258,13 @@ func FetchChapters(c *gin.Context) {
288 258
289// GET Maps of a Chapter 259// GET Maps of a Chapter
290// 260//
291// @Summary Get maps from the specified chapter id. 261// @Description Get maps from the specified chapter id.
292// @Tags games & chapters 262// @Tags games & chapters
293// @Produce json 263// @Produce json
294// @Param id path int true "Chapter ID" 264// @Param id path int true "Chapter ID"
295// @Success 200 {object} models.Response{data=models.ChapterMapsResponse} 265// @Success 200 {object} models.Response{data=models.ChapterMapsResponse}
296// @Failure 400 {object} models.Response 266// @Failure 400 {object} models.Response
297// @Router /chapters/{id} [get] 267// @Router /chapters/{id} [get]
298func FetchChapterMaps(c *gin.Context) { 268func FetchChapterMaps(c *gin.Context) {
299 chapterID := c.Param("id") 269 chapterID := c.Param("id")
300 intID, err := strconv.Atoi(chapterID) 270 intID, err := strconv.Atoi(chapterID)