File size: 2,264 Bytes
4b8eb24
04c4194
4b8eb24
 
 
 
 
 
 
 
12bad22
4b8eb24
 
12bad22
4b8eb24
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
12bad22
4b8eb24
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
12bad22
4b8eb24
 
 
 
 
 
 
12bad22
4b8eb24
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
"""
DocuLens - Runs & Stats API endpoints.

Provides /api/v1/runs, /api/v1/runs/:id, and /api/v1/runs/stats
for the dashboard and ingestion views.
"""

import logging
from typing import Optional

from fastapi import APIRouter, Query, HTTPException, Depends

from db.supabase import list_runs, get_run, get_stats, is_enabled
from middleware import check_rate_limit

logger = logging.getLogger(__name__)

runs_router = APIRouter()


@runs_router.get("/api/v1/runs")
async def api_list_runs(
    status: Optional[str] = Query(None, description="Filter by status: running|completed|failed"),
    result: Optional[str] = Query(None, description="Filter by result: passed|failed|needs_review"),
    use_case: Optional[str] = Query(None, description="Filter by use case slug"),
    search: Optional[str] = Query(None, description="Search by filename"),
    page: int = Query(1, ge=1),
    per_page: int = Query(25, ge=1, le=100),
    org_id: Optional[str] = Query(None),
    user_id: Optional[str] = Query(None),
    api_key: str = Depends(check_rate_limit),
):
    """List pipeline runs with filtering and pagination."""
    if not is_enabled():
        return {
            "runs": [],
            "pagination": {"page": 1, "per_page": per_page, "total": 0, "pages": 0},
        }

    return list_runs(
        org_id=org_id,
        user_id=user_id,
        status=status,
        result=result,
        use_case=use_case,
        search=search,
        page=page,
        per_page=per_page,
    )


@runs_router.get("/api/v1/runs/stats")
async def api_run_stats(
    period_days: int = Query(30, ge=1, le=365),
    org_id: Optional[str] = Query(None),
    user_id: Optional[str] = Query(None),
    api_key: str = Depends(check_rate_limit),
):
    """Get aggregate stats for the dashboard."""
    return get_stats(org_id=org_id, user_id=user_id, period_days=period_days)



@runs_router.get("/api/v1/runs/{run_id}")
async def api_get_run(run_id: str, api_key: str = Depends(check_rate_limit)):
    """Get a single run with full stage details."""
    if not is_enabled():
        raise HTTPException(status_code=404, detail="Run not found")

    run = get_run(run_id)
    if not run:
        raise HTTPException(status_code=404, detail="Run not found")
    return run