
Por Matías Machado
En un momento donde la inteligencia artificial está revolucionando la forma en que trabajamos en IT, este proyecto se destacó por ir un paso más allá: usamos IA para automatizar una migración compleja de infraestructura.
Una compañía global con arquitectura basada en Azure Service Bus y más de 900 suscripciones activas necesitaba migrar su sistema de mensajería a AWS SNS + SQS. ¿El problema? Cada suscripción incluía lógicas de filtrado personalizadas, muchas de ellas imposibles de traducir directamente sin refactor.
Lo que podría haber llevado semanas de trabajo manual se resolvió en horas, gracias al uso de OpenAI y Terraform. En este artículo te contamos cómo lo hicimos: desde el diseño modular con IaC, hasta la automatización de la traducción de filtros con GPT-4.
El desafío: llevar esta arquitectura a AWS utilizando SNS + SQS, respetando las lógicas de filtrado existentes, con una fuerte apuesta por escalar la gestión de estos recursos mediante Infraestructura como Código (IaC).
En este artículo exploramos la solución implementada, las herramientas utilizadas, los obstáculos encontrados y el rol clave de OpenAI para automatizar la traducción de filtros.
Contexto y arquitectura
En la arquitectura original:
- Cada componente del sistema (ventas, facturación, órdenes, productos, etc.) publicaba mensajes en un topic de Azure Service Bus.
- Cada tenant tenía su conjunto de queues que se suscribían a estos topics, con filtros de mensajes personalizados.
En AWS se replicó este modelo con:
- SNS Topics como puntos de publicación.
- SQS Queues para cada tenant, con SNS Subscriptions que aplican filter policies.
Etapas del desarrollo
1. Relevamiento y planificación
Se realizó un relevamiento completo de los recursos en Azure, incluyendo:
- Topics existentes
- Suscripciones por tenant
- Filtros utilizados en cada suscripción
Se identificaron más de 900 suscripciones activas, con una diversidad de filtros complejos, muchos de ellos imposibles de traducir directamente a SNS Filter Policies debido a las restricciones propias del servicio (ej: máximo de 5 atributos por filtro).
2. Terraform para IaC
Se desarrolló un módulo de Terraform para manejar SNS + SQS, permitiendo leer la configuración desde archivos .tfvars.json por tenant.
module "sns_sqs" {
source = "../../modules/sqs-subscriptions"
tenants_configuration = var.tenants_configuration
}
Cada archivo tfvars.json contiene la definición de queues y filtros del tenant correspondiente.
El estado de Terraform se almacena de forma aislada por tenant en `
`. Para poder automatizar la creación y gestión de los distintos tenants no se define en código, sino en runtime de Terraform:sqs-subscriptions/${tenant}/terraform.tfstate
backend "s3" {
bucket = "infraestructura-iac"
region = "us-east-1"
}
TENANT="DUMMY"
terraform init -backend-config="sqs-subscriptions/${TENANT}/terraform.tfstate"
terraform apply -var-file="clients.tfvars.d/${TENANT}.tfvars.json"
Esta organización permite mantener separados los despliegues y actualizar individualmente por tenant.
3. El problema del filtrado: Azure vs AWS
Azure Service Bus permite queries complejas en los filtros, como:
messageType = 'order.created' AND isVIP = true AND region IN ('us', 'mx')
SNS en cambio soporta filter policies con un máximo de 5 atributos, sin queries SQL:
{
"messageType": ["order.created"],
"region": ["us", "mx"]
}
Esto hizo necesario reformular la lógica de filtrado. Por ejemplo, se reemplazaron flags booleanas por un array de “tags” para cada mensaje:
{
"tags": ["vip", "expedited"]
}
4. Uso de OpenAI para traducir filtros
Traducir manualmente 900+ filtros llevaría más de 200 horas. Para automatizar esto, se desarrolló un script en Python que:
1. Lee el archivo JSON con todas las suscripciones scrapeadas de Azure.
2. Utiliza la API de OpenAI (GPT-4) con un prompt diseñado para traducir la lógica de filtrado al formato SNS.
3. Actualiza el JSON final que luego es consumido por Terraform.
Fragmento de código del script:
import openai
response = openai.ChatCompletion.create(
model="gpt-4",
messages=[
{"role": "system", "content": "Convert Azure Service Bus SQL filter to AWS SNS filter policy"},
{"role": "user", "content": f"SQL Filter: {azure_filter}\nAttributes: {attribute_list}"}
]
)
json_output = response["choices"][0]["message"]["content"]
sns_filter = json.loads(json_output)
Se forzó al modelo a devolver únicamente JSON válido, lo cual permite parsear con json.loads
y garantizar compatibilidad con Terraform.
5. Prompt Engineering aplicado
El uso de modelos de lenguaje como GPT-4 para resolver problemas técnicos depende en gran medida de una disciplina conocida como prompt engineering.
Esta práctica consiste en diseñar instrucciones claras y precisas para que el modelo entienda el contexto, las reglas de negocio y el formato deseado en la respuesta.
En tareas técnicas como esta, un buen prompt puede marcar la diferencia entre resultados útiles o inconsistentes. A continuación, se muestra el prompt utilizado junto con ejemplos y un conjunto de buenas prácticas para su diseño:
El prompt utilizado fue cuidadosamente diseñado para minimizar errores de interpretación y asegurar consistencia en las respuestas. A continuación se muestra una versión más completa y anonimizada del prompt real.
Buenas prácticas aplicadas al diseñar el prompt:
- Dar contexto claro y establecer el rol: Se define al modelo como un “senior cloud engineer” para guiar el tono y nivel técnico esperado.
- Proveer ejemplos reales: Ejemplos concretos ayudan a establecer patrones y formatos deseados.
- Solicitar un formato de salida específico: Se indica explícitamente que la respuesta debe ser un objeto JSON válido, sin explicaciones.
- Modelos y parámetros bien definidos: Se utilizó gpt-4 con temperatura baja ( temperature=0 ) para obtener respuestas más consistentes y menos creativas, privilegiando precisión técnica.
Estas decisiones permitieron que el modelo no solo fuera efectivo, sino también confiable en respuestas repetidas, evitando ambigüedades e inconsistencias comunes cuando se omite contexto o formato.
You are a system that receives Azure Service Bus filter queries (SQL-like boolean expressions) and converts them into AWS SNS-compatible subscription filter policies in JSON format.
Your task is to:
1. Parse the Azure Service Bus filter query.
2. Convert the logical operators AND/OR and nested parentheses into SNS-compatible JSON format using:
- AND → multiple fields at the root level of the JSON object.
- OR → multiple values in a field's array (same key), or use "$or" to represent logical ORs across different fields or expressions.
3. Apply the following field transformations:
- Discard filters that contain `1=1` (no-op).
- When separating conditions inside a parenthesis that are under an OR into more than 1 field for SNS, those fields should be inside an OR operator. If there is only 1 field for SNS, don't use OR operator
4. Convert expressions as follows:
- `field = true` → `"field": [true]`
- `field = 'value'` or `field = value` (numeric) → `"field": ["value"]` (treat all values as **strings**)
- `field <> value` or `field != value` → `"field": [{ "anything-but": ["value"] }]` (value must be string)
- `field IS NULL` → `"field": [{ "exists": false }]`
- `field IS NOT NULL` → `"field": [{ "exists": true }]`
IMPORTANT: All values in the resulting SNS JSON must be strings, even if the original input uses numeric literals. Convert any numeric values to strings.
Output must be valid JSON representing the SNS subscription filter policy. Do not include explanations, headers, or any text besides the JSON.
---
Example 1 - Input:
1. Input: messageType = 'product.updated' AND region IN ('us', 'mx')
Output:
{
"messageType": ["product.updated"],
"region": ["us", "mx"]
}
2. Input: isActive = true OR status = 'pending'
Output:
{
"isActive": [true],
"status": ["pending"]
}
3. Input: messageType IN ('order.created', 'order.paid') AND priority = 'high'
Output:
{
"messageType": ["order.created", "order.paid"],
"priority": ["high"]
}
4. Input: region IN ('br', 'ar') AND isInternal = false AND environment = 'prod'
Output:
{
"region": ["br", "ar"],
"isInternal": [false],
"environment": ["prod"]
}
Esta solución, junto con las pruebas de validación, permitió completar el trabajo en menos de 50 horas, ahorrando más del 75% del tiempo estimado.
6. Validación y pruebas
Las nuevas configuraciones se validaron con pruebas unitarias, enviando mensajes de prueba y verificando que las SQS queues recibieran solo los mensajes esperados según los filtros traducidos. Cada tenant se migró de forma progresiva, permitiendo rollback inmediato en caso de error.
IA como herramienta de trabajo diario
Este caso demuestra que:
- La IA puede reducir semanas de trabajo intensivo.
- Combinada con Terraform + AWS IaC, mejora calidad y confiabilidad.
- GPT-4 es un recurso real para DevOps cuando se domina el prompt engineering.
¿Necesitas migrar a AWS con seguridad y velocidad?
En Craftech ayudamos a founders y equipos técnicos a modernizar su infraestructura con DevOps gestionado, Kubernetes y automatización IaC.
Agenda una reunión con nosotros y descubre cómo podemos ayudarte 👉 https://craftech.io/contact/