Files
system-docs/v4-archive/the-factory/docs/THE_FACTORY_Especificacion_Tecnica_v1.md

723 lines
24 KiB
Markdown
Raw Normal View History

# 🏭 THE FACTORY
## Especificación Técnica Genérica v1.0
**Incubador Iterativo — Sistema SFE/HST Enterprise v5.0**
> *"Zero retención de datos. Todo entra, se procesa, se va."*
---
## Índice
1. [Visión General](#1-visión-general)
2. [Ciclo de Trabajo](#2-ciclo-de-trabajo)
3. [Modelo de Datos](#3-modelo-de-datos)
4. [Componentes Internos](#4-componentes-internos)
5. [Catálogo de Modelos](#5-catálogo-de-modelos)
6. [Integración con Contrato Común v1.2](#6-integración-con-contrato-común-v12)
7. [API HTTP](#7-api-http)
8. [Configuración](#8-configuración)
9. [Ejemplo de Uso Completo](#9-ejemplo-de-uso-completo)
10. [Próximos Pasos](#10-próximos-pasos)
---
## 1. Visión General
### 1.1 ¿Qué es The Factory?
The Factory es un **trabajador IA disciplinado** que ejecuta trabajo hasta alcanzar calidad. A diferencia de los sistemas tradicionales de generación única, The Factory implementa un **ciclo iterativo de producción-evaluación** hasta convergencia.
```
┌─────────────────────────────────────────────────────────────────┐
│ THE FACTORY │
│ │
│ • Recibe trabajo (Job) │
│ • Ejecuta ciclos iterativos │
│ • Evalúa cada iteración │
│ • Para cuando: conformidad | max ciclos | presupuesto │
│ • Devuelve resultados │
│ │
└─────────────────────────────────────────────────────────────────┘
```
| Característica | Descripción |
|----------------|-------------|
| **Naturaleza** | Incubador iterativo con ciclo de mejora continua |
| **Filosofía** | Zero retención — stateless entre Jobs |
| **Objetivo** | Producir artefactos de calidad mediante iteración |
| **Parada** | Por conformidad, límite de ciclos, o presupuesto |
### 1.2 Principios Fundamentales
| Principio | Descripción |
|-----------|-------------|
| **Stateless** | No retiene estado entre Jobs. Cada ejecución es independiente |
| **Determinista** | Mismo Job + misma semilla = mismo resultado |
| **Intercambiable** | Los modelos subyacentes pueden sustituirse sin romper el sistema |
| **Trazable** | Toda ejecución queda registrada vía trace_id |
| **No persiste** | Los archivos solo existen en el almacenamiento externo |
### 1.3 Arquitectura de Responsabilidades
```
THE CORP (el que encarga)
├── Tiene el espacio de trabajo
├── Tiene el log
├── Define el Job
└── Recibe los resultados
THE FACTORY (el que fabrica)
├── Lee de donde le dicen
├── Ejecuta ciclos
├── Escribe donde le dicen
└── No retiene NADA
STORAGE (el que persiste)
├── Almacena artefactos
├── Externo a Factory
└── Puede ser S3, Hostinger, local, etc.
```
| Componente | Rol | Responsabilidad |
|------------|-----|-----------------|
| **THE CORP** | El que encarga | Define Job, provee workspace, recibe resultados |
| **THE FACTORY** | El que fabrica | Ejecuta ciclos, evalúa, itera hasta convergencia |
| **STORAGE** | El que persiste | Almacena artefactos (externo a Factory) |
---
## 2. Ciclo de Trabajo
### 2.1 Flujo Principal
```
Job ──► EJECUTOR ──► Artefacto ──► EVALUADOR ──► ¿Converge?
│ │
│ ┌─────────────────────┘
│ │
│ Sí│No
│ │ │
│ ▼ └──────────────┐
│ FIN │
│ ▼
└─────────── Nueva iteración (con feedback)
```
#### Paso 1: Recepción del Job
The Factory recibe un Job que contiene:
- **Semilla**: Instrucción inicial / prompt
- **Objetivo**: Criterio de éxito (qué es "listo")
- **Función**: Tipo de generación (texto, imagen, audio, video)
- **Límites**: Ciclos máximos, presupuesto, timeout
- **Referencias**: URLs de entrada/salida
#### Paso 2: Ejecución
El **Ejecutor** toma la semilla (y feedback previo si existe) y produce un artefacto. Es agnóstico del modelo — puede usar cualquier LLM, generador de imagen, audio o video.
#### Paso 3: Evaluación
El **Evaluador** (Comité) analiza el artefacto contra el objetivo definido:
- Determina si **converge** (cumple criterios) o no
- Si no converge, genera **feedback estructurado** para el Ejecutor
#### Paso 4: Decisión
- **Si converge** → Termina y entrega
- **Si no converge** → Nueva iteración con feedback
- **Si límite alcanzado** → Entrega última versión funcional + informe
### 2.2 Criterios de Parada
| Criterio | Condición | Resultado |
|----------|-----------|-----------|
| **CONFORMITY** | El evaluador dice "listo" | Entrega artefacto final |
| **MAX_CYCLES** | Se agotan iteraciones permitidas | Entrega última funcional + informe |
| **BUDGET** | Se agota el presupuesto definido | Igual que MAX_CYCLES |
| **TIMEOUT** | Se agota el tiempo máximo | Igual que MAX_CYCLES |
| **ERROR** | Error irrecuperable | Entrega parcial + error |
| **CANCELLED** | Cancelación externa | Entrega estado actual |
---
## 3. Modelo de Datos
### 3.1 JobInput — La Semilla
Estructura de entrada que define todo lo necesario para iniciar un trabajo:
```json
{
"job_id": "uuid-v4",
"seed": "Instrucción inicial / prompt",
"objective": "Qué se considera éxito",
"function": "TEXT_GENERATION",
"input_refs": ["url/de/materia/prima"],
"output_ref": "url/donde/escribir",
"log_ref": "url/del/log",
"limits": {
"max_cycles": 10,
"budget_usd": 10.0,
"timeout_minutes": 60,
"min_confidence": 0.8
}
}
```
| Campo | Tipo | Requerido | Descripción |
|-------|------|-----------|-------------|
| `job_id` | UUID | Auto | Identificador único del Job |
| `seed` | string | Sí | Instrucción inicial / prompt |
| `objective` | string | Sí | Criterio de éxito (qué es "listo") |
| `function` | enum | Sí | Tipo de generación |
| `input_refs` | string[] | No | URLs de materia prima |
| `output_ref` | string | Sí | URL donde escribir resultado |
| `log_ref` | string | Sí | URL del log de ejecución |
| `limits` | Limits | Sí | Restricciones del Job |
### 3.2 Functions Soportadas
| Function | Descripción | Output típico |
|----------|-------------|---------------|
| `TEXT_GENERATION` | Generación de texto/código | .txt, .md, .json, .py |
| `IMAGE_GENERATION` | Generación de imágenes | .png, .jpg, .webp |
| `AUDIO_GENERATION` | Generación de audio/voz | .mp3, .wav, .opus |
| `VIDEO_GENERATION` | Generación de video | .mp4, .webm |
| `CODE_GENERATION` | Código con validación | Archivos de código |
| `DOCUMENT_GENERATION` | Documentos estructurados | .pdf, .docx |
| `MULTIMODAL` | Combinación de modalidades | Variable |
### 3.3 Limits — Restricciones
| Campo | Tipo | Default | Descripción |
|-------|------|---------|-------------|
| `max_cycles` | int | 10 | Máximo de iteraciones permitidas |
| `budget_usd` | float | 10.0 | Presupuesto máximo en USD |
| `timeout_minutes` | int | 60 | Tiempo máximo de ejecución |
| `min_confidence` | float | 0.8 | Confianza mínima para convergencia |
### 3.4 JobState — Estado en Tiempo Real
```json
{
"job_id": "uuid",
"status": "RUNNING",
"current_iteration": 3,
"spent_usd": 0.045,
"stop_reason": null,
"final_artifact_ref": null,
"last_functional_iteration": 2,
"created_at": "2025-12-16T10:30:00Z",
"started_at": "2025-12-16T10:30:01Z",
"completed_at": null
}
```
| Campo | Tipo | Descripción |
|-------|------|-------------|
| `job_id` | UUID | Identificador del Job |
| `status` | enum | PENDING \| RUNNING \| CONVERGED \| EXHAUSTED \| FAILED \| CANCELLED |
| `current_iteration` | int | Iteración actual (1-based) |
| `spent_usd` | float | Costo acumulado |
| `stop_reason` | enum | Razón de parada (si terminó) |
| `final_artifact_ref` | string | URL del artefacto final |
| `last_functional_iteration` | int | Última iteración sin errores graves |
| `created_at` | datetime | Momento de creación |
| `started_at` | datetime | Momento de inicio de procesamiento |
| `completed_at` | datetime | Momento de finalización |
### 3.5 JobResult — Resultado Final
```json
{
"job_id": "uuid",
"status": "CONVERGED",
"stop_reason": "CONFORMITY",
"converged": true,
"final_artifact_ref": "s3://bucket/output/artifact.md",
"last_functional_iteration": 3,
"total_iterations": 3,
"total_cost_usd": 0.045,
"total_duration_ms": 12500,
"created_at": "2025-12-16T10:30:00Z",
"started_at": "2025-12-16T10:30:01Z",
"completed_at": "2025-12-16T10:30:13Z"
}
```
---
## 4. Componentes Internos
### 4.1 JobManager — El Orquestador
El JobManager es el componente central que gestiona el ciclo de vida de los Jobs:
```python
class JobManager:
async def submit_job(input: JobInput) -> JobState
async def get_job_status(job_id: str) -> JobState
async def cancel_job(job_id: str) -> bool
def get_job_result(job_id: str) -> JobResult
```
| Método | Descripción |
|--------|-------------|
| `submit_job(input)` | Recibe y encola un Job para procesamiento |
| `get_job_status(id)` | Obtiene el estado actual de un Job |
| `cancel_job(id)` | Cancela un Job en ejecución |
| `get_job_result(id)` | Obtiene el resultado final de un Job completado |
### 4.2 Executor — El Productor
El Executor es responsable de generar artefactos. Es agnóstico del modelo subyacente.
#### Interfaz
```python
async def execute(job_input: JobInput, iter_input: IterationInput) -> IterationOutput
```
#### IterationInput
| Campo | Tipo | Descripción |
|-------|------|-------------|
| `iteration_number` | int | Número de iteración actual |
| `seed` | string | Semilla original del Job |
| `previous_feedback` | string? | Feedback de la evaluación anterior |
| `accumulated_context` | dict | Contexto acumulado entre iteraciones |
#### IterationOutput
| Campo | Tipo | Descripción |
|-------|------|-------------|
| `artifact_ref` | string | URL del artefacto generado |
| `artifact_hash` | string | SHA-256 del artefacto |
| `executor_model` | string | Modelo usado (ej: "claude-sonnet-4") |
| `cost_usd` | float | Costo de esta iteración |
| `metadata` | dict | Metadatos adicionales |
### 4.3 Evaluator — El Comité
El Evaluator analiza artefactos y determina convergencia.
#### Interfaz
```python
async def evaluate(job_input: JobInput, eval_input: EvaluationInput) -> EvaluationResult
```
#### EvaluationInput
| Campo | Tipo | Descripción |
|-------|------|-------------|
| `job_objective` | string | Objetivo definido en el Job |
| `iteration_number` | int | Número de iteración actual |
| `artifact_ref` | string | URL del artefacto a evaluar |
| `previous_evaluations` | list | Historial de evaluaciones anteriores |
#### EvaluationResult
| Campo | Tipo | Descripción |
|-------|------|-------------|
| `converged` | bool | True si el artefacto cumple el objetivo |
| `confidence` | float | Nivel de confianza (0.0 - 1.0) |
| `strengths` | string[] | Aspectos positivos identificados |
| `weaknesses` | string[] | Aspectos a mejorar |
| `feedback_for_executor` | string | Instrucciones para la siguiente iteración |
| `evaluator_model` | string | Modelo usado para evaluar |
| `cost_usd` | float | Costo de la evaluación |
### 4.4 FactoryLogger — Trazabilidad
El Logger registra cada evento del ciclo de vida:
| EventType | Momento | Datos registrados |
|-----------|---------|-------------------|
| `JOB_CREATED` | Al recibir Job | seed, objective, limits |
| `JOB_STARTED` | Al iniciar procesamiento | timestamp |
| `ITERATION_START` | Al iniciar iteración | iteration_number |
| `EXECUTOR_CALL` | Al llamar Ejecutor | has_feedback |
| `EXECUTOR_RESPONSE` | Al recibir artefacto | artifact_ref, model, cost |
| `EVALUATOR_CALL` | Al llamar Evaluador | artifact_ref |
| `EVALUATOR_RESPONSE` | Al recibir evaluación | converged, confidence |
| `ITERATION_END` | Al terminar iteración | converged, total_spent |
| `JOB_CONVERGED` | Al alcanzar conformidad | final_artifact_ref |
| `JOB_MAX_ITERATIONS` | Al agotar ciclos | last_iteration |
| `JOB_BUDGET_EXHAUSTED` | Al agotar presupuesto | spent_usd |
| `JOB_ERROR` | Al ocurrir error | error, phase |
| `JOB_COMPLETED` | Al finalizar | status, stop_reason, totals |
---
## 5. Catálogo de Modelos
The Factory es agnóstico de modelos. Estos son los recomendados por modalidad:
### 5.1 LLMs (Texto/Código)
| Modelo | Proveedor | Tipo | Fortalezas |
|--------|-----------|------|------------|
| Claude Sonnet 4 | Anthropic | API | Razonamiento, código, instrucciones |
| GPT-4o | OpenAI | API | Multimodal, velocidad, generalista |
| Gemini 2.5 Pro | Google | API | Contexto enorme (1M tokens) |
| Llama 3.3 70B | Meta | Local/API | Open source, privacidad |
| Qwen 2.5 72B | Alibaba | Local/API | Multilingüe, código |
### 5.2 Imagen
| Modelo | Proveedor | Tipo | Fortalezas |
|--------|-----------|------|------------|
| Flux 1.1 Pro | Black Forest | API | Calidad, texto en imagen |
| DALL-E 3 | OpenAI | API | Facilidad, integración |
| Flux Schnell | Black Forest | Local | Rápido, buena calidad |
| Stable Diffusion XL | Stability | Local | Personalizable, LoRAs |
### 5.3 Audio
| Modelo | Proveedor | Tipo | Fortalezas |
|--------|-----------|------|------------|
| ElevenLabs | ElevenLabs | API | Voces naturales, clonación |
| XTTS-v2 | Coqui | Local | Multilingüe, privacidad |
| Suno | Suno | API | Generación musical |
| Faster-Whisper | SYSTRAN | Local | STT rápido y preciso |
### 5.4 Video
| Modelo | Proveedor | Tipo | Fortalezas |
|--------|-----------|------|------------|
| Runway Gen-3 | Runway | API | Calidad cinematográfica |
| Kling 1.6 | Kuaishou | API | Duración, coherencia |
| Pika | Pika Labs | API | Efectos, estilización |
---
## 6. Integración con Contrato Común v1.2
Para integrarse con sistemas externos (como Jarvis/Alfred), The Factory puede adaptar sus estructuras al Contrato Común v1.2.
### 6.1 Mapeo JobInput → Envelope
| JobInput | Envelope v1.2 | Transformación |
|----------|---------------|----------------|
| `job_id` | `envelope.trace_id` | Directo |
| `function` | `routing.module` | Mapeo (TEXT_GENERATION → TEXT_GEN) |
| `seed + objective` | `payload.content` | Combinar en estructura |
| `limits` | `envelope.ttl_ms + context` | Transformar a milisegundos |
| `input_refs` | `storage.input_ref` | Primera referencia |
| `output_ref` | `storage.output_ref` | Directo |
### 6.2 Mapeo Function → Module
| Factory Function | Jarvis Module | Fallback Chain sugerida |
|------------------|---------------|-------------------------|
| `TEXT_GENERATION` | `TEXT_GEN` | CLAUDE_SONNET → GPT4O → LLAMA_70B |
| `IMAGE_GENERATION` | `IMAGE_GEN` | FLUX_PRO → DALLE3 → FLUX_LOCAL |
| `AUDIO_GENERATION` | `AUDIO_GEN` | ELEVENLABS → XTTS_LOCAL |
| `VIDEO_GENERATION` | `VIDEO_GEN` | RUNWAY → KLING |
| `CODE_GENERATION` | `TEXT_GEN + VALIDATOR` | CLAUDE → GPT4O |
### 6.3 Envelope de Ejemplo
```json
{
"contract_version": "1.2",
"profile": "FULL",
"envelope": {
"trace_id": "job_id_aquí",
"parent_trace_id": null,
"step_id": "uuid-paso",
"step_index": 1,
"total_steps": 1,
"idempotency_key": "sha256_del_seed",
"timestamp_init": "2025-12-16T10:30:00.000Z",
"ttl_ms": 3600000
},
"routing": {
"module": "TEXT_GEN",
"version": "1.0",
"provider_preference": ["anthropic", "openai", "local"],
"fallback_chain": ["CLAUDE_SONNET", "GPT4O", "LLAMA_70B"],
"max_fallback_level": 2
},
"payload": {
"type": "structured",
"content": {
"seed": "Escribe un haiku...",
"objective": "Un haiku válido 5-7-5..."
}
},
"storage": {
"input_location": "external",
"output_location": "external",
"output_ref": "s3://bucket/output/"
}
}
```
### 6.4 Adapter Pattern
Se recomienda implementar un `ContractAdapter` que permita:
- Recibir Jobs en formato nativo de Factory
- Transformar a Envelope v1.2 para llamadas a Jarvis
- Recibir respuestas en formato Envelope
- Transformar a estructuras internas de Factory
```python
class ContractAdapter:
def job_to_envelope(job: JobInput, iteration: int) -> dict
def envelope_to_iteration_output(envelope: dict) -> IterationOutput
def envelope_to_evaluation_result(envelope: dict) -> EvaluationResult
```
---
## 7. API HTTP
### 7.1 Endpoints
| Método | Endpoint | Descripción |
|--------|----------|-------------|
| `GET` | `/health` | Health check |
| `GET` | `/` | Información del sistema |
| `POST` | `/jobs` | Crear nuevo Job |
| `GET` | `/jobs/{job_id}` | Obtener estado de Job |
| `DELETE` | `/jobs/{job_id}` | Cancelar Job |
| `GET` | `/jobs/{job_id}/result` | Obtener resultado final |
### 7.2 POST /jobs — Crear Job
#### Request
```json
{
"seed": "Escribe un haiku sobre programación",
"objective": "Un haiku válido (5-7-5 sílabas) sobre programación",
"function": "TEXT_GENERATION",
"output_ref": "/workspace/output/haiku.txt",
"log_ref": "/workspace/logs/job_001.json",
"limits": {
"max_cycles": 5,
"budget_usd": 1.0
}
}
```
#### Response (202 Accepted)
```json
{
"job_id": "550e8400-e29b-41d4-a716-446655440000",
"status": "PENDING",
"created_at": "2025-12-16T10:30:00Z"
}
```
### 7.3 GET /jobs/{id} — Estado
```json
{
"job_id": "550e8400-e29b-41d4-a716-446655440000",
"status": "RUNNING",
"current_iteration": 2,
"spent_usd": 0.023,
"created_at": "2025-12-16T10:30:00Z",
"started_at": "2025-12-16T10:30:01Z"
}
```
### 7.4 GET /jobs/{id}/result — Resultado
```json
{
"job_id": "550e8400-e29b-41d4-a716-446655440000",
"status": "CONVERGED",
"stop_reason": "CONFORMITY",
"converged": true,
"final_artifact_ref": "/workspace/output/haiku.txt",
"total_iterations": 3,
"total_cost_usd": 0.045,
"total_duration_ms": 12500
}
```
---
## 8. Configuración
### 8.1 Variables de Entorno
| Variable | Default | Descripción |
|----------|---------|-------------|
| `ENVIRONMENT` | development | Entorno de ejecución |
| `DEBUG` | false | Modo debug |
| `WORKSPACE_PATH` | /workspace | Ruta del workspace |
| `LOG_LEVEL` | INFO | Nivel de logging |
| `DEFAULT_MAX_CYCLES` | 10 | Ciclos por defecto |
| `DEFAULT_BUDGET_USD` | 10.0 | Presupuesto por defecto |
| `DEFAULT_TIMEOUT_MIN` | 60 | Timeout por defecto |
### 8.2 API Keys
| Variable | Descripción |
|----------|-------------|
| `OPENROUTER_API_KEY` | API key para OpenRouter (multi-modelo) |
| `ANTHROPIC_API_KEY` | API key de Anthropic (Claude) |
| `OPENAI_API_KEY` | API key de OpenAI |
| `REPLICATE_API_KEY` | API key de Replicate |
| `FAL_API_KEY` | API key de Fal.ai |
### 8.3 Configuración de Modelos
```bash
# Modelos por función
EXECUTOR_MODEL_TEXT=claude-sonnet-4-20250514
EXECUTOR_MODEL_IMAGE=flux-1.1-pro
EXECUTOR_MODEL_AUDIO=elevenlabs-multilingual-v2
EXECUTOR_MODEL_VIDEO=runway-gen3
# Modelo del evaluador
EVALUATOR_MODEL=claude-sonnet-4-20250514
```
---
## 9. Ejemplo de Uso Completo
### Escenario: Generación de Artículo Técnico
#### 1. Enviar Job
```bash
POST /jobs
```
```json
{
"seed": "Escribe un artículo técnico de 1000 palabras sobre el estado actual de la IA generativa en 2025",
"objective": "Artículo bien estructurado, técnicamente preciso, con introducción, desarrollo y conclusión. Debe mencionar modelos actuales y tendencias.",
"function": "TEXT_GENERATION",
"output_ref": "s3://bucket/articles/ai-2025.md",
"log_ref": "s3://bucket/logs/job-article.json",
"limits": {
"max_cycles": 5,
"budget_usd": 2.0
}
}
```
#### 2. Iteración 1
- **Ejecutor**: Genera primer borrador
- **Evaluador**:
- Confianza: 0.6
- Fortalezas: Buena estructura básica
- Debilidades: Falta profundidad técnica, conclusión débil
- **No converge**
#### 3. Iteración 2
- **Ejecutor**: Recibe feedback, mejora secciones técnicas
- **Evaluador**:
- Confianza: 0.75
- Fortalezas: Mejor contenido técnico
- Debilidades: Conclusión aún genérica
- **No converge**
#### 4. Iteración 3
- **Ejecutor**: Refuerza conclusión con proyecciones específicas
- **Evaluador**:
- Confianza: 0.92
- Fortalezas: Cumple todos los criterios
- Debilidades: Ninguna significativa
- **¡CONVERGE!**
#### 5. Resultado Final
```json
{
"job_id": "550e8400-e29b-41d4-a716-446655440000",
"status": "CONVERGED",
"stop_reason": "CONFORMITY",
"converged": true,
"final_artifact_ref": "s3://bucket/articles/ai-2025.md",
"total_iterations": 3,
"total_cost_usd": 0.18,
"total_duration_ms": 45000
}
```
---
## 10. Próximos Pasos
### 10.1 Este Documento (Especificación Genérica) ✅
- [x] Definición de arquitectura y componentes
- [x] Modelo de datos completo
- [x] Ciclo de trabajo y criterios de parada
- [x] API HTTP
- [x] Catálogo de modelos
- [x] Mapeo a Contrato Común v1.2
### 10.2 Siguiente: Implementación RunPod
- [ ] Dockerfile optimizado para GPU
- [ ] Handler serverless para RunPod
- [ ] Workers especializados por modalidad
- [ ] Configuración de endpoints
- [ ] Gestión de modelos locales
### 10.3 Futuro: Integración con Alfred
- [ ] Workflow n8n para invocar Factory
- [ ] Webhooks de callback
- [ ] Logging a SYS_LOG
- [ ] Persistencia de artefactos en Hostinger
---
## Anexo: Diagrama de Secuencia
```
┌──────┐ ┌───────────┐ ┌──────────┐ ┌───────────┐
│ CORP │ │ JobManager│ │ Executor │ │ Evaluator │
└──┬───┘ └─────┬─────┘ └────┬─────┘ └─────┬─────┘
│ │ │ │
│ submit_job() │ │ │
│──────────────>│ │ │
│ │ │ │
│ │────────────────────────────────────────┐
│ │ LOOP [hasta convergencia] │
│ │ │ │ │
│ │ execute() │ │ │
│ │───────────────>│ │ │
│ │ │ │ │
│ │ artifact │ │ │
│ │<───────────────│ │ │
│ │ │ │ │
│ │ evaluate() │ │ │
│ │───────────────────────────────-->│ │
│ │ │ │ │
│ │ result │ │ │
│ │<─────────────────────────────────│ │
│ │────────────────────────────────────────┘
│ │ │ │
│ JobResult │ │ │
│<──────────────│ │ │
│ │ │ │
```
---
**Sistema SFE/HST Enterprise v5.0**
*Documento generado: Diciembre 2025*