Aller au contenu

Local (Dev)

Objectif & portée

Horodatage

  • Tous les timestamps JSON sont au format ISO 8601 UTC (suffixe Z). L'affichage local (UTC+1) est une option UI uniquement.

  • Exécuter SalamBot en local pour développement, tests et démos.

  • Stack par défaut: Docker Compose; notes K8s local (kind/microk8s) optionnelles.
  • Inclure observabilité minimale, persistance et données d'exemple.

Architecture locale (aperçu)

Service Port Rôle
gateway 8080 API/ingress
orchestrateur 8081 coordination
nlu 8082 NLU/LLM wrapper
rag 8083 retrieval
postgres 5432 métadonnées
redis 6379 cache/queues
qdrant 6333 Vector DB
minio 9000/9001 objets (KB/documents) + console
prometheus 9090 métriques
grafana 3001 dashboards
otel-collector 4317/4318 OTLP gRPC/HTTP → export observabilité
tempo 3200 traces distribuées

Prérequis

⚠️ Sécurité dev vs prod
Les identifiants par défaut (ex. Grafana admin/admin, MinIO admin/admin) et services non chiffrés sont réservés au local. En prod/on-prem : changer tous les mots de passe, activer TLS (ingress + MinIO console), restreindre l'accès à Grafana/Prometheus (IP/VPN/SSO) et désactiver les consoles publiques inutiles.

  • Docker ≥ 24 et Compose v2
  • Make (optionnel), Git
  • CPU 4+, RAM 8 Go+, 10 Go disque libres
  • Accès aux images et secrets requis (dev)

URL rapides d'observabilité

Interfaces principales

Service URL Login par défaut Description
Prometheus http://localhost:9090 - Métriques et requêtes PromQL
Grafana http://localhost:3000 admin/admin Dashboards et visualisations
Tempo http://localhost:3200 - API traces (via Grafana)

Pages utiles

  • Prometheus Targets : http://localhost:9090/targets
  • Prometheus Graph : http://localhost:9090/graph
  • Prometheus Alerts : http://localhost:9090/alerts
  • Grafana Explore : http://localhost:3000/explore

Requêtes PromQL de base

# Taux de requêtes HTTP par seconde
sum(rate(http_requests_total[1m]))

# Latence P95 par route
histogram_quantile(0.95, sum(rate(http_server_duration_ms_bucket[5m])) by (le,route))

# Erreurs RAG
sum(rate(rag_search_errors_total[5m]))

# Santé des services
up{job="otel-collector"}

Vérifications rapides

# Métriques du collector
curl -s http://localhost:8889/metrics | head

# Targets Prometheus
curl -s http://localhost:9090/api/v1/targets | jq '.data.activeTargets[] | {job, instance, health, lastScrape}'

# Test requête PromQL
curl -s "http://localhost:9090/api/v1/query?query=up" | jq '.data.result[] | {metric, value}'

Démarrage des services

  • Si votre docker-compose.yml utilise des profiles, activez l'observabilité (inclut otel-collector) :
docker compose --profile observability up -d

Mise en route rapide

  1. Cloner le repo et se placer à la racine.
  2. Copier .env.example vers .env et ajuster.
  3. Lancer docker compose up -d (ou make up).
  4. Vérifier docker compose ps puis /health.
  5. Ouvrir Grafana : http://localhost:3001
git clone <repo>
cd salambot
cp .env.example .env
docker compose up -d
curl -f http://localhost:8080/health

Configuration .env (extraits)

  • Variables clés: TENANT=demo, OPENAI_API_KEY=..., RAG_PROVIDER=qdrant.
  • Endpoints internes pointent sur localhost et ports ci-dessus.
  • Sécurité: valeurs dev uniquement, ne pas committer.
TENANT=demo
OPENAI_API_KEY=sk-...
POSTGRES_URL=postgres://salambot:salambot@postgres:5432/salambot
REDIS_URL=redis://redis:6379
QDRANT_URL=http://qdrant:6333
MINIO_ENDPOINT=http://minio:9000
MINIO_ROOT_USER=admin
MINIO_ROOT_PASSWORD=adminadmin
MINIO_CONSOLE=http://localhost:9001
# Export OTLP vers l'OTel Collector (HTTP 4318)
OTEL_EXPORTER_OTLP_ENDPOINT=http://otel-collector:4318
OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf

