diff --git a/internal/handler/dashboard.go b/internal/handler/dashboard.go index 4d6440d..0d7038c 100644 --- a/internal/handler/dashboard.go +++ b/internal/handler/dashboard.go @@ -29,7 +29,8 @@ func NewDashboard(r *Render, d *service.Dashboard) Dashboard { func (handler DashboardImpl) Handle(router *http.ServeMux) { router.Handle("GET /dashboard", handler.handleDashboard()) - router.Handle("GET /dashboard/dataset", handler.handleDashboardDataset()) + router.Handle("GET /dashboard/main-chart", handler.handleDashboardMainChart()) + router.Handle("GET /dashboard/treasure-chests", handler.handleDashboardTreasureChests()) } func (handler DashboardImpl) handleDashboard() http.HandlerFunc { @@ -47,7 +48,7 @@ func (handler DashboardImpl) handleDashboard() http.HandlerFunc { } } -func (handler DashboardImpl) handleDashboardDataset() http.HandlerFunc { +func (handler DashboardImpl) handleDashboardMainChart() http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { updateSpan(r) @@ -105,3 +106,56 @@ func (handler DashboardImpl) handleDashboardDataset() http.HandlerFunc { } } } + +func (handler DashboardImpl) handleDashboardTreasureChests() http.HandlerFunc { + return func(w http.ResponseWriter, r *http.Request) { + updateSpan(r) + + user := middleware.GetUser(r) + + treeList, err := handler.d.TreasureChests(r.Context(), user) + if err != nil { + handleError(w, r, err) + return + } + + w.Header().Set("Content-Type", "application/json") + w.WriteHeader(http.StatusOK) + + data := "" + for _, item := range treeList { + children := "" + for _, child := range item.Children { + if child.Value < 0 { + children += fmt.Sprintf(`{"name":"%s\n%.2f €","value":%d},`, child.Name, float64(child.Value)/100, -child.Value) + } else { + children += fmt.Sprintf(`{"name":"%s\n%.2f €","value":%d},`, child.Name, float64(child.Value)/100, child.Value) + } + } + children = children[:len(children)-1] + data += fmt.Sprintf(`{"name":"%s","children":[%s]},`, item.Name, children) + } + data = data[:len(data)-1] + + _, err = fmt.Fprintf(w, ` + { + "aria": { + "enabled": true, + "decal": { + "show": false + } + }, + "series": [ + { + "data": [%s], + "type": "treemap", + "name": "Savings" + } + ] + } + `, data) + if err != nil { + slog.InfoContext(r.Context(), "could not write response", "err", err) + } + } +} diff --git a/internal/service/dashboard.go b/internal/service/dashboard.go index 4726434..6f70bae 100644 --- a/internal/service/dashboard.go +++ b/internal/service/dashboard.go @@ -75,3 +75,40 @@ func (s Dashboard) MainChart( return timeEntries, nil } + +func (s Dashboard) TreasureChests( + ctx context.Context, + user *types.User, +) ([]*types.DashboardTreasureChest, error) { + if user == nil { + return nil, ErrUnauthorized + } + + treasureChests := make([]*types.TreasureChest, 0) + err := s.db.SelectContext(ctx, &treasureChests, `SELECT * FROM treasure_chest WHERE user_id = ?`, user.Id) + err = db.TransformAndLogDbError(ctx, "dashboard TreasureChests", nil, err) + if err != nil { + return nil, err + } + + treasureChests = sortTreasureChests(treasureChests) + + result := make([]*types.DashboardTreasureChest, 0) + for _, t := range treasureChests { + if t.ParentId == nil { + result = append(result, &types.DashboardTreasureChest{ + Name: t.Name, + Value: t.CurrentBalance, + Children: make([]types.DashboardTreasureChest, 0), + }) + } else { + result[len(result)-1].Children = append(result[len(result)-1].Children, types.DashboardTreasureChest{ + Name: t.Name, + Value: t.CurrentBalance, + Children: make([]types.DashboardTreasureChest, 0), + }) + } + } + + return result, nil +} diff --git a/internal/service/treasure_chest.go b/internal/service/treasure_chest.go index 645dfbc..54e0ed5 100644 --- a/internal/service/treasure_chest.go +++ b/internal/service/treasure_chest.go @@ -205,7 +205,7 @@ func (s TreasureChestImpl) GetAll(ctx context.Context, user *types.User) ([]*typ return nil, err } - return sortTree(treasureChests), nil + return sortTreasureChests(treasureChests), nil } func (s TreasureChestImpl) Delete(ctx context.Context, user *types.User, idStr string) error { @@ -277,7 +277,7 @@ func (s TreasureChestImpl) Delete(ctx context.Context, user *types.User, idStr s return nil } -func sortTree(nodes []*types.TreasureChest) []*types.TreasureChest { +func sortTreasureChests(nodes []*types.TreasureChest) []*types.TreasureChest { var ( roots []*types.TreasureChest ) diff --git a/internal/template/dashboard/dashboard.templ b/internal/template/dashboard/dashboard.templ index 362cf96..5e98fb3 100644 --- a/internal/template/dashboard/dashboard.templ +++ b/internal/template/dashboard/dashboard.templ @@ -2,6 +2,7 @@ package dashboard templ Dashboard() {