# Kanban - mockupAWS

> **Progetto:** mockupAWS - Backend Profiler & Cost Estimator  
> **Versione Target:** v0.2.0  
> **Data:** 2026-04-07  
> **Principio:** Little Often - Task < 2 ore

---

## Legenda

- 🔴 **TODO** - Da fare
- 🟡 **IN PROGRESS** - In corso
- 🟢 **DONE** - Completato
- ⚪ **BLOCKED** - Bloccato

**Stime:** XS (15-30min) | S (30-60min) | M (1-2h) | L (2-4h) | XL (>4h, da spezzare)

---

## 🔴 TODO - Fase 1: Database & Backend Core

### Database Setup (DB-001 → DB-006)

#### DB-001: Alembic Setup
**Assegnato:** @db-engineer  
**Priorità:** Alta  
**Stima:** S

**Descrizione:**
Configurare Alembic per migrazioni database async.

**Criteri Done:**
- [ ] Installare alembic e asyncpg
- [ ] Inizializzare `alembic init`
- [ ] Configurare `alembic.ini` con async URL
- [ ] Configurare `alembic/env.py` per SQLAlchemy 2.0 async
- [ ] Testare `alembic current` (connessione OK)

**Files:**
- `backend/alembic.ini`
- `backend/alembic/env.py`

---

#### DB-002: Migration - Scenarios Table
**Assegnato:** @db-engineer  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** DB-001

**Descrizione:**
Creare migrazione per tabella scenarios con tutti i campi e constraints.

**Criteri Done:**
- [ ] Creare migration `001_create_scenarios_table.py`
- [ ] Definire tutti i campi (id, name, description, tags, status, region, timestamps, totals)
- [ ] Aggiungere constraints (CHK, FK)
- [ ] Aggiungere indexes (status, region, created_at, tags)
- [ ] Creare trigger updated_at
- [ ] Testare `alembic upgrade head`

**SQL Reference:** Vedere `export/architecture.md` sezione 3.2

---

#### DB-003: Migration - Scenario Logs Table
**Assegnato:** @db-engineer  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** DB-002

**Descrizione:**
Creare migrazione per tabella scenario_logs.

**Criteri Done:**
- [ ] Creare migration `002_create_scenario_logs_table.py`
- [ ] Definire campi (id, scenario_id, timestamps, hash, preview, etc.)
- [ ] Aggiungere FK a scenarios con ON DELETE CASCADE
- [ ] Aggiungere indexes (scenario_id, received_at, hash, has_pii)
- [ ] Testare relazione con scenarios

---

#### DB-004: Migration - Scenario Metrics Table
**Assegnato:** @db-engineer  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** DB-002

**Descrizione:**
Creare migrazione per tabella scenario_metrics (time-series).

**Criteri Done:**
- [ ] Creare migration `003_create_scenario_metrics_table.py`
- [ ] Definire campi per metriche time-series
- [ ] Aggiungere indexes (scenario_id, timestamp, metric_type)
- [ ] Testare query aggregazione

---

#### DB-005: Migration - AWS Pricing Table
**Assegnato:** @db-engineer  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** DB-002

**Descrizione:**
Creare migrazione per tabella aws_pricing con storico prezzi.

**Criteri Done:**
- [ ] Creare migration `004_create_aws_pricing_table.py`
- [ ] Definire campi (service, region, tier, price, unit, dates)
- [ ] Aggiungere constraints (price > 0, valid dates)
- [ ] Aggiungere unique constraint parziale per active prices
- [ ] Testare query get_active_pricing

---

#### DB-006: Migration - Reports Table
**Assegnato:** @db-engineer  
**Priorità:** Media  
**Stima:** S  
**Dipende da:** DB-002

**Descrizione:**
Creare migrazione per tabella reports.

**Criteri Done:**
- [ ] Creare migration `005_create_reports_table.py`
- [ ] Definire campi (format, file_path, metadata)
- [ ] Aggiungere indexes

---

#### DB-007: Seed AWS Pricing Data
**Assegnato:** @db-engineer  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** DB-005

**Descrizione:**
Popolare tabella aws_pricing con dati reali.