Données & persistance

  • Volumes Docker pour Postgres, MinIO, Qdrant.
  • Seed de données démo (tenant, KB) via scripts.
  • Commandes pour reset sélectif (DB/KV/Vector).

Initialisation MinIO (avant seed)

docker compose exec minio mc alias set local http://minio:9000 \
  "$MINIO_ROOT_USER" "$MINIO_ROOT_PASSWORD"
docker compose exec minio mc mb -p local/salambot-kb || true
docker compose exec minio mc policy set public local/salambot-kb
docker compose exec orchestrateur python -m salambot.jobs.seed_kb --tenant demo --incremental
# Reset Qdrant (attention: destructif)
curl -X DELETE http://localhost:6333/collections/salambot-kb

Observabilité locale

Services d'observabilité

Service Port URL Rôle
Prometheus 9090 http://localhost:9090 Métriques et alertes
Grafana 3001 http://localhost:3001 Dashboards (admin/admin)
OpenTelemetry 4317 http://localhost:4317 OTLP gRPC (traces/métriques)
OpenTelemetry 4318 http://localhost:4318 OTLP HTTP (traces/métriques)
Collector Metrics 8889 http://localhost:8889/metrics Métriques Prometheus du Collector
Tempo 3200 http://localhost:3200 Backend traces (Jaeger-compatible)

Dashboards Grafana disponibles

  1. API Overview (salambot-api-overview) :
  2. Taux de requêtes API (RPS)
  3. Latence API P50/P95/P99 avec exemplars
  4. Taux d'erreur 4xx/5xx
  5. Disponibilité SLO (99.9% target)

  6. RAG Overview (salambot-rag-overview) :

  7. Recherches RAG vers Qdrant (RPS)
  8. Latence recherche P50/P95/P99
  9. Taux d'erreur RAG
  10. Statut Qdrant et fiabilité

  11. OpenTelemetry Infrastructure (salambot-otel-infra) :

  12. Statut Collector/Prometheus/Grafana
  13. Débit spans et métriques
  14. Taux d'erreur export
  15. Utilisation mémoire

Exemples PromQL utiles

# Latence P95 API Gateway
histogram_quantile(0.95, sum(rate(http_request_duration_ms_bucket{job="salambot-gateway"}[5m])) by (le, route))

# Taux d'erreur 5xx sur 5 minutes
sum(rate(http_requests_total{job="salambot-gateway", code=~"5.."}[5m])) / sum(rate(http_requests_total{job="salambot-gateway"}[5m])) * 100

# Recherches RAG par seconde
sum(rate(rag_search_total{db_system="qdrant"}[5m])) by (peer_service)

# Latence recherche Qdrant P99
histogram_quantile(0.99, sum(rate(rag_search_latency_ms_bucket{db_system="qdrant"}[5m])) by (le))

# Disponibilité services SalamBot
avg_over_time(up{job=~"salambot-.*"}[5m])

Alertes configurées

  • Latence API : P95 > 2s ou P99 > 5s pendant 5 minutes
  • Taux d'erreur : 5xx > 5% ou erreurs RAG > 2% pendant 5 minutes
  • Disponibilité : Qdrant down ou services SalamBot indisponibles

Accès rapide

# macOS
open http://localhost:9090 || true  # Prometheus
open http://localhost:3001 || true  # Grafana
# Linux
xdg-open http://localhost:9090 || true
xdg-open http://localhost:3001 || true
# Logs
docker compose logs -f gateway orchestrateur nlu rag
# Métriques directes
curl http://localhost:8889/metrics  # Collector
curl http://localhost:8080/metrics  # Gateway
curl http://localhost:8083/metrics  # RAG

Tests fumée

  • Vérifier santé services (health checks).
  • Générer une réponse et vérifier TTFB.
  • Tester recherche RAG.
TOKEN="dev-token" # adapter si auth activée
TENANT="demo"

# Health
curl -H "Authorization: Bearer $TOKEN" \
     -H "X-SalamBot-Tenant: $TENANT" \
     http://localhost:8080/health

