tva
← Insights

Cómo Configurar un Buzón de Correo para tu Agente de IA de Proyecto

Tarde o temprano, el agente de IA específico de proyecto que construiste necesita una dirección de correo electrónico. El patrón de bot de Telegram que describimos en Cómo Crear un Asistente de IA Específico de Proyecto via Telegram gestiona el chat en tiempo real, pero el correo es un canal diferente: notificaciones de servicios, confirmaciones de proveedores, restablecimientos de contraseña OAuth, correspondencia de backoffice con personas que no usan Telegram. Puedes redirigir ese correo a una dirección personal y vivir con el ruido, o puedes darle al proyecto su propio buzón en un subdominio dedicado.

Esta guía cubre la segunda opción: un buzón dedicado en un subdominio de proyecto, con DKIM, SPF y DMARC configurados correctamente. El patrón utiliza un proveedor para el DNS (Cloudflare en nuestro caso) y un proveedor separado para el sistema de correo (Opalstack), que es la configuración con la que acaban la mayoría de las operaciones pequeñas: DNS donde ya vive el dominio apex, correo en el proveedor que tenga un IMAP decente, acceso API razonable y una reputación que sobreviva a los filtros de Gmail.

La configuración completa son cuatro llamadas API más tres registros DNS. Con la preparación adecuada, tarda unos diez minutos de principio a fin. Te mostraremos las llamadas, la verificación y los modos de fallo que nos pillaron la primera vez.

Qué Resuelve Esta Guía

  • Un subdominio de proyecto (system.example.com) sin infraestructura de correo asociada
  • Correo entrante a una dirección específica de proyecto que rebota porque no existe ningún registro MX
  • Correo saliente del proyecto que falla las verificaciones DKIM en Gmail y acaba en spam
  • Registros SPF y DMARC que existen pero no tienen nada contra lo que autenticar
  • Un agente de IA que necesita un canal de correo sin enrutarlo a través de tu cuenta personal

Lo Que Necesitarás

  • Un dominio apex que controles, con DNS en un proveedor que exponga una API (Cloudflare, Route53, DigitalOcean DNS, etc.)
  • Un proveedor de correo que admita añadir dominios via API, genere claves DKIM al crear el dominio y exponga endpoints IMAP/SMTP (Opalstack, Mailcow, Migadu, Fastmail, etc.)
  • Tokens API para ambos proveedores, almacenados en algún lugar desde el que puedas ejecutar comandos de shell
  • dig, openssl s_client y un intérprete de Python para la verificación
  • Unos quince minutos

Por Qué el Patrón de Mezcla de Proveedores

El modelo mental por defecto es "un único proveedor para todo": alojar el sitio web, el DNS y el buzón en el mismo lugar. Eso funciona hasta que cualquiera de los tres necesita evolucionar de forma independiente. Cubrimos el marco de decisión para elegir entre servicios agrupados y especialistas dedicados en La Decisión de Self-Hosting: Cuándo el SaaS Cuesta Más que tu Propia Infraestructura, y la misma lógica aplica aquí a menor escala.

En nuestro caso, el DNS del dominio apex está en Cloudflare porque necesitamos la resolución AnyCast, el proxying para los sitios públicos y la API para la gestión automatizada de registros. El sistema de correo está en Opalstack porque su coste por buzón es insignificante, la reputación de su servidor IMAP es sólida y su API es una de las más limpias del espacio de hosting de correo en la UE. No vamos a mover el DNS para mejorar el correo, ni el correo para mejorar el DNS. El coste de gestionarlos por separado son exactamente tres registros DNS y un único modelo mental: el proveedor DNS le dice al mundo adónde va el correo; el proveedor de correo lo recibe, almacena y firma.

Esta separación importa operativamente porque limita el radio de explosión de un fallo. Una interrupción del proveedor DNS detiene nuevas decisiones de enrutamiento de correo, pero el correo ya en tránsito hacia los hosts MX sigue llegando. Una interrupción del proveedor de correo detiene la entrega, pero las consultas DNS siguen resolviéndose. Si hubiéramos apilado todo en un único proveedor, ambas capas habrían fallado juntas. La misma lógica aparece en nuestra arquitectura de producción para apilar reverse proxies: separación de responsabilidades, cada capa reemplazable de forma independiente.