**Criteri Done:**
- [ ] Creare migration `006_seed_aws_pricing.py` (opzionale: file separato)
- [ ] Inserire prezzi per us-east-1:
  - SQS: $0.40 per milione richieste
  - Lambda Request: $0.20 per milione
  - Lambda Compute: $0.0000166667 per GB-second
  - Bedrock Claude Input: $0.003 per 1K tokens
  - Bedrock Claude Output: $0.015 per 1K tokens
- [ ] Inserire prezzi per eu-west-1 (simili)
- [ ] Verificare dati inseriti

**Dati:** Vedere `export/prd.md` sezione 4.3

---

### Backend - Database Layer (BE-001 → BE-005)

#### BE-001: Database Connection & Session Management
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** DB-001

**Descrizione:**
Configurare SQLAlchemy 2.0 async con gestione sessioni.

**Criteri Done:**
- [ ] Creare `backend/src/core/database.py`
- [ ] Configurare `create_async_engine` con pool
- [ ] Creare `AsyncSessionLocal` factory
- [ ] Creare `get_db()` dependency per FastAPI
- [ ] Testare connessione in test

**Codice Target:**
```python
# core/database.py
from sqlalchemy.ext.asyncio import create_async_engine, AsyncSession
from sqlalchemy.orm import sessionmaker

engine = create_async_engine(DATABASE_URL, echo=True, future=True)
AsyncSessionLocal = sessionmaker(engine, class_=AsyncSession, expire_on_commit=False)

async def get_db():
    async with AsyncSessionLocal() as session:
        yield session
```

---

#### BE-002: SQLAlchemy Models
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** L  
**Dipende da:** BE-001

**Descrizione:**
Creare tutti i modelli SQLAlchemy corrispondenti alle tabelle.

**Criteri Done:**
- [ ] Creare `backend/src/models/base.py` (Base, TimestampMixin)
- [ ] Creare `scenario.py` (Scenario model)
- [ ] Creare `scenario_log.py` (ScenarioLog model)
- [ ] Creare `scenario_metric.py` (ScenarioMetric model)
- [ ] Creare `aws_pricing.py` (AwsPricing model)
- [ ] Creare `report.py` (Report model)
- [ ] Definire tutte le relationships
- [ ] Testare models (creazione istanze)

**Files:**
- `backend/src/models/__init__.py`
- `backend/src/models/base.py`
- `backend/src/models/scenario.py`
- `backend/src/models/scenario_log.py`
- `backend/src/models/scenario_metric.py`
- `backend/src/models/aws_pricing.py`
- `backend/src/models/report.py`

---

#### BE-003: Pydantic Schemas
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** BE-002

**Descrizione:**
Creare Pydantic schemas per request/response validation.

**Criteri Done:**
- [ ] Creare `backend/src/schemas/scenario.py`
  - ScenarioCreate, ScenarioUpdate, ScenarioResponse, ScenarioList
- [ ] Creare `backend/src/schemas/log.py`
  - LogIngest, LogResponse
- [ ] Creare `backend/src/schemas/metric.py`
  - MetricSummary, CostBreakdown
- [ ] Creare `backend/src/schemas/pricing.py`
  - PricingResponse, PricingUpdate
- [ ] Creare `backend/src/schemas/report.py`
  - ReportRequest, ReportResponse
- [ ] Validators per campi (name not empty, valid region, etc.)

---

### Backend - Repository Layer (BE-004 → BE-008)

#### BE-004: Base Repository
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** BE-002

**Descrizione:**
Implementare Base Repository con operazioni CRUD generiche.

**Criteri Done:**
- [ ] Creare `backend/src/repositories/base.py`
- [ ] Implementare `BaseRepository` class (Generic[T])
- [ ] Metodi: get(), list(), create(), update(), delete(), count()
- [ ] Supporto per filters e pagination
- [ ] Type hints completi

**Codice Target:**
```python
class BaseRepository(Generic[T]):
    def __init__(self, model: Type[T]):
        self.model = model
    
    async def get(self, db: AsyncSession, id: UUID) -> T | None:
        result = await db.execute(select(self.model).where(self.model.id == id))
        return result.scalar_one_or_none()
    
    async def list(self, db: AsyncSession, skip: int = 0, limit: int = 100, **filters) -> list[T]:
        query = select(self.model)
        for key, value in filters.items():
            query = query.where(getattr(self.model, key) == value)
        query = query.offset(skip).limit(limit)
        result = await db.execute(query)
        return result.scalars().all()
```

