From 796886f49fef3b9b0f4a2b9692408b3bf142ba7b Mon Sep 17 00:00:00 2001 From: blazSmehov Date: Wed, 1 Apr 2026 12:54:17 +0200 Subject: [PATCH] feat: add implementation where you can get last track for each unique tracker id --- internal/app/server/routes.go | 1 + internal/pkg/controller/tracks_controller.go | 51 ++++++++++++++++++++ 2 files changed, 52 insertions(+) diff --git a/internal/app/server/routes.go b/internal/app/server/routes.go index 197ac35..6240d97 100644 --- a/internal/app/server/routes.go +++ b/internal/app/server/routes.go @@ -59,6 +59,7 @@ func (a *ServerApp) RegisterRoutes() http.Handler { // Tracks r.HandleFunc("/reslevis/getTracks/{id}", controller.TracksListController(a.DB, a.ctx)).Methods("GET") + r.HandleFunc("/reslevis/getTracks", controller.TracksListAllController(a.DB, a.ctx)).Methods("GET") r.HandleFunc("/reslevis/health", controller.HealthController(a.AppState, a.ctx)).Methods("GET") diff --git a/internal/pkg/controller/tracks_controller.go b/internal/pkg/controller/tracks_controller.go index dd69c8e..d01c5d1 100644 --- a/internal/pkg/controller/tracks_controller.go +++ b/internal/pkg/controller/tracks_controller.go @@ -2,6 +2,7 @@ package controller import ( "context" + "log/slog" "net/http" "strconv" "time" @@ -42,3 +43,53 @@ func TracksListController(db *gorm.DB, context context.Context) http.HandlerFunc response.JSON(w, http.StatusOK, tracks) } } + +func TracksListAllController(db *gorm.DB, context context.Context) http.HandlerFunc { + return func(w http.ResponseWriter, r *http.Request) { + query := r.URL.Query() + lStr := query.Get("limit") + if lStr == "" { + lStr = "100" + } + + limit, err := strconv.Atoi(lStr) + if err != nil { + slog.Error("Error in converting limit string to integer value") + response.InternalError(w, "internal server error", err) + return + } + + offsetStr := query.Get("offset") + if offsetStr == "" { + offsetStr = "0" + } + + offset, err := strconv.Atoi(offsetStr) + if err != nil { + slog.Error("Error in converting offset string to integer value") + response.InternalError(w, "internal server error", err) + return + } + + var tracks []model.Tracks + + // Subquery to get the latest timestamp per tracker + subQuery := db.Model(&model.Tracks{}). + Select("tracker, MAX(timestamp) AS max_timestamp"). + Group("tracker") + + if err := db.WithContext(context). + Table("tracks"). + Select("tracks.*"). + Joins("JOIN (?) AS latest ON tracks.tracker = latest.tracker AND tracks.timestamp = latest.max_timestamp", subQuery). + Order("tracks.timestamp DESC"). + Limit(limit). + Offset(offset). + Find(&tracks).Error; err != nil { + response.InternalError(w, "failed to list tracks", err) + return + } + + response.JSON(w, http.StatusOK, tracks) + } +}