{
  "name": "AI Email Squad · 4.1 Supervisor + 4.6 Revisor ciego (workshop Milton Suárez)",
  "nodes": [
    {
      "parameters": {
        "content": "## AI Email Squad\n### patrón 4.1 · Supervisor\n\nUn **orquestador** lee el brief, decide\na qué especialista llama, en qué orden\ny si le hace repetir algo. No es una\ncadena fija: es un jefe con equipo.\n\nCada especialista cuelga del jefe como\n**herramienta**, tiene su propio modelo\ny su propio **documento de oficio**\n(el equivalente a un *skill*).\n\nAl final, y **fuera** del orquestador,\nestá el **revisor ciego** (patrón 4.6):\nve el resultado y nada del proceso. Si\nfuera una herramienta más, el jefe\npodría no llamarlo — o llamarlo\nsabiendo lo que quiere oír.\n\n---\n**Antes de la primera corrida:**\n1. Conecta OpenRouter en un nodo morado\n   (todos comparten credencial)\n2. En el nodo de Brevo crea la credencial\n   **Header Auth**: `api-key` / `xkeysib-...`\n3. **Execute workflow** → abre la URL del\n   formulario → rellena → enviar\n\nCoste por corrida: **~$0,15-0,30**\n\n---\nMilton Suárez · recursos.miltonsuarez.com",
        "height": 820,
        "width": 460,
        "color": 7
      },
      "id": "nota-patron",
      "name": "Nota patron",
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        -620,
        20
      ]
    },
    {
      "parameters": {
        "content": "## Cómo leer este lienzo — y por qué NO es una línea de montaje\n\n**Arriba, la fila principal:** formulario → orquestador → revisor ciego → Brevo. Solo cuatro pasos, porque el trabajo de verdad no pasa por ahí.\n\n**Abajo, colgando del orquestador:** los cuatro especialistas. No están conectados entre sí. Ninguno sabe que los demás existen. El orquestador los llama por su nombre cuando los necesita, les pasa el encargo que él decide, y junta lo que devuelven.\n\n**Debajo de cada especialista:** su modelo y su documento de oficio. Ese documento es lo que en Claude Code sería un *skill*: contexto especializado que solo carga quien lo necesita, en vez de meterlo todo en un prompt gigante que pagan todos.\n\n**Cambia el brief y cambia el plan.** Con el mismo lienzo, una campaña de reactivación y un lanzamiento se resuelven distinto, porque el que decide es el orquestador, no el cableado.",
        "height": 260,
        "width": 1500,
        "color": 4
      },
      "id": "nota-lectura",
      "name": "Nota lectura",
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        640,
        1180
      ]
    },
    {
      "parameters": {
        "content": "## Por qué el revisor está aquí\n\ny no colgado del orquestador.\n\nUn auditor que forma parte del\nequipo que produce **no es un\nauditor**: es parte del equipo.\n\nAquí solo recibe el artefacto\nterminado. No vio el brief\noriginal, ni las idas y venidas,\nni qué especialista falló.\n\nJuzga lo que llegaría al cliente,\nque es exactamente lo único que\nimporta.\n\n**Patrón 4.6 — Revisor ciego.**",
        "height": 420,
        "width": 380,
        "color": 6
      },
      "id": "nota-ciego",
      "name": "Nota ciego",
      "type": "n8n-nodes-base.stickyNote",
      "typeVersion": 1,
      "position": [
        2180,
        20
      ]
    },
    {
      "parameters": {
        "formTitle": "Brief de campana de email",
        "formDescription": "Escribe la campana que necesitas. El squad decide como resolverla.",
        "formFields": {
          "values": [
            {
              "fieldLabel": "Que campana necesito",
              "fieldType": "textarea",
              "requiredField": true,
              "placeholder": "Ej: reactivar cuentas que se registraron y nunca conectaron un canal"
            },
            {
              "fieldLabel": "Objetivo",
              "fieldType": "dropdown",
              "requiredField": true,
              "fieldOptions": {
                "values": [
                  {
                    "option": "Conversion"
                  },
                  {
                    "option": "Nurturing"
                  },
                  {
                    "option": "Reactivacion"
                  },
                  {
                    "option": "Lanzamiento"
                  },
                  {
                    "option": "Educacion"
                  }
                ]
              }
            },
            {
              "fieldLabel": "A quien le hablamos",
              "fieldType": "text",
              "requiredField": true,
              "placeholder": "Ej: fundadores de PyMEs con el trial expirado hace menos de 30 dias"
            },
            {
              "fieldLabel": "Que quiero que haga el lector",
              "fieldType": "text",
              "requiredField": true,
              "placeholder": "Ej: que vuelva y conecte su primer canal"
            },
            {
              "fieldLabel": "Oferta o gancho (opcional)",
              "fieldType": "textarea",
              "requiredField": false,
              "placeholder": "Dejalo vacio si no hay oferta: el squad no inventara ninguna"
            },
            {
              "fieldLabel": "Que NO debe decir (opcional)",
              "fieldType": "textarea",
              "requiredField": false,
              "placeholder": "Ej: no mencionar precios, no comparar con competidores"
            },
            {
              "fieldLabel": "Remitente verificado en Brevo",
              "fieldType": "email",
              "requiredField": true,
              "placeholder": "tu@tudominio.com"
            },
            {
              "fieldLabel": "ID de la lista de Brevo",
              "fieldType": "number",
              "requiredField": true,
              "placeholder": "1"
            }
          ]
        },
        "options": {}
      },
      "id": "brief-de-campana",
      "name": "Brief de campana",
      "type": "n8n-nodes-base.formTrigger",
      "typeVersion": 2,
      "position": [
        -100,
        300
      ],
      "notes": "Al pulsar Execute workflow n8n te da la URL del formulario. Es el unico punto de entrada: no hay datos cableados en ningun nodo."
    },
    {
      "parameters": {
        "mode": "raw",
        "jsonOutput": "={{ JSON.stringify({\n  marca: \"GrowthPilot es una SaaS de dashboard unificado de marketing digital para startups y PyMEs: conecta Google Ads, Meta Ads, Analytics, Mailchimp, HubSpot y Stripe en un solo panel, con metricas en tiempo real y alertas.\\nPlanes: Free $0 (2 canales) · Growth $29/mes (8 canales, alertas, reportes diarios) · Pro $79/mes (ilimitado, AI insights, forecasting).\\nColor primario para el HTML: #2563EB\",\n  campana: $json['Que campana necesito'],\n  objetivo: $json['Objetivo'],\n  audiencia: $json['A quien le hablamos'],\n  accion_deseada: $json['Que quiero que haga el lector'],\n  oferta: $json['Oferta o gancho (opcional)'] || 'sin oferta',\n  restricciones: $json['Que NO debe decir (opcional)'] || 'ninguna adicional',\n  sender_email: $json['Remitente verificado en Brevo'],\n  brevo_list_id: $json['ID de la lista de Brevo']\n}, null, 2) }}",
        "options": {}
      },
      "id": "el-brief",
      "name": "El brief",
      "type": "n8n-nodes-base.set",
      "typeVersion": 3.3,
      "position": [
        180,
        300
      ],
      "notes": "Deja el brief con nombres limpios. Es lo unico que ve el orquestador."
    },
    {
      "parameters": {
        "promptType": "define",
        "text": "=BRIEF DE LA CAMPANA\nQue necesita: {{ $json.campana }}\nObjetivo: {{ $json.objetivo }}\nAudiencia: {{ $json.audiencia }}\nQue queremos que haga el lector: {{ $json.accion_deseada }}\nOferta: {{ $json.oferta }}\nRestricciones: {{ $json.restricciones }}\n\nCONTEXTO DE MARCA\n{{ $json.marca }}\n\nResuelvelo con tu equipo.",
        "hasOutputParser": false,
        "options": {
          "systemMessage": "Eres el director de un equipo de email marketing. Tu no escribes, no maquetas y\nno disenas secuencias: para eso tienes cuatro especialistas colgados como\nherramientas.\n\nTU TRABAJO\n1. Lee el brief y decide que hace falta de verdad. No todas las campanas\n   necesitan lo mismo: una de educacion no lleva la misma arquitectura que una\n   de reactivacion.\n2. Llama a los especialistas que necesites, en el orden que tenga sentido.\n   Puedes llamar a uno mas de una vez si lo que devuelve no sirve.\n3. En CADA llamada pasa el encargo completo. Ellos no ven el brief ni lo que\n   han hecho los demas: arrancan en blanco. Si no se lo cuentas, no existe.\n4. Junta el resultado y devuelvelo en el formato exacto de abajo.\n\nTU EQUIPO\n- estratega: decide segmentos y arquitectura de la secuencia\n- copywriter: escribe el texto del email\n- maquetador: convierte el texto en HTML de email\n- automatizador: define esperas, ramas y topes de envio\n\nREGLAS\n- No hagas tu el trabajo de un especialista aunque sepas hacerlo. Si lo haces,\n  el equipo no sirve para nada.\n- Cero cifras inventadas: solo lo que este en el brief o en la marca.\n- Si el brief no menciona oferta, no inventes ninguna.\n\nFORMATO DE SALIDA — exacto, sin nada antes ni despues:\n\nASUNTO: [maximo 9 palabras, sin mayusculas sostenidas, sin emoji]\nPREHEADER: [entre 40 y 90 caracteres]\nHTML:\n[el HTML completo que devolvio el maquetador, empezando por <!DOCTYPE html>]\nCOMO LO RESOLVI: [3 lineas: a quien llamaste, en que orden y por que]"
        }
      },
      "id": "orquestador",
      "name": "ORQUESTADOR",
      "type": "@n8n/n8n-nodes-langchain.agent",
      "typeVersion": 2,
      "position": [
        520,
        300
      ],
      "notes": "Es el jefe. Decide a quien llama y con que encargo. Los especialistas cuelgan de el como herramientas, no como pasos de una cadena."
    },
    {
      "parameters": {
        "model": "anthropic/claude-opus-5",
        "options": {
          "maxTokens": 3000
        }
      },
      "id": "opus-5---el-jefe",
      "name": "Opus 5 - el jefe",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenRouter",
      "typeVersion": 1,
      "position": [
        520,
        60
      ]
    },
    {
      "parameters": {
        "toolDescription": "Disena segmentos y la arquitectura de la secuencia: cuantos emails, en que orden, con que espaciado y que objetivo cada uno. Usalo al principio, cuando aun no sabes que forma tiene la campana.",
        "name": "estratega",
        "text": "={{ $fromAI('encargo', 'El encargo completo para este especialista: que necesitas, con que material y en que formato lo quieres de vuelta') }}",
        "hasOutputParser": false,
        "options": {
          "systemMessage": "Eres estratega de email marketing. Recibes un encargo con el brief dentro.\n\nDevuelve:\nOBJETIVO: reformulado en una frase medible\nSEGMENTOS: entre 2 y 4, con criterio y tono de cada uno\nARQUITECTURA: una fila por email — numero, dia (D+0, D+3...), objetivo y\n  subject sugerido\nPARA EL COPYWRITER: que debe respetar y que debe evitar\n\nConsulta tu documento de segmentacion antes de responder. No inventes cifras de\nrendimiento: si citas un promedio de industria, di que lo es.",
          "maxIterations": 6
        }
      },
      "id": "estratega",
      "name": "estratega",
      "type": "@n8n/n8n-nodes-langchain.agentTool",
      "typeVersion": 2.2,
      "position": [
        180,
        760
      ]
    },
    {
      "parameters": {
        "model": "anthropic/claude-opus-5",
        "options": {
          "maxTokens": 2200
        }
      },
      "id": "opus-5---estrategia",
      "name": "Opus 5 - estrategia",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenRouter",
      "typeVersion": 1,
      "position": [
        90,
        990
      ]
    },
    {
      "parameters": {
        "name": "marco_de_segmentacion",
        "description": "Marco de segmentacion y arquitectura de secuencias de email",
        "language": "javaScript",
        "jsCode": "return \"MARCO DE SEGMENTACION\\n\\nPor engagement:\\n- activos: interactuaron en los ultimos 30 dias\\n- tibios: entre 30 y 90 dias\\n- dormidos: mas de 90 dias\\n\\nPor etapa del journey: awareness, consideracion, decision, post-compra.\\n\\nRFM (recency, frequency, monetary): High Value, Medium, At Risk, Lost.\\n\\nESPACIADO QUE FUNCIONA\\n- Reactivacion: D+0, D+3, D+7. Mas apretado se percibe como acoso.\\n- Nurturing: D+0, D+5, D+12. Da tiempo a leer.\\n- Lanzamiento: D+0, D+2, D+5. La urgencia justifica el ritmo.\\n- Educacion: semanal. El valor esta en la constancia, no en la presion.\\n\\nREGLA DE ORO\\nUn email = un objetivo = un CTA. Si un email tiene dos llamadas a la accion,\\nno tiene ninguna.\";"
      },
      "id": "doc-marco_de_segmentacion",
      "name": "doc: marco_de_segmentacion",
      "type": "@n8n/n8n-nodes-langchain.toolCode",
      "typeVersion": 1.1,
      "position": [
        290,
        990
      ]
    },
    {
      "parameters": {
        "toolDescription": "Escribe el texto del email: asunto, preheader, cuerpo y CTA. Usalo cuando ya sepas que email quieres y para quien. Necesita que le pases el objetivo, la audiencia y las restricciones.",
        "name": "copywriter",
        "text": "={{ $fromAI('encargo', 'El encargo completo para este especialista: que necesitas, con que material y en que formato lo quieres de vuelta') }}",
        "hasOutputParser": false,
        "options": {
          "systemMessage": "Eres copywriter de email marketing B2B. Recibes un encargo con lo que hay que\nescribir.\n\nConsulta tu documento de brand voice ANTES de escribir una linea: el tono no es\nnegociable.\n\nDevuelve exactamente:\nASUNTO: [maximo 9 palabras]\nPREHEADER: [40-90 caracteres, que complemente el asunto, no que lo repita]\nCUERPO: [markdown, 120-200 palabras, parrafos cortos, de tu]\nCTA: [maximo 5 palabras]\n\nCero cifras que no esten en el encargo. Si te falta un dato, dilo en vez de\nrellenarlo.",
          "maxIterations": 6
        }
      },
      "id": "copywriter",
      "name": "copywriter",
      "type": "@n8n/n8n-nodes-langchain.agentTool",
      "typeVersion": 2.2,
      "position": [
        560,
        760
      ]
    },
    {
      "parameters": {
        "model": "anthropic/claude-opus-5",
        "options": {
          "maxTokens": 1800
        }
      },
      "id": "opus-5---copy",
      "name": "Opus 5 - copy",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenRouter",
      "typeVersion": 1,
      "position": [
        470,
        990
      ]
    },
    {
      "parameters": {
        "name": "brand_voice",
        "description": "Tono de voz de la marca: lo que si y lo que nunca se hace",
        "language": "javaScript",
        "jsCode": "return \"BRAND VOICE — GrowthPilot\\n\\nTONO\\n- Directo: sin rodeos, al grano. Respetamos el tiempo del lector.\\n- Cercano: hablamos de tu, como un colega que sabe del tema.\\n- Seguro: sabemos de lo que hablamos, sin exagerar.\\n- Practico: todo accionable. Nada de teoria vacia.\\n\\nSIEMPRE\\n- Datos y numeros concretos\\n- Ejemplos reales\\n- Lenguaje simple y directo\\n- Un toque de personalidad\\n\\nNUNCA\\n- Jerga corporativa vacia: sinergia, apalancamiento, paradigma, ecosistema\\n- Promesas exageradas: \\\"10x tu revenue en una semana\\\"\\n- Exclamaciones multiples\\n- MAYUSCULAS SOSTENIDAS en el asunto\\n- Mas de un emoji, y solo si aporta contexto\\n- Aperturas de relleno: \\\"espero que estes bien\\\", \\\"me pongo en contacto\\\"\\n\\nPRUEBA DEL ALGODON\\nSi el primer parrafo se podria enviar a cualquier otra empresa, es generico y\\nhay que reescribirlo.\";"
      },
      "id": "doc-brand_voice",
      "name": "doc: brand_voice",
      "type": "@n8n/n8n-nodes-langchain.toolCode",
      "typeVersion": 1.1,
      "position": [
        670,
        990
      ]
    },
    {
      "parameters": {
        "toolDescription": "Convierte un email en markdown en HTML que funcione en clientes de correo reales. Usalo cuando ya tengas el texto aprobado. Pasale el texto completo y el color de marca.",
        "name": "maquetador",
        "text": "={{ $fromAI('encargo', 'El encargo completo para este especialista: que necesitas, con que material y en que formato lo quieres de vuelta') }}",
        "hasOutputParser": false,
        "options": {
          "systemMessage": "Eres maquetador de emails. Recibes texto y devuelves HTML.\n\nConsulta tu documento de reglas antes de maquetar: el HTML de email no es HTML\nde web y lo que funciona en el navegador se rompe en Outlook.\n\nDEVUELVE UNICAMENTE EL HTML. Empieza por <!DOCTYPE html> y termina en </html>.\nSin explicaciones y sin vallas de codigo markdown.",
          "maxIterations": 6
        }
      },
      "id": "maquetador",
      "name": "maquetador",
      "type": "@n8n/n8n-nodes-langchain.agentTool",
      "typeVersion": 2.2,
      "position": [
        940,
        760
      ]
    },
    {
      "parameters": {
        "model": "anthropic/claude-sonnet-5",
        "options": {
          "maxTokens": 3200
        }
      },
      "id": "sonnet-5---html",
      "name": "Sonnet 5 - HTML",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenRouter",
      "typeVersion": 1,
      "position": [
        850,
        990
      ]
    },
    {
      "parameters": {
        "name": "reglas_html_email",
        "description": "Reglas de HTML de email que sobreviven a Outlook y a Gmail",
        "language": "javaScript",
        "jsCode": "return \"HTML DE EMAIL — LO QUE DE VERDAD FUNCIONA\\n\\nESTRUCTURA\\n- Layout con <table>, nunca flexbox ni grid: Outlook usa el motor de Word.\\n- Tabla exterior al 100% + tabla interior de 600px, centrada con align=\\\"center\\\".\\n- Nada de position, float ni margin negativo.\\n\\nCSS\\n- Todo en linea, en atributos style. Un <style> en el head lo elimina Gmail\\n  en algunos clientes.\\n- Fuentes con fallback: Arial, Helvetica, sans-serif. Nada de webfonts.\\n- Interlineado explicito: font:16px/1.6 Arial,sans-serif.\\n\\nBOTONES\\n- Nunca <button>. Un <a> con padding, background y display:inline-block.\\n- Minimo 44px de alto: se pulsa con el dedo.\\n\\nOBLIGATORIO\\n- Enlace de baja al final con el placeholder {{unsubscribe_url}}.\\n- Ancho maximo 600px.\\n- Texto alternativo en toda imagen: muchos clientes las bloquean por defecto.\\n\\nMOVIL\\nMas del 70% de los emails se abren en el movil. Una sola columna siempre.\";"
      },
      "id": "doc-reglas_html_email",
      "name": "doc: reglas_html_email",
      "type": "@n8n/n8n-nodes-langchain.toolCode",
      "typeVersion": 1.1,
      "position": [
        1050,
        990
      ]
    },
    {
      "parameters": {
        "toolDescription": "Define la automatizacion: que dispara la secuencia, cuanto se espera entre emails, que ramas hay segun comportamiento y que saca a alguien de la secuencia. Usalo cuando ya tengas la arquitectura.",
        "name": "automatizador",
        "text": "={{ $fromAI('encargo', 'El encargo completo para este especialista: que necesitas, con que material y en que formato lo quieres de vuelta') }}",
        "hasOutputParser": false,
        "options": {
          "systemMessage": "Eres arquitecto de automatizacion de email. Defines COMO se ejecuta la\nsecuencia, no que dice.\n\nConsulta tu documento de entregabilidad antes de proponer tiempos.\n\nDevuelve:\nDISPARADOR: que evento mete a alguien en la secuencia\nESPERAS: cuanto entre cada email y por que\nRAMAS: que pasa si abre y no hace clic, si hace clic y no convierte, y si no\n  abre nada\nSALIDAS: que saca a alguien de la secuencia\nTOPES: frecuencia maxima por contacto y ventana horaria\n\nNo propongas ramas que no se puedan medir con datos de un ESP normal: apertura,\nclic, baja y conversion.",
          "maxIterations": 6
        }
      },
      "id": "automatizador",
      "name": "automatizador",
      "type": "@n8n/n8n-nodes-langchain.agentTool",
      "typeVersion": 2.2,
      "position": [
        1320,
        760
      ]
    },
    {
      "parameters": {
        "model": "anthropic/claude-sonnet-5",
        "options": {
          "maxTokens": 1800
        }
      },
      "id": "sonnet-5---secuencia",
      "name": "Sonnet 5 - secuencia",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenRouter",
      "typeVersion": 1,
      "position": [
        1230,
        990
      ]
    },
    {
      "parameters": {
        "name": "entregabilidad",
        "description": "Buenas practicas de entregabilidad, timing y frecuencia de envio",
        "language": "javaScript",
        "jsCode": "return \"ENTREGABILIDAD Y TIMING\\n\\nTECNICO (sin esto, nada de lo demas importa)\\n- SPF, DKIM y DMARC configurados en el dominio.\\n- Dominio nuevo: warm-up de 2 a 4 semanas subiendo volumen poco a poco.\\n- Ratio texto/imagen: al menos 60% texto. Un email que es una sola imagen va a\\n  spam.\\n\\nFRECUENCIA\\n- Maximo 2-3 emails por semana y contacto en secuencias activas.\\n- Nunca dos emails el mismo dia al mismo contacto.\\n- Respeta una ventana horaria: martes a jueves, 9-11h en la zona del contacto,\\n  suele rendir mejor en B2B.\\n\\nHIGIENE DE LISTA\\n- Saca a los dormidos de mas de 6 meses: bajan tu reputacion de envio.\\n- Rebotes duros: eliminar de inmediato.\\n- Baja en un clic, visible. Esconderla genera marcas de spam, que cuestan mucho\\n  mas que una baja.\\n\\nPALABRAS QUE DISPARAN FILTROS\\ngratis, urgente, garantizado, sin riesgo, oferta limitada, actua ahora,\\n100%, felicidades, dinero facil.\";"
      },
      "id": "doc-entregabilidad",
      "name": "doc: entregabilidad",
      "type": "@n8n/n8n-nodes-langchain.toolCode",
      "typeVersion": 1.1,
      "position": [
        1430,
        990
      ]
    },
    {
      "parameters": {
        "promptType": "define",
        "text": "=Te llega esto para auditar. No sabes quien lo hizo ni como.\n\n{{ $json.output }}\n\nAuditalo.",
        "hasOutputParser": false,
        "options": {
          "systemMessage": "Eres auditor externo. No formas parte del equipo que produjo esto y no viste\ncomo se hizo: solo ves el resultado, que es exactamente lo que veria el\ncliente.\n\nNO reescribes nada. Si te dan ganas de mejorar el texto, aguantate y\ndescribelo como problema.\n\nComprueba:\n1. FORMATO: hay linea ASUNTO? hay PREHEADER? hay HTML que empiece por\n   <!DOCTYPE? Si falta alguna, es BLOQUEANTE: la campana no se puede crear.\n2. ASUNTO: 9 palabras o menos, sin mayusculas sostenidas, un emoji como maximo.\n3. PREHEADER: entre 40 y 90 caracteres, y no repite el asunto.\n4. HTML: usa <table>? el CSS esta en linea? hay enlace de baja? ancho 600px?\n   Marca [ROMPE EN OUTLOOK] lo que uses de HTML moderno.\n5. TONO: marca [JERGA] la jerga corporativa vacia y [EXAGERADO] las promesas\n   desmedidas.\n6. GENERICO: el primer parrafo se podria enviar a cualquier otra empresa? Si\n   si, marcalo.\n\nCierra con una linea exacta:\n\nVEREDICTO: PUBLICABLE\no\nVEREDICTO: NO SUBIR - [motivo en una frase]\n\nSi no encuentras ni un problema, dilo y enumera que comprobaste. No inventes\nproblemas para parecer util."
        }
      },
      "id": "revisor-ciego",
      "name": "REVISOR CIEGO",
      "type": "@n8n/n8n-nodes-langchain.agent",
      "typeVersion": 2,
      "position": [
        1900,
        300
      ],
      "notes": "Colgado DESPUES del orquestador, no como herramienta suya. Solo ve el artefacto terminado: ni el brief, ni las llamadas, ni quien fallo. Patron 4.6 — revisor ciego."
    },
    {
      "parameters": {
        "model": "anthropic/claude-sonnet-5",
        "options": {
          "maxTokens": 2000
        }
      },
      "id": "sonnet-5---auditoria",
      "name": "Sonnet 5 - auditoria",
      "type": "@n8n/n8n-nodes-langchain.lmChatOpenRouter",
      "typeVersion": 1,
      "position": [
        1900,
        60
      ]
    },
    {
      "parameters": {
        "method": "POST",
        "url": "https://api.brevo.com/v3/emailCampaigns",
        "authentication": "genericCredentialType",
        "genericAuthType": "httpHeaderAuth",
        "sendBody": true,
        "specifyBody": "json",
        "jsonBody": "={{ (() => {\n  const salida = $('ORQUESTADOR').item.json.output;\n  const asunto = (salida.match(/ASUNTO:\\s*(.+)/) || [null,'Sin asunto'])[1].trim();\n  const pre = (salida.match(/PREHEADER:\\s*(.+)/) || [null,''])[1].trim();\n  const m = salida.match(/<!DOCTYPE[\\s\\S]*<\\/html>/i);\n  const html = m ? m[0] : '<html><body><pre>' + salida + '</pre></body></html>';\n  return JSON.stringify({\n    name: 'Squad — ' + $('El brief').item.json.campana.slice(0,60) + ' — ' + $now.toFormat('LL-dd HH:mm'),\n    subject: asunto,\n    sender: { name: 'GrowthPilot', email: $('El brief').item.json.sender_email },\n    recipients: { listIds: [ Number($('El brief').item.json.brevo_list_id) ] },\n    htmlContent: html,\n    previewText: pre\n  });\n})() }}",
        "options": {}
      },
      "id": "brevo-campana-draft",
      "name": "Brevo: campana draft",
      "type": "n8n-nodes-base.httpRequest",
      "typeVersion": 4.2,
      "position": [
        2280,
        300
      ],
      "notes": "Crea la campana como DRAFT: nunca envia. Credencial Header Auth con Name 'api-key' y Value tu clave xkeysib-... Si el revisor dijo NO SUBIR, borra la campana desde Brevo y corrige el brief."
    }
  ],
  "connections": {
    "Brief de campana": {
      "main": [
        [
          {
            "node": "El brief",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "Opus 5 - el jefe": {
      "ai_languageModel": [
        [
          {
            "node": "ORQUESTADOR",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "El brief": {
      "main": [
        [
          {
            "node": "ORQUESTADOR",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "estratega": {
      "ai_tool": [
        [
          {
            "node": "ORQUESTADOR",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "Opus 5 - estrategia": {
      "ai_languageModel": [
        [
          {
            "node": "estratega",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "doc: marco_de_segmentacion": {
      "ai_tool": [
        [
          {
            "node": "estratega",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "copywriter": {
      "ai_tool": [
        [
          {
            "node": "ORQUESTADOR",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "Opus 5 - copy": {
      "ai_languageModel": [
        [
          {
            "node": "copywriter",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "doc: brand_voice": {
      "ai_tool": [
        [
          {
            "node": "copywriter",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "maquetador": {
      "ai_tool": [
        [
          {
            "node": "ORQUESTADOR",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "Sonnet 5 - HTML": {
      "ai_languageModel": [
        [
          {
            "node": "maquetador",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "doc: reglas_html_email": {
      "ai_tool": [
        [
          {
            "node": "maquetador",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "automatizador": {
      "ai_tool": [
        [
          {
            "node": "ORQUESTADOR",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "Sonnet 5 - secuencia": {
      "ai_languageModel": [
        [
          {
            "node": "automatizador",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "doc: entregabilidad": {
      "ai_tool": [
        [
          {
            "node": "automatizador",
            "type": "ai_tool",
            "index": 0
          }
        ]
      ]
    },
    "Sonnet 5 - auditoria": {
      "ai_languageModel": [
        [
          {
            "node": "REVISOR CIEGO",
            "type": "ai_languageModel",
            "index": 0
          }
        ]
      ]
    },
    "ORQUESTADOR": {
      "main": [
        [
          {
            "node": "REVISOR CIEGO",
            "type": "main",
            "index": 0
          }
        ]
      ]
    },
    "REVISOR CIEGO": {
      "main": [
        [
          {
            "node": "Brevo: campana draft",
            "type": "main",
            "index": 0
          }
        ]
      ]
    }
  },
  "pinData": {},
  "settings": {
    "executionOrder": "v1"
  },
  "tags": []
}