Buzón Dedicado, Alias de Reenvío o Bandeja de Entrada SaaS

Antes de crear nada, elige el nivel de dedicación adecuado. Las tres opciones no son equivalentes.

Un buzón dedicado significa una bandeja de entrada real que almacena correo, tiene credenciales IMAP y puede tanto enviar como recibir. Coste: aproximadamente uno a tres euros al mes en un proveedor de correo self-hosted, más el trabajo de configuración de la API. Esto es lo que usa el agente de IA cuando necesita leer correo de verdad: para parsear confirmaciones entrantes de proveedores, gestionar notificaciones de servicios o mantener un hilo con un interlocutor humano a lo largo de varios intercambios.

Un alias de reenvío significa una dirección virtual que simplemente redirige a una bandeja de entrada existente. Coste: cero, solo configuración. Es la opción correcta cuando el agente de IA solo necesita recibir en una dirección de marca del proyecto, pero la lectura y el procesamiento reales ocurren en una bandeja humana ya existente. El inconveniente es que el agente no tiene acceso IMAP, no hay filtrado por proyecto en el destino y no hay una ruta de rollback limpia cuando el proyecto termina: la limpieza de aliases se olvida.

Una bandeja de entrada SaaS significa un servicio como Postmark, Mailgun Inbound o AWS SES con reglas de recepción. Coste: facturación por mensaje más el trabajo de ingeniería para conectar el agente de IA a los receptores de webhooks. Es la opción correcta cuando el agente necesita gestionar alto volumen, enrutar correo por reglas de cabeceras o disparar flujos de trabajo automatizados en cada mensaje. Para un agente de proyecto específico que gestiona decenas o cientos de mensajes al mes, es excesivo.

Para el caso de uso del artículo sobre el asistente de IA en Telegram: un operador humano, dos colaboradores del proyecto y un bot respaldado por Claude, el buzón dedicado es la solución correcta. El agente obtiene una dirección real que puede leer con IMAP, desde la que puede enviar con SMTP y que vive o muere de forma limpia con el proyecto.

Paso 1: Registrar el Subdominio en tu Sistema de Correo

El proveedor de correo tiene que saber que tu subdominio de proyecto es uno de sus dominios antes de aceptar correo para él. Esta es la llamada que también genera el par de claves DKIM.

POST https://my.mailhost.example/api/v1/domain/create/
Authorization: Token <YOUR_MAIL_API_TOKEN>
Content-Type: application/json

[{"name": "system.example.com"}]

La respuesta contiene tres campos que te interesan: el UUID del dominio (que necesitas para la limpieza y para el mapeo de direcciones más adelante), el campo state (normalmente PENDING_CREATE unos segundos, luego READY) y un campo dkim_record con un valor TXT completamente formateado listo para pegar en DNS:

{
  "id": "<DOMAIN_UUID>",
  "state": "PENDING_CREATE",
  "name": "system.example.com",
  "dkim_record": "v=DKIM1; k=rsa; p=MIGfMA0GCSqGSIb3DQEBAQUAA4G..."
}

Espera hasta que state cambie a READY y luego captura el valor de dkim_record. Lo pegarás tal cual en el proveedor DNS en el siguiente paso. Si la llamada de creación falla con un error de invalid hostname, la causa más común es que tu proveedor de correo solo admite dominios de segundo nivel y rechaza subdominios de tres niveles. Abre un ticket de soporte; hasta ahora no hemos encontrado ningún proveedor que lo rechace en la práctica.

Antes de continuar, verifica el tamaño de la clave DKIM. Un valor de dkim_record de menos de unos 250 bytes es una clave RSA de 1024 bits; las claves de 2048 bits tienen entre 380 y 420 bytes aproximadamente. NIST declaró obsoleto el RSA de 1024 bits en 2013, y Gmail, Microsoft, Yahoo y AWS SES tratan las claves de 2048 bits como el estándar de referencia en 2026: las de 1024 bits siguen autenticando, pero suponen una señal débil en los filtros de spam empresariales. Si tu proveedor te permite elegir el tamaño, elige 2048; un valor predeterminado de solo 1024 bits es una señal sobre la calidad del proveedor.

Paso 2: Configurar los Registros DNS

