Add honeycomb completion heatmap and data migration framework

- Add completion_summary endpoint data to residence detail response
- Track completed_from_column on task completions (overdue/due_soon/upcoming)
- Add GetCompletionSummary repo method with monthly aggregation
- Add one-time data migration framework (data_migrations table + registry)
- Add backfill migration to classify historical completions
- Add standalone backfill script for manual/dry-run usage

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Trey t
2026-03-12 00:05:10 -05:00
parent 739b245ee6
commit 6803f6ec18
12 changed files with 958 additions and 21 deletions

View File

@@ -58,8 +58,9 @@ func (s *ResidenceService) SetSubscriptionService(subService *SubscriptionServic
s.subscriptionService = subService
}
// GetResidence gets a residence by ID with access check
func (s *ResidenceService) GetResidence(residenceID, userID uint) (*responses.ResidenceResponse, error) {
// GetResidence gets a residence by ID with access check.
// The `now` parameter is used for timezone-aware completion summary aggregation.
func (s *ResidenceService) GetResidence(residenceID, userID uint, now time.Time) (*responses.ResidenceResponse, error) {
// Check access
hasAccess, err := s.residenceRepo.HasAccess(residenceID, userID)
if err != nil {
@@ -78,6 +79,17 @@ func (s *ResidenceService) GetResidence(residenceID, userID uint) (*responses.Re
}
resp := responses.NewResidenceResponse(residence)
// Attach completion summary (honeycomb grid data)
if s.taskRepo != nil {
summary, err := s.taskRepo.GetCompletionSummary(residenceID, now, 10)
if err != nil {
log.Warn().Err(err).Uint("residence_id", residenceID).Msg("Failed to fetch completion summary")
} else {
resp.CompletionSummary = summary
}
}
return &resp, nil
}