summaryrefslogtreecommitdiff
path: root/internal/handlers/handlers.go
diff options
context:
space:
mode:
authorPeter Stone <thepeterstone@gmail.com>2026-01-26 08:10:27 -1000
committerPeter Stone <thepeterstone@gmail.com>2026-01-26 08:10:27 -1000
commit2e739638477e87a1b1df662740f191c86db60186 (patch)
tree302916e1e0c99ae47213128fa79133752203a271 /internal/handlers/handlers.go
parentaff60af8ba24c8d5330c706ddf26927d81436d79 (diff)
Phase 5: Extract functions to reduce complexity
- Create atoms.go with BuildUnifiedAtomList, SortAtomsByUrgency, PartitionAtomsByTime - Create helpers.go with parseFormOr400, requireFormValue - Refactor HandleTabTasks from 95 lines to 25 lines using extracted functions - Remove duplicate atomUrgencyTier function - Update handlers to use parseFormOr400 helper Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Diffstat (limited to 'internal/handlers/handlers.go')
-rw-r--r--internal/handlers/handlers.go97
1 files changed, 5 insertions, 92 deletions
diff --git a/internal/handlers/handlers.go b/internal/handlers/handlers.go
index 635a69d..595ab67 100644
--- a/internal/handlers/handlers.go
+++ b/internal/handlers/handlers.go
@@ -511,8 +511,7 @@ func (h *Handler) HandleCreateCard(w http.ResponseWriter, r *http.Request) {
// HandleCompleteCard marks a Trello card as complete
func (h *Handler) HandleCompleteCard(w http.ResponseWriter, r *http.Request) {
- if err := r.ParseForm(); err != nil {
- JSONError(w, http.StatusBadRequest, "Failed to parse form", err)
+ if !parseFormOr400(w, r) {
return
}
@@ -822,8 +821,7 @@ func (h *Handler) HandleGetBugs(w http.ResponseWriter, r *http.Request) {
// HandleReportBug saves a new bug report
func (h *Handler) HandleReportBug(w http.ResponseWriter, r *http.Request) {
- if err := r.ParseForm(); err != nil {
- JSONError(w, http.StatusBadRequest, "Invalid form data", err)
+ if !parseFormOr400(w, r) {
return
}
@@ -962,82 +960,14 @@ func (h *Handler) HandleUpdateTask(w http.ResponseWriter, r *http.Request) {
// HandleTabTasks renders the unified Tasks tab (Todoist + Trello cards with due dates + Bugs)
func (h *Handler) HandleTabTasks(w http.ResponseWriter, r *http.Request) {
- tasks, err := h.store.GetTasks()
+ atoms, boards, err := BuildUnifiedAtomList(h.store)
if err != nil {
JSONError(w, http.StatusInternalServerError, "Failed to fetch tasks", err)
return
}
- boards, err := h.store.GetBoards()
- if err != nil {
- JSONError(w, http.StatusInternalServerError, "Failed to fetch boards", err)
- return
- }
-
- bugs, err := h.store.GetUnresolvedBugs()
- if err != nil {
- log.Printf("Warning: failed to fetch bugs: %v", err)
- bugs = nil
- }
-
- atoms := make([]models.Atom, 0)
-
- for _, task := range tasks {
- if !task.Completed {
- atoms = append(atoms, models.TaskToAtom(task))
- }
- }
-
- for _, board := range boards {
- for _, card := range board.Cards {
- if card.DueDate != nil || isActionableList(card.ListName) {
- atoms = append(atoms, models.CardToAtom(card))
- }
- }
- }
-
- // Add unresolved bugs as atoms
- for _, bug := range bugs {
- atoms = append(atoms, models.BugToAtom(models.Bug{
- ID: bug.ID,
- Description: bug.Description,
- CreatedAt: bug.CreatedAt,
- }))
- }
-
- for i := range atoms {
- atoms[i].ComputeUIFields()
- }
-
- sort.SliceStable(atoms, func(i, j int) bool {
- tierI := atomUrgencyTier(atoms[i])
- tierJ := atomUrgencyTier(atoms[j])
-
- if tierI != tierJ {
- return tierI < tierJ
- }
-
- if atoms[i].DueDate != nil && atoms[j].DueDate != nil {
- if !atoms[i].DueDate.Equal(*atoms[j].DueDate) {
- return atoms[i].DueDate.Before(*atoms[j].DueDate)
- }
- }
-
- return atoms[i].Priority > atoms[j].Priority
- })
-
- var currentAtoms, futureAtoms []models.Atom
- for _, a := range atoms {
- // Don't show recurring tasks until the day they're due
- if a.IsRecurring && a.IsFuture {
- continue
- }
- if a.IsFuture {
- futureAtoms = append(futureAtoms, a)
- } else {
- currentAtoms = append(currentAtoms, a)
- }
- }
+ SortAtomsByUrgency(atoms)
+ currentAtoms, futureAtoms := PartitionAtomsByTime(atoms)
data := struct {
Atoms []models.Atom
@@ -1436,23 +1366,6 @@ func isActionableList(name string) bool {
strings.Contains(lower, "today")
}
-// atomUrgencyTier returns the urgency tier for sorting
-func atomUrgencyTier(a models.Atom) int {
- if a.DueDate == nil {
- return 4
- }
- if a.IsOverdue {
- return 0
- }
- if a.IsFuture {
- return 3
- }
- if a.HasSetTime {
- return 1
- }
- return 2
-}
-
// ScheduledItem represents a scheduled event or task for the planning view
type ScheduledItem struct {
Type string