Tres registros, todos creados en tu proveedor DNS para el subdominio del proyecto. Ninguno puede enrutarse a través del edge de Cloudflare: los registros MX y TXT deben ser DNS-only, y la API de Cloudflare silenciosamente los dejará como DNS-only si configuras proxied: true, pero es más limpio establecerlo explícitamente.

Los dos registros MX le dicen a los remitentes dónde entregar el correo. La mayoría de los proveedores de correo tienen dos o más hosts MX con igual prioridad para un failover round-robin:

POST https://api.dnsprovider.example/zones/<ZONE_ID>/dns_records

{"type":"MX","name":"system.example.com",
 "content":"mx1.de.mailhost.example","priority":10,
 "ttl":3600,"proxied":false}

{"type":"MX","name":"system.example.com",
 "content":"mx2.de.mailhost.example","priority":10,
 "ttl":3600,"proxied":false}

El registro TXT de DKIM usa el valor dkim_record del Paso 1, colocado en dkim._domainkey.<subdominio>:

{"type":"TXT",
 "name":"dkim._domainkey.system.example.com",
 "content":"v=DKIM1; k=rsa; p=MIGfMA0G...",
 "ttl":3600,"proxied":false}

Si la clave pública DKIM tiene más de 255 bytes (que es el caso de las claves RSA de 2048 bits), tendrás que dividirla en múltiples fragmentos entre comillas: "fragmento1" "fragmento2". La mayoría de los proveedores DNS gestionan la división automáticamente en su API; si el tuyo no lo hace, tendrás que hacerlo tú.

Los registros SPF y DMARC se configuran una vez, en el propio subdominio y en _dmarc.<subdominio>. SPF le dice a los receptores qué IPs están autorizadas a enviar para este dominio; DMARC les dice qué hacer cuando SPF o DKIM fallan:

{"type":"TXT","name":"system.example.com",
 "content":"v=spf1 include:spf.mailhost.example ~all",
 "ttl":3600,"proxied":false}

{"type":"TXT","name":"_dmarc.system.example.com",
 "content":"v=DMARC1; p=none; rua=mailto:[email protected]; aspf=r; adkim=r",
 "ttl":3600,"proxied":false}

Empieza DMARC con p=none. Esto es el modo de monitorización: los receptores envían informes agregados a la dirección rua, pero no se rechaza ningún correo por política. El proceso de implantación estándar consiste en dos a seis semanas en p=none hasta que los informes agregados muestren al menos un 98% de cumplimiento para el correo legítimo, seguido de una rampa gradual mediante la etiqueta pct=: por ejemplo p=quarantine; pct=25 durante dos semanas, luego pct=75, luego pct=100 y finalmente p=reject. Saltarse la rampa e ir directamente a p=reject en un dominio completamente nuevo es una manera segura de descartar tu propio correo legítimo antes de haber validado la cadena de firma DKIM.

Paso 3: Crear el Buzón y el Mapeo de Direcciones

El modelo de datos del proveedor de correo suele tener dos recursos separados: un mailuser (la cuenta IMAP con credenciales y cuota) y una dirección (la cadena local@dominio que enruta el correo a un mailuser). Son recursos separados porque el mismo mailuser puede ser el destino de varias direcciones distintas en el mismo dominio o en dominios diferentes.

Genera una contraseña robusta y crea el mailuser. La convención de nombres varía según el proveedor; el patrón habitual es <local>_<dominio-con-guiones-bajos>. Atento al límite de longitud: la mayoría de los proveedores limitan los nombres de mailuser a 32 caracteres, algo fácil de superar con un subdominio largo:

import secrets, string
alphabet = string.ascii_letters + string.digits + "!@#%^&*-_=+"
password = ''.join(secrets.choice(alphabet) for _ in range(32))

# Luego:
POST /api/v1/mailuser/create/
[{"name": "bot_system_example_com",
  "imap_server": "<IMAP_SERVER_UUID>",
  "password": password}]

Una vez que el mailuser esté en estado READY, crea el mapeo de dirección que vincula local@subdominio con él:

POST /api/v1/address/create/
[{"source": "[email protected]",
  "destinations": ["<MAILUSER_UUID>"],
  "forwards": []}]

El array forwards sirve para enviar copias a direcciones externas adicionales. Déjalo vacío a menos que quieras reenviar el buzón a una bandeja humana en paralelo, lo cual es un patrón útil durante la fase de traspaso del proyecto pero que a largo plazo genera desorden.