# Génération (endpoint canonique)
curl -X POST http://localhost:8080/v1/generate/reply \
  -H 'Content-Type: application/json' \
  -H "Authorization: Bearer $TOKEN" \
  -H "X-SalamBot-Tenant: $TENANT" \
  -d '{
    "schema_version":"1.0",
    "tenant":"demo",
    "channel":"webchat",
    "message_id":"msg_smoke",
    "correlation_id":"corr_smoke",
    "timestamp":"2025-08-14T10:00:00Z",
    "locale":"fr-MA",
    "data":{"prompt":"Bonjour","context":[]}
  }'

# Recherche RAG (endpoint canonique)
curl -X POST http://localhost:8080/v1/search/query \
  -H 'Content-Type: application/json' \
  -H "Authorization: Bearer $TOKEN" \
  -H "X-SalamBot-Tenant: $TENANT" \
  -d '{"query":"test","tenant":"demo","top_k":3}'

# Note: si l'environnement DEV désactive l'auth, retirer les en-têtes
# Authorization/X-SalamBot-Tenant et documenter clairement cette exception.

Tests et validation

Tests de bout en bout

# Tests Gateway (smoke tests)
cd services/gateway
pnpm test

# Tests RAG (endpoints + métriques)
cd services/rag
pnpm test

# Tests NLU
cd services/nlu
pnpm test

# Tests Orchestrator
cd services/orchestrator
pnpm test

# Tests script seed-kb (nécessite Qdrant actif)
npx vitest run scripts/tests/seed-kb.test.ts

Validation des endpoints

# Health checks
curl http://localhost:8080/health
curl http://localhost:8081/health
curl http://localhost:8082/health
curl http://localhost:8083/health

# Test search endpoint
curl -X POST http://localhost:8080/v1/search/query \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer test-token" \
  -H "X-SalamBot-Tenant: demo" \
  -d '{"query": "comment utiliser SalamBot", "top_k": 5}'

# Test generate endpoint
curl -X POST http://localhost:8080/v1/generate/reply \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer test-token" \
  -H "X-SalamBot-Tenant: demo" \
  -d '{"query": "Bonjour, comment ça va?"}'

# Métriques Prometheus
curl http://localhost:8083/metrics

Note API : webhooks & signatures HMAC centralisés dans API/reference.md#webhooks.

Troubleshooting

  • Conflits de ports: modifier mapping dans compose.
  • Mémoire insuffisante: réduire réplicas, désactiver services non utilisés.
  • Démarrage lent DB/Vector: relancer rag après qdrant prêt.
  • Erreur de secrets: vérifier .env et variables exportées.
  • Certificats/SSL locaux: utiliser HTTP interne en dev.

Démarrage ordonné (healthchecks)

# extrait docker-compose.yml
services:
  qdrant:
    healthcheck:
      test: ['CMD', 'curl', '-f', 'http://localhost:6333/collections']
      interval: 10s
      timeout: 3s
      retries: 12
  postgres:
    healthcheck:
      test: ['CMD-SHELL', 'pg_isready -U salambot -d salambot']
      interval: 10s
      timeout: 3s
      retries: 12
  redis:
    healthcheck:
      test: ['CMD', 'redis-cli', 'ping']
      interval: 10s
      timeout: 3s
      retries: 12
  rag:
    depends_on:
      qdrant:
        condition: service_healthy
  orchestrateur:
    depends_on:
      postgres:
        condition: service_healthy
      redis:
        condition: service_healthy

Endpoints canoniques

  • Utiliser uniquement : /v1/generate/reply et /v1/search/query.
  • Supprimer toute référence à des variantes (/generate/reply, /v1/chat/completions, etc.).

Cohérence API: utilisez les chemins canoniques décrits dans API/reference.md. Si plusieurs variantes existent (/v1/generate/reply, /v1/chat/completions), indiquez celle supportée localement.

Nettoyage

  1. Arrêt: docker compose down
  2. Purge volumes (destructif): docker compose down -v
  3. Suppression images optionnelle: docker image prune

Notes K8s local (optionnel)

  • Déploiement rapide avec kind: kind create cluster.
  • Utiliser manifests allégés + NodePort.
  • Observabilité via kube-prometheus-stack (profil dev).

Références croisées

Horodatage des exemples : UTC Z uniquement (affichage local optionnel).