---

#### BE-005: Scenario Repository
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** BE-004

**Descrizione:**
Implementare ScenarioRepository con metodi specifici.

**Criteri Done:**
- [ ] Creare `backend/src/repositories/scenario_repo.py`
- [ ] Estendere BaseRepository
- [ ] Metodi specifici:
  - `get_by_name()`
  - `list_by_status()`
  - `list_by_region()`
  - `update_status()`
  - `increment_total_requests()`
  - `update_total_cost()`
- [ ] Testare tutti i metodi

---

#### BE-006: Log Repository
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** S  
**Dipende da:** BE-004

**Descrizione:**
Implementare LogRepository.

**Criteri Done:**
- [ ] Creare `backend/src/repositories/log_repo.py`
- [ ] Metodi specifici:
  - `get_by_hash()` - per deduplicazione
  - `list_by_scenario()`
  - `count_by_scenario()`
  - `count_pii_by_scenario()`

---

#### BE-007: Metric Repository
**Assegnato:** @backend-dev  
**Priorità:** Media  
**Stima:** S  
**Dipende da:** BE-004

**Descrizione:**
Implementare MetricRepository.

**Criteri Done:**
- [ ] Creare `backend/src/repositories/metric_repo.py`
- [ ] Metodi specifici:
  - `get_aggregated_by_scenario()`
  - `list_by_type()`
  - `get_cost_breakdown()`

---

#### BE-008: Pricing Repository
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** S  
**Dipende da:** BE-004

**Descrizione:**
Implementare PricingRepository.

**Criteri Done:**
- [ ] Creare `backend/src/repositories/pricing_repo.py`
- [ ] Metodi specifici:
  - `get_active_by_service_region()` - CRITICO per calcolo costi
  - `list_active()`

---

### Backend - Service Layer (BE-009 → BE-014)

#### BE-009: Cost Calculator Service
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** BE-008

**Descrizione:**
Implementare servizio calcolo costi usando prezzi da database.

**Criteri Done:**
- [ ] Creare `backend/src/services/cost_calculator.py`
- [ ] Metodi:
  - `calculate_sqs_cost(blocks, region)`
  - `calculate_lambda_cost(invocations, gb_seconds, region)`
  - `calculate_bedrock_cost(input_tokens, output_tokens, region)`
  - `calculate_total_cost(log_entry, region)`
- [ ] Query pricing repository per prezzi attivi
- [ ] Formule corrette (vedi architecture.md)
- [ ] Unit tests con mock pricing

---

#### BE-010: Scenario Service
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** L  
**Dipende da:** BE-005

**Descrizione:**
Implementare ScenarioService con business logic.

**Criteri Done:**
- [ ] Creare `backend/src/services/scenario_service.py`
- [ ] Metodi CRUD:
  - `create_scenario(data)`
  - `get_scenario(id)`
  - `list_scenarios(filters, pagination)`
  - `update_scenario(id, data)`
  - `delete_scenario(id)`
- [ ] Metodi lifecycle:
  - `start_scenario(id)` - draft → running
  - `stop_scenario(id)` - running → completed
  - `archive_scenario(id)` - completed → archived
- [ ] Validazioni (name unique, valid transitions)
- [ ] Unit tests

---

#### BE-011: Ingest Service
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** L  
**Dipende da:** BE-006, BE-009

**Descrizione:**
Implementare IngestService per elaborazione log.

**Criteri Done:**
- [ ] Creare `backend/src/services/ingest_service.py`
- [ ] Metodi:
  - `ingest_log(scenario_id, log_data)` - MAIN METHOD
  - `validate_scenario(scenario_id)` - check status == running
  - `process_log(log_data)` - calcola metriche
  - `persist_log(scenario_id, processed_log)` - salva su DB
  - `update_scenario_metrics(scenario_id, metrics)`
- [ ] Integrare PII detection
- [ ] Integrare token counting
- [ ] Integrare SQS block calculation
- [ ] Integrare cost calculator
- [ ] Transaction management (DB commit)

---

#### BE-012: PII Detector Service
**Assegnato:** @backend-dev  
**Priorità:** Media  
**Stima:** S  
**Dipende da:** None