Paso 4: Verificar la Configuración de Extremo a Extremo

Cuatro verificaciones, en orden. No omitas la del bucle interno: es la única prueba que confirma que el enrutamiento entrante llega realmente al buzón.

Propagación DNS. Los proveedores AnyCast de la clase de Cloudflare suelen propagar en bien menos de un minuto. Repite hasta que aparezcan ambos registros:

for i in $(seq 1 36); do
  mx=$(dig +short system.example.com MX)
  dkim=$(dig +short dkim._domainkey.system.example.com TXT)
  if [ -n "$mx" ] && [ -n "$dkim" ]; then break; fi
  sleep 5
done
echo "MX: $mx"
echo "DKIM: $dkim"

Login IMAP. Confirma que las credenciales funcionan y que el buzón está respaldado por una bandeja de entrada real:

openssl s_client -crlf -connect imap.mailhost.example:993 -quiet
a1 LOGIN bot_system_example_com <password>
a2 SELECT INBOX

Respuesta esperada: a1 OK Logged in seguido del SELECT confirmando EXISTS 0 en un buzón recién creado.

Bucle interno (self-loopback). La mejor prueba de extremo a extremo: enviar un correo desde la nueva dirección a sí misma y comprobar que llega al IMAP. Esto valida toda la cadena: autenticación SMTP, firma DKIM, resolución MX, aceptación del correo, entrega al buzón, visibilidad IMAP, sin depender de que el filtro de spam de ningún proveedor externo coopere:

import smtplib, ssl, imaplib, time
from email.message import EmailMessage

msg = EmailMessage()
msg["From"] = "[email protected]"
msg["To"]   = "[email protected]"
msg["Subject"] = "loopback test"
msg.set_content("hello self")

with smtplib.SMTP("smtp.mailhost.example", 587) as s:
    s.starttls(context=ssl.create_default_context())
    s.login("bot_system_example_com", "<password>")
    s.send_message(msg)

time.sleep(10)
imap = imaplib.IMAP4_SSL("imap.mailhost.example", 993)
imap.login("bot_system_example_com", "<password>")
imap.select("INBOX")
typ, search = imap.search(None, "ALL")
print("inbox count:", len(search[0].split()))

En las cabeceras del correo entregado, busca la línea Authentication-Results. Una configuración correcta mostrará spf=pass con el smtp.mailfrom correcto y una cabecera DKIM-Signature con d=<tu subdominio> y s=dkim. Si están presentes, cada parte de la cadena funciona; la única variable restante es cómo te valoran los receptores externos, cosa que los informes DMARC te irán contando a lo largo de los días siguientes.

Salida externa. Envía un correo a una dirección externa que puedas verificar: un Gmail personal, una bandeja de trabajo separada, algo fuera del sistema. Confirma que llega a la bandeja de entrada, no al spam. Si el primer envío desde un dominio nuevo acaba en spam, la causa más frecuente es que la reputación del dominio remitente todavía no existe; el calentamiento es gradual, pero un único correo de prueba debería pasar limpiamente porque el receptor evalúa DKIM y SPF por sus propios méritos, no por el volumen histórico de envíos.

Errores Habituales

El límite de 32 caracteres en el nombre de mailuser aparece cuando tu subdominio más la parte local es más larga de lo esperado. backoffice_dashboard_system_example_com tiene treinta y nueve caracteres y es rechazado; bo_dashboard_system_example_com cabe con treinta y uno. Elige las abreviaturas conscientemente en lugar de dejar que la API te las imponga a mitad del despliegue.

La trampa del proxy de Cloudflare. La interfaz de Cloudflare permite activar el proxy de la nube naranja en cualquier registro. Para A/AAAA en un origen web casi siempre querrás tenerlo activado. Para registros MX, siempre desactivado: Cloudflare no proxifica correo. La trampa surge cuando activas el proxying en masa mediante un script e incluyes accidentalmente los registros MX. Cloudflare descarta silenciosamente la opción de proxy para los tipos no compatibles, así que parece que ha funcionado, pero puedes perder minutos intentando descubrir qué ha fallado.

