Add day-grouped timesheet with day accept and commit history

This commit is contained in:
2026-09-14 15:04:55 +02:00
parent dcd2e97a1d
commit 75e47d7f40
4 changed files with 124 additions and 20 deletions
+29
View File
@@ -42,6 +42,11 @@ def derive_zed_suggestions(db: Session, device_id: str, project_slug: str, idle_
TimeEntry.kind == "zed_inferred",
TimeEntry.status == "suggested",
))
existing_ids = set(db.scalars(select(TimeEntry.external_id).where(
TimeEntry.source == "zed",
TimeEntry.device_id == device_id,
TimeEntry.project_slug == project_slug,
)))
blocks: list[tuple[datetime, datetime, int]] = []
start = previous = None
@@ -59,6 +64,11 @@ def derive_zed_suggestions(db: Session, device_id: str, project_slug: str, idle_
for start_at, end_at, duration in blocks:
entry_id = stable_id(device_id, project_slug, start_at.isoformat(), end_at.isoformat())
# Blocks whose stable ID already exists (accepted, rejected, or still
# suggested) must not be re-added: the unique constraint would reject
# the insert, and user decisions about a block must stick.
if entry_id in existing_ids:
continue
db.add(TimeEntry(
source="zed", device_id=device_id, external_id=entry_id, kind="zed_inferred",
status="suggested", start_at=start_at, end_at=end_at, duration_seconds=duration,
@@ -85,3 +95,22 @@ def daily_summary(entries: list[TimeEntry]) -> dict:
elif entry.status == "suggested":
suggestions += entry.duration_seconds
return {"by_day": dict(totals), "suggested_seconds": suggestions}
def group_entries_by_day(entries: list[TimeEntry]) -> dict:
days: dict = defaultdict(list)
for entry in entries:
days[entry.start_at.astimezone(TZ).date()].append(entry)
for day_entries in days.values():
day_entries.sort(key=lambda item: item.start_at)
return dict(days)
def group_commits_by_day(commits: list[RawEvent]) -> dict:
days: dict = defaultdict(list)
for commit in commits:
if commit.occurred_at is not None:
days[commit.occurred_at.astimezone(TZ).date()].append(commit)
for day_commits in days.values():
day_commits.sort(key=lambda item: item.occurred_at)
return dict(days)