From 4378d354f432e7f261dfe6c7d3d9d4867b366f8e Mon Sep 17 00:00:00 2001 From: Abhimanyu Saharan Date: Wed, 4 Mar 2026 16:11:14 +0530 Subject: [PATCH] fix(ci): resolve backend check failures in dashboard metrics --- backend/app/api/activity.py | 13 ++++----- backend/app/api/metrics.py | 26 +++++++----------- backend/tests/test_activity_api_rows.py | 4 +-- backend/tests/test_metrics_kpis.py | 35 ++++++++++++++++++++----- 4 files changed, 43 insertions(+), 35 deletions(-) diff --git a/backend/app/api/activity.py b/backend/app/api/activity.py index a9b453ca..fb68ed40 100644 --- a/backend/app/api/activity.py +++ b/backend/app/api/activity.py @@ -248,14 +248,11 @@ async def list_activity( actor: ActorContext = ACTOR_DEP, ) -> LimitOffsetPage[ActivityEventRead]: """List activity events visible to the calling actor.""" - statement: Any = ( - select( - ActivityEvent, - col(ActivityEvent.board_id).label("event_board_id"), - col(Task.board_id).label("task_board_id"), - ) - .outerjoin(Task, col(ActivityEvent.task_id) == col(Task.id)) - ) + statement: Any = select( + ActivityEvent, + col(ActivityEvent.board_id).label("event_board_id"), + col(Task.board_id).label("task_board_id"), + ).outerjoin(Task, col(ActivityEvent.task_id) == col(Task.id)) if actor.actor_type == "agent" and actor.agent: statement = statement.where(col(ActivityEvent.agent_id) == actor.agent.id) elif actor.actor_type == "user" and actor.user: diff --git a/backend/app/api/metrics.py b/backend/app/api/metrics.py index ba05e8be..cd716952 100644 --- a/backend/app/api/metrics.py +++ b/backend/app/api/metrics.py @@ -423,15 +423,7 @@ async def _pending_approvals_snapshot( rows = ( await session.exec( - select( - col(Approval.id), - col(Approval.board_id), - col(Board.name), - col(Approval.action_type), - col(Approval.confidence), - col(Approval.created_at), - col(Task.title), - ) + select(Approval, Board, Task) .join(Board, col(Board.id) == col(Approval.board_id)) .outerjoin(Task, col(Task.id) == col(Approval.task_id)) .where(col(Approval.board_id).in_(board_ids)) @@ -443,15 +435,15 @@ async def _pending_approvals_snapshot( items = [ DashboardPendingApproval( - approval_id=approval_id, - board_id=board_id, - board_name=board_name, - action_type=action_type, - confidence=float(confidence), - created_at=created_at, - task_title=task_title, + approval_id=approval.id, + board_id=approval.board_id, + board_name=board.name, + action_type=approval.action_type, + confidence=float(approval.confidence), + created_at=approval.created_at, + task_title=task.title if task is not None else None, ) - for approval_id, board_id, board_name, action_type, confidence, created_at, task_title in rows + for approval, board, task in rows ] return DashboardPendingApprovals(total=total, items=items) diff --git a/backend/tests/test_activity_api_rows.py b/backend/tests/test_activity_api_rows.py index f632afb4..d371dd28 100644 --- a/backend/tests/test_activity_api_rows.py +++ b/backend/tests/test_activity_api_rows.py @@ -129,9 +129,7 @@ def test_coerce_activity_rows_rejects_invalid_values(): event = _make_event() with pytest.raises( TypeError, - match=( - "Expected \\(ActivityEvent, event_board_id, task_board_id\\) rows" - ), + match="Expected \\(ActivityEvent, event_board_id, task_board_id\\) rows", ): _coerce_activity_rows([(event, "bad", None)]) diff --git a/backend/tests/test_metrics_kpis.py b/backend/tests/test_metrics_kpis.py index ce33cdbb..f346a140 100644 --- a/backend/tests/test_metrics_kpis.py +++ b/backend/tests/test_metrics_kpis.py @@ -6,6 +6,9 @@ from uuid import uuid4 import pytest from app.api import metrics as metrics_api +from app.models.approvals import Approval +from app.models.boards import Board +from app.models.tasks import Task class _ExecResult: @@ -97,16 +100,34 @@ async def test_pending_approvals_snapshot_returns_empty_for_empty_scope() -> Non async def test_pending_approvals_snapshot_maps_rows() -> None: approval_id = uuid4() board_id = uuid4() + organization_id = uuid4() + task_id = uuid4() created_at = datetime(2026, 3, 4, 12, 0, 0) + approval = Approval( + id=approval_id, + board_id=board_id, + task_id=task_id, + action_type="approve_task", + confidence=87.0, + created_at=created_at, + status="pending", + ) + board = Board( + id=board_id, + organization_id=organization_id, + name="Operations Board", + slug="operations-board", + ) + task = Task( + id=task_id, + board_id=board_id, + title="Validate rollout checklist", + ) rows: list[tuple[object, ...]] = [ ( - approval_id, - board_id, - "Operations Board", - "approve_task", - 87.0, - created_at, - "Validate rollout checklist", + approval, + board, + task, ) ] session = _SequentialSession(