**Descrizione:**
Implementare servizio rilevamento PII (estrazione da main.py attuale).

**Criteri Done:**
- [ ] Creare `backend/src/services/pii_detector.py`
- [ ] Pattern regex per:
  - Email
  - SSN (opzionale)
  - Credit card (opzionale)
  - Phone (opzionale)
- [ ] Metodo `detect(message) -> dict`
- [ ] Unit tests con vari input

---

#### BE-013: Report Service (Base)
**Assegnato:** @backend-dev  
**Priorità:** Media  
**Stima:** M  
**Dipende da:** BE-007

**Descrizione:**
Implementare ReportService per generazione CSV.

**Criteri Done:**
- [ ] Creare `backend/src/services/report_service.py`
- [ ] Metodi:
  - `generate_csv(scenario_id)` - CSV export
  - `compile_metrics(scenario_id)` - aggrega dati
- [ ] CSV format con headers
- [ ] Unit tests

---

#### BE-014: Tokenizer Service (Refactor)
**Assegnato:** @backend-dev  
**Priorità:** Bassa  
**Stima:** XS  
**Dipende da:** None

**Descrizione:**
Refactor profilera esistente in servizio.

**Criteri Done:**
- [ ] Creare `backend/src/services/tokenizer_service.py`
- [ ] Spostare logica da `src/profiler.py`
- [ ] Mantenere encoding cl100k_base

---

### Backend - API Layer (BE-015 → BE-020)

#### BE-015: API Dependencies & Error Handling
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** None

**Descrizione:**
Configurare FastAPI dependencies e exception handlers.

**Criteri Done:**
- [ ] Creare `backend/src/api/deps.py`
  - `get_db()` - DB session
  - `get_current_scenario()` - scenario validation
- [ ] Creare `backend/src/core/exceptions.py`
  - AppException base
  - NotFoundException
  - ValidationException
  - ConflictException
- [ ] Creare exception handlers in `main.py`
- [ ] Global error response format

---

#### BE-016: Scenarios API Endpoints
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** L  
**Dipende da:** BE-010, BE-015

**Descrizione:**
Implementare tutti gli endpoint CRUD per scenari.

**Criteri Done:**
- [ ] Creare `backend/src/api/v1/scenarios.py`
- [ ] Endpoints:
  - `POST /api/v1/scenarios` - Create
  - `GET /api/v1/scenarios` - List (con pagination, filters)
  - `GET /api/v1/scenarios/{id}` - Get detail
  - `PUT /api/v1/scenarios/{id}` - Update
  - `DELETE /api/v1/scenarios/{id}` - Delete
  - `POST /api/v1/scenarios/{id}/start` - Start
  - `POST /api/v1/scenarios/{id}/stop` - Stop
  - `POST /api/v1/scenarios/{id}/archive` - Archive
- [ ] Integrare schemas per request/response
- [ ] Integration tests

---

#### BE-017: Ingest API Endpoint (Refactor)
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** BE-011, BE-016

**Descrizione:**
Aggiornare endpoint `/ingest` esistente per usare database.

**Criteri Done:**
- [ ] Refactor `backend/src/api/v1/ingest.py`
- [ ] Aggiungere header `X-Scenario-ID` required
- [ ] Validare scenario esiste e status == running
- [ ] Usare IngestService per elaborazione
- [ ] Rimuovere stato in-memory (mantenere solo per cache)
- [ ] Response 202 Accepted con log_id
- [ ] Integration tests

---

#### BE-018: Metrics API Endpoint
**Assegnato:** @backend-dev  
**Priorità:** Alta  
**Stima:** M  
**Dipende da:** BE-017

**Descrizione:**
Implementare endpoint metrics per scenari.

**Criteri Done:**
- [ ] Creare `backend/src/api/v1/metrics.py`
- [ ] Endpoints:
  - `GET /api/v1/scenarios/{id}/metrics` - Summary metrics
  - `GET /api/v1/scenarios/{id}/metrics/costs` - Cost breakdown
  - `GET /api/v1/scenarios/{id}/metrics/timeseries` - Time series
- [ ] Aggregare dati da scenario_logs e scenario_metrics
- [ ] Integration tests

---

#### BE-019: Pricing API Endpoints (Admin)
**Assegnato:** @backend-dev  
**Priorità:** Media  
**Stima:** S  
**Dipende da:** BE-016

**Descrizione:**
Implementare endpoint per gestione prezzi.

**Criteri Done:**
- [ ] Creare `backend/src/api/v1/pricing.py`
- [ ] Endpoints:
  - `GET /api/v1/pricing` - List
  - `POST /api/v1/pricing` - Create (admin)
  - `PUT /api/v1/pricing/{id}` - Update (admin)
- [ ] Integration tests

---

#### BE-020: Reports API Endpoint
**Assegnato:** @backend-dev  
**Priorità:** Media  
**Stima:** S  
**Dipende da:** BE-013

**Descrizione:**
Implementare endpoint report generation.

**Criteri Done:**
- [ ] Creare `backend/src/api/v1/reports.py`
- [ ] Endpoints:
  - `POST /api/v1/scenarios/{id}/reports` - Generate
  - `GET /api/v1/reports/{id}/download` - Download
- [ ] Supporto format CSV (PDF future)
- [ ] Integration tests

---

### Testing (QA-001 → QA-005)

#### QA-001: Unit Tests - Services
**Assegnato:** @qa-engineer + @backend-dev  
**Priorità:** Alta  
**Stima:** L  
**Dipende da:** BE-009, BE-010, BE-011

**Descrizione:**
Scrivere unit tests per tutti i services.

**Criteri Done:**
- [ ] `tests/unit/test_cost_calculator.py`
- [ ] `tests/unit/test_scenario_service.py`
- [ ] `tests/unit/test_ingest_service.py`
- [ ] `tests/unit/test_pii_detector.py`
- [ ] Mock repositories per isolamento
- [ ] Coverage > 80% per service

---

#### QA-002: Integration Tests - API
**Assegnato:** @qa-engineer + @backend-dev  
**Priorità:** Alta  
**Stima:** L  
**Dipende da:** BE-016, BE-017, BE-018

**Descrizione:**
Scrivere integration tests per API endpoints.

**Criteri Done:**
- [ ] `tests/integration/test_api_scenarios.py`
- [ ] `tests/integration/test_api_ingest.py`
- [ ] `tests/integration/test_api_metrics.py`
- [ ] Test database con rollback per test
- [ ] Test fixtures per dati

---

#### QA-003: E2E Test - Full Flow
**Assegnato:** @qa-engineer  
**Priorità:** Media  
**Stima:** M  
**Dipende da:** QA-002

**Descrizione:**
Test end-to-end del flusso completo.

**Criteri Done:**
- [ ] `tests/e2e/test_full_flow.py`
- [ ] Flow: Create → Start → Ingest 10 logs → Get Metrics → Stop
- [ ] Verifica costi calcolati correttamente

---

## 🟡 IN PROGRESS

*Vuoto - In attesa inizio Fase 1*

---

## 🟢 DONE

*Vuoto - Progetto appena iniziato*

---

## ⚪ BLOCKED

*Vuoto - Nessun blocco attuale*

---

## 📊 Summary

| Fase | Task Totali | Completati | In Progress | Todo |
|------|-------------|------------|-------------|------|
| Fase 1 - Database | 7 | 0 | 0 | 7 |
| Fase 1 - Backend DB | 5 | 0 | 0 | 5 |
| Fase 1 - Backend Repo | 5 | 0 | 0 | 5 |
| Fase 1 - Backend Service | 6 | 0 | 0 | 6 |
| Fase 1 - Backend API | 6 | 0 | 0 | 6 |
| Fase 1 - Testing | 3 | 0 | 0 | 3 |
| **TOTALE** | **32** | **0** | **0** | **32** |

---

## 🎯 Priorità per Sprint 1 (Week 1)

**Goal:** Database pronto e API base funzionanti

1. DB-001 → DB-003 (Database setup e prime 2 tabelle)
2. BE-001 → BE-003 (Connessione e models)
3. BE-004 → BE-005 (Base repo e scenario repo)
4. BE-009 (Cost calculator - critico)
5. BE-015 → BE-016 (API base e scenarios CRUD)

---

*Documento creato da @spec-architect*  
*Versione: 1.0*  
*Data: 2026-04-07*
