Workflow: SupplierProductChange¶
Resumen¶
Implementación de Laravel Workflow para orquestar el proceso de cambios en SupplierProduct. El workflow centraliza y secuencia las operaciones que ocurren cuando cambian atributos de un producto de proveedor (precio, stock, contenido, ofertas).
Problema que resuelve¶
Anteriormente, cuando un SupplierProduct cambiaba múltiples atributos simultáneamente, se despachaban múltiples jobs de forma independiente:
SupplierProduct cambia precio + stock
│
├──► CalculatePricesJob
├──► EvaluateSelectedSupplierProductJob
└──► Múltiples sincronizaciones duplicadas
Problemas: - Sincronizaciones duplicadas por cambios compuestos - Falta de secuencia garantizada entre procesos - Difícil trazabilidad y auditoría - Sin consolidación de cambios
Solución implementada¶
Un único workflow que orquesta todo el proceso:
SupplierProduct cambia
│
▼
┌─────────────────────────────────────┐
│ SupplierProductChangeWorkflow │
├─────────────────────────────────────┤
│ 1. CalculatePricesActivity │ ← Solo si cambió precio/oferta
│ 2. GenerateContentActivity │ ← Solo si cambió contenido (CL)
│ 3. EvaluateSelectedActivity │ ← Siempre
│ 4. DispatchSyncActivity │ ← Solo si es necesario sincronizar
└─────────────────────────────────────┘
│
▼
Jobs de sync independientes
(Medusa, WooCommerce, etc.)
Archivos creados¶
app/Workflows/SupplierProductChange/
├── SupplierProductChangeWorkflow.php # Workflow principal
└── Activities/
├── CalculatePricesActivity.php # Calcula precios del SupplierProduct
├── GenerateContentActivity.php # Genera contenido IA (solo CL, PC-/PCM-)
├── EvaluateSelectedActivity.php # Evalúa selección de proveedor
└── DispatchSyncActivity.php # Despacha jobs de sync a canales
Archivos modificados¶
| Archivo | Cambio |
|---|---|
config/workflows.php |
Agregado feature flag supplier_product_change_workflow |
app/Services/Sync/Evaluation/SupplierProductEvaluationStrategy.php |
Integración con workflow via feature flag |
.env |
Variable WORKFLOW_SUPPLIER_PRODUCT_CHANGE=true |
Configuración¶
Activar el workflow¶
# En .env
WORKFLOW_SUPPLIER_PRODUCT_CHANGE=true
Desactivar (volver a jobs tradicionales)¶
# En .env
WORKFLOW_SUPPLIER_PRODUCT_CHANGE=false
Tipos de cambio detectados¶
| Constante | Valor | Descripción |
|---|---|---|
CHANGE_PRICE |
price |
Cambio en regular_price o special_price |
CHANGE_STOCK |
stock |
Cambio en total_stock |
CHANGE_CONTENT |
content |
Cambio en name, short_description, long_description |
CHANGE_OFFER |
offer |
Cambio en offer_start o offer_end |
CHANGE_REASSIGNMENT |
reassignment |
Cambio en id_product_item |
Flujo de ejecución¶
Paso 1: CalculatePricesActivity¶
- Condición: Solo si detectó cambio de
priceuoffer - Acción: Ejecuta
$supplierProduct->calculateAndStorePrices() - Resultado: Precios calculados y almacenados
Paso 2: GenerateContentActivity¶
- Condición: Solo si detectó cambio de
content - Validaciones adicionales:
- El proveedor debe ser
CL(Compulandia) - El SKU debe comenzar con
PC-oPCM- - Acción: Despacha
GenerateProductContentJob - Resultado: Contenido IA generado para el ProductItem
Paso 3: EvaluateSelectedActivity¶
- Condición: Siempre se ejecuta
- Acción: Evalúa todos los SupplierProducts del ProductItem para determinar el proveedor seleccionado
- Resultado:
should_sync: Si debe sincronizarsync_type: Tipo de sincronización (product_basic,product_status)selection_changed: Si cambió el proveedor seleccionado
Paso 4: DispatchSyncActivity¶
- Condición: Solo si
should_sync = truey existeproduct_item_id - Acción: Usa
ProductSyncDispatcherServicepara despachar jobs a los canales configurados - Resultado: Jobs de sincronización despachados a sus colas respectivas
Monitoreo¶
Waterline UI¶
El paquete laravel-workflow/waterline proporciona una interfaz web para visualizar:
- Estado de workflows (pending, running, completed, failed)
- Activities ejecutadas
- Timeline de ejecución
- Excepciones
Consultas manuales¶
// Ver workflows recientes
$workflows = \Workflow\Models\StoredWorkflow::latest()->take(10)->get();
// Ver logs de un workflow específico
$logs = \Workflow\Models\StoredWorkflowLog::where('stored_workflow_id', $id)->get();
// Ver resultado de un workflow
$workflow = \Workflow\WorkflowStub::load($id);
$output = $workflow->output();
Resultado del workflow¶
El workflow retorna un array con toda la información para auditoría:
[
'supplier_product_id' => 5,
'detected_changes' => ['price', 'stock'],
'started_at' => '2026-01-06T15:27:43-03:00',
'completed_at' => '2026-01-06T15:27:44-03:00',
'steps' => [
'calculate_prices' => ['executed' => true, 'result' => [...]],
'generate_content' => ['executed' => false, 'reason' => '...'],
'evaluate_selected' => ['executed' => true, 'result' => [...]],
'dispatch_sync' => ['executed' => true, 'result' => [...]]
],
'summary' => [
'prices_calculated' => true,
'content_generated' => false,
'selection_changed' => true,
'sync_dispatched' => true,
'sync_type' => 'product_status'
]
]
Beneficios¶
- Consolidación de cambios: Un único workflow por save() del SupplierProduct
- Secuencia garantizada: Los pasos se ejecutan en orden correcto
- Ejecución condicional: Solo se ejecutan las activities necesarias
- Trazabilidad: Todo queda registrado en la base de datos del workflow
- Auditoría: Resultado completo con timestamps y detalles de cada paso
- Independencia de sync: Los jobs de sincronización corren aparte, no bloquean el workflow
- Tolerancia a fallos: Si un servicio externo falla, el workflow ya completó
Dependencias¶
laravel-workflow/laravel-workflow: ^1.0laravel-workflow/waterline: ^1.0 (UI de monitoreo)
Próximos pasos potenciales¶
- [ ] Agregar señales para cancelar workflows en progreso
- [ ] Implementar deduplicación por SupplierProduct (evitar workflows duplicados)
- [ ] Agregar métricas de tiempo de ejecución por activity
- [ ] Configurar alertas para workflows fallidos
- [ ] Extender a otros modelos (ProductItem, etc.)
Fecha de implementación¶
Enero 2026
Autor¶
Implementado con asistencia de Claude Code