Greylisting en el primer correo entrante. Los sistemas de correo a veces ponen en lista gris el primer mensaje de un remitente desconocido: respuesta temporal 4xx, solicitan al remitente que reintente en unos minutos. Gmail reintenta automáticamente. Si tu primera prueba de humo de correo entrante parece fallar, espera quince minutos antes de declararlo roto.

El límite de consultas DNS de SPF. SPF tiene un límite estricto de diez consultas DNS durante la evaluación (RFC 7208 §4.6.4). Un único include:spf.mailhost.example cuenta como una consulta aunque ese include se resuelva internamente a docenas de IPs. Solo alcanzas el límite si empiezas a encadenar varios remitentes: por ejemplo, añadir más adelante include:_spf.resend.com para un pipeline de marketing. Planifica el registro SPF pensando en la lista de remitentes a largo plazo, no solo en el primero.

Campo dkim_privkey vacío en el lado del proveedor de correo. Algunos proveedores exponen un endpoint de creación de dominio que tiene éxito pero no genera realmente la clave DKIM, requiriendo una llamada separada de "activar DKIM". Verifica que el campo dkim_record en la respuesta de creación no esté vacío antes de continuar. Si está vacío, consulta la documentación del proveedor para encontrar la llamada secundaria.

Monitorización superficial del despliegue. Si gestionas docenas de dominios, un registro DKIM defectuoso o un destino de informes DMARC caducado no aparecerán en la monitorización rutinaria a menos que los compruebes activamente. Nuestra rutina de revisión mensual para servicios self-hosted incluye un paso de auditoría de registros de correo precisamente por este motivo.

Ignorar MTA-STS cuando está disponible. MTA-STS publica una política que obliga a los remitentes a usar TLS hacia tus hosts MX y a validar el certificado. Gmail, Microsoft 365 y Yahoo lo comprueban; la adopción global todavía está por debajo del uno por ciento, así que una política válida es una pequeña señal de reputación. El inconveniente es operativo: una política que apunta a hosts MX que fallan la verificación TLS bloquea el correo entrante legítimo. Si tu proveedor expone MTA-STS, actívalo después de que DKIM y DMARC estén estables.

Proceso de Rollback

Si la verificación falla o decides que el proyecto no necesita su propio buzón, la limpieza es idempotente y tarda cinco minutos:

  1. POST /api/v1/address/delete/ con el UUID de la dirección
  2. POST /api/v1/mailuser/delete/ con el UUID del mailuser
  3. POST /api/v1/domain/delete/ con el UUID del dominio en el sistema de correo (esto también elimina las claves DKIM)
  4. DELETE /zones/<zone>/dns_records/<id> para cada uno de los tres registros DNS

El orden importa porque algunos proveedores se niegan a eliminar el dominio mientras tenga direcciones asociadas. El orden inverso también te da un punto razonable donde detenerte e inspeccionar: si el Paso 1 falla porque hay correo en el buzón que olvidaste, todavía no has roto el enrutamiento a nivel DNS.

Dejar los registros SPF y DMARC en el subdominio tras un rollback es inofensivo. Autentican contra nada, pero también le dicen a los receptores futuros que este subdominio explícitamente no envía correo legítimo, lo que supone un pequeño beneficio anti-spoofing. Los tratamos como activados por defecto una vez que existen. Este tipo de razonamiento sobre "residuos seguros" es la misma lógica que aplicamos a la recuperación ante desastres para servicios self-hosted: el patrón de limpieza posterior importa tanto como el patrón de instalación.

Conclusión

Un buzón de proyecto específico no es infraestructura; es un pequeño primitivo operativo que permite a un agente de IA —o a cualquier otro proceso automatizado— convertirse en un participante de primera clase en los flujos de trabajo basados en correo electrónico. El patrón de cuatro llamadas API anterior se traslada limpiamente entre proveedores de correo; los registros DNS se trasladan limpiamente entre proveedores DNS. Lo que vale la pena hacer bien es el límite entre los dos sistemas: qué registro vive dónde, cómo son los modos de fallo y cómo verificar de extremo a extremo sin depender de que el filtro de spam de ningún proveedor externo se comporte correctamente.

Si quieres ayuda para diseñar un stack específico de proyecto —agente de Telegram, buzón de correo, ingesta de documentos y todo lo demás— tva puede ayudarte.


Artículos Relacionados

Artículos relacionados