Saltar a contenido

ADR-032 · cis-sii-monitor → módulo tributario en cis-admin (pivot)

Fecha: 2026-05-04 Source: /srv/projects/cis/cis-plan/DECISIONS.md (do not edit here — re-split desde la fuente)


Contexto

/srv/projects/cds/cis/cis-sii-monitor/ fue creado como scaffolding en marzo 2026 con la idea de separar el "watcher" del SII en un microservicio propio (puerto :8262 reservado, DB propia cis_sii_monitor, stack FastAPI + Playwright + scheduler). El propio CLAUDE.md del repo reconoce que "al final este servicio se mergeará como módulo tributario dentro de cis-admin" — es decir, el scaffolding nació con fecha de caducidad.

Diagnóstico actualizado (agent-sii-monitor, 2026-05-04):

  • cis-sii-monitor/backend/ está vacío. Solo existen CLAUDE.md, AGENT-CONTEXT.md, README.md. 0 LOC implementadas.
  • cis-admin/frontend (SPA /tributario) ya tiene UI completa desde Fase D.2 (output agent-DE) — cards de "Datos SII", "Declaraciones vivas", "DTE en proceso", calendario de obligaciones.
  • cis-sii-gateway (servicio CIS, port :8270) ya hace todo el scrape/SOAP DTE y expone /sii/contribuyente/datos, /sii/libros, /sii/dte/pending. El watcher solo necesita hacer poll a este gateway, no scrape SII directo.

Arrancar el microservicio standalone hoy implicaría duplicar: DB, auth (OIDC), deploy (Caddy site + systemd unit + healthz), conexión a vault, conexión a cis-sii-gateway, y notificación (re-implementar email/whatsapp). Todo ya existe en cis-admin.

Decisión

  1. cis-sii-monitor queda deprecated. El repo se marca con DEPRECATED-SEE-cis-admin-tributario.md y CATALOGO §2 lo lista 🪦. No se borra (referencia histórica), pero no recibe más implementación.
  2. El watcher se implementa como módulo tributario dentro de cis-admin. Concretamente:
  3. app/services/sii_monitor.py · poll_sii_inbox() + process_incoming_dte() + notify_obligacion_proxima() + run_cycle().
  4. app/workers/sii_monitor_worker.py · arq + Redis. Cron job cada SII_MONITOR_POLL_SECONDS (default 600s).
  5. Tablas nuevas en DB cis_admin: dte_received (idempotente por (rut_emisor, tipo_dte, folio)) y obligacion_alert_log (anti-spam por bucket (obligacion_id, channel, days_before)). Migración SQL 046_sii_monitor_dte_alerts.sql.
  6. systemd unit cis-admin-sii-monitor.service (deploy/, no enabled todavía — pendiente humano).
  7. Puerto :8262 liberado. Se elimina la reserva en /srv/projects/a §3 cuando otro servicio CIS lo necesite.
  8. Umbrales de alerta: buckets discretos (7, 3, 1, 0) días antes de vencer. UNIQUE (obligacion_id, channel, days_before) previene re-alertar el mismo bucket. Default threshold 7d configurable via SII_MONITOR_ALERT_DAYS.

Alternativas descartadas

  • Mantener microservicio standalone: duplica infra (DB, auth, deploy) sin beneficio operativo. El watcher es ~200 LOC + 1 cron, cabe perfectamente en cis-admin.
  • Embeber en cis-sii-gateway: el gateway ya tiene una superficie cargada (DTE SOAP + REST boleta + scraping). Añadir lógica de obligaciones + alertas mezcla adquisición de datos con acción sobre el negocio.
  • Hacer el cron solo via systemd timer: descarta arq/Redis. Funciona pero no escala si en el futuro queremos retries con backoff o tareas one-shot disparadas desde la UI; mejor invertir 30 min en el wiring arq y reusarlo cuando llegue cis-inbox-sync v2.

Consecuencias

  • -1 microservicio mental que mantener. CIS pasa de 9 servicios CIS-* a 8 (CATALOGO §2).
  • Reuso real: notificación, auth, DB session, conexión al gateway, todo proviene de cis-admin.
  • El módulo tributario queda completo end-to-end (UI + API proxy + watcher + alertas).
  • ⚠️ Acopla cis-admin a Redis. Hoy cis-admin no usa Redis directamente; el worker lo introduce. Mitigación: Redis ya corre en vps-cis (lo usa cis-claudia + cis-inbox-sync).
  • ⚠️ systemd unit no enabled todavía. Pendiente: aplicar migración 046 + pip install -r requirements.txt (arq+redis) + systemctl enable --now cis-admin-sii-monitor.service. Acción humana documentada en este ADR.
  • ⚠️ El repo cis-sii-monitor/ ocupa espacio. Decisión de archivarlo o borrarlo queda pendiente para limpieza Fase 3 post-cutover cis-admin.

Implementación (este sprint)

Artefacto Path
Modelo DTEReceived cis-admin/backend/app/models/dte_received.py
Modelo ObligacionAlertLog cis-admin/backend/app/models/obligacion_alert_log.py
Servicio sii_monitor cis-admin/backend/app/services/sii_monitor.py
Worker arq cis-admin/backend/app/workers/sii_monitor_worker.py
Migración 046 cis-admin/backend/app/db/migrations/046_sii_monitor_dte_alerts.sql
systemd unit cis-admin/deploy/cis-admin-sii-monitor.service (no enabled)
Tests cis-admin/backend/tests/test_sii_monitor.py (5+ tests pytest)
Marker deprecated cis-sii-monitor/DEPRECATED-SEE-cis-admin-tributario.md
CATALOGO §2 fila cis-sii-monitor marcada 🪦

Verificación pendiente (humano)

  1. psql cis_admin < app/db/migrations/046_sii_monitor_dte_alerts.sql — aplicar migración.
  2. pip install -r requirements.txt dentro del venv de cis-admin — agregar arq+redis.
  3. pytest backend/tests/test_sii_monitor.py -v — confirmar 5+ tests OK.
  4. sudo cp deploy/cis-admin-sii-monitor.service /etc/systemd/system/ + systemctl daemon-reload + systemctl enable --now cis-admin-sii-monitor.service.
  5. journalctl -u cis-admin-sii-monitor.service -f — verificar primer ciclo (poll + alert).

Relaciona

  • cis-sii-gateway (provider de /sii/dte/pending, /sii/contribuyente/datos, /sii/libros).
  • cis-admin/frontend/.../tributario (UI, output agent-DE Fase D.2).
  • cis-inbox-sync.service (pattern de worker background sobre cis-admin sibling).
  • app/api/v1/sii.py (proxy a cis-sii-gateway, reusa _gateway_get y headers).
  • app/services/notification.py (notify_many + email).
  • ADR-010 (stack canónico admin: FastAPI + Postgres + SPA Vite/React).

Referencias

  • /srv/projects/cds/cis/cis-sii-monitor/CLAUDE.md (auto-reconoce el destino merger).
  • /srv/projects/cds/cis/cis-plan/BACKLOG.md fila 6.8 ("cis-sii-monitor watcher · service inactive").
  • /srv/projects/cis/CATALOGO.md §2 (cis-sii-monitor → 🪦).
  • Commit del pivot: pendiente (este sprint, sin autor humano hasta merge).