No uses Roles Primitivos: Crea Custom Roles en Google Cloud con Terraform (IAM)
Usar Owner o Editor para resolver rápidamente un problema de permisos puede parecer práctico durante el desarrollo, pero en producción convierte IAM en una superficie de riesgo, aumenta el blast radius y dificulta la gobernanza. En esta guía de nivel Senior / Staff / Architect diseñaremos roles personalizados de Google Cloud con Terraform para automatizar el principio de menor privilegio sin sacrificar operabilidad.
Lo que aprenderás
El problema arquitectónico: más permisos no significa más productividad
Uno de los antipatrones más habituales en Google Cloud es conceder un rol extremadamente amplio porque resuelve inmediatamente un error de autorización. El problema aparece cuando ese workaround llega a producción y se convierte en dependencia permanente.
IAM debe modelarse como parte de la arquitectura, no como una configuración manual posterior. La pregunta correcta no es “¿qué rol hace que funcione?”, sino: “¿qué conjunto mínimo de permisos permite que este workload realice exactamente su función?”
Los roles primitivos Owner, Editor y Viewer tienen una granularidad demasiado gruesa para muchos escenarios empresariales. Especialmente peligrosos son Owner y Editor cuando se asignan a identidades de workloads, pipelines CI/CD o cuentas de servicio.
El riesgo no es únicamente de seguridad. Un permiso excesivo también puede incrementar el blast radius operativo: una identidad comprometida o un pipeline defectuoso puede modificar recursos que nunca debería haber podido tocar.
Regla práctica: si una identidad sólo necesita leer BigQuery y ejecutar determinadas operaciones, no debería recibir capacidad administrativa sobre todo el proyecto.
Matriz de decisión IAM: ¿qué tipo de rol utilizar?
Custom Roles no significa que debamos crear un rol personalizado para cada identidad. La decisión correcta comienza por utilizar la opción más específica y mantenible disponible.
| Alternativa | Granularidad | Gobernanza | Riesgo | Coste operativo | Cuándo utilizarla |
|---|---|---|---|---|---|
| Owner / Editor | Muy baja | Difícil | Alto | Bajo inicialmente, alto a escala | Evitar como patrón de acceso para workloads y equipos. |
| Viewer | Baja | Moderada | Medio-bajo | Bajo | Acceso puramente de lectura cuando el alcance resulta adecuado. |
| Roles predefinidos | Alta | Alta | Bajo | Bajo | Primera opción para la mayoría de escenarios empresariales. |
| Custom Role | Muy alta | Alta si se gobierna como código | Muy bajo potencialmente | Medio | Cuando los roles predefinidos no permiten alcanzar el mínimo privilegio necesario. |
| Custom Role + Conditions | Muy alta | Muy alta | Muy bajo potencialmente | Medio-alto | Escenarios avanzados que requieren limitar adicionalmente recursos o contexto. |
¿Qué es realmente un Custom Role de Google Cloud?
Un Custom Role permite definir un conjunto explícito de permisos IAM que representa una capacidad concreta de negocio o plataforma. En lugar de asignar una colección amplia de privilegios porque “se parece” al caso de uso, se declara exactamente qué operaciones son necesarias.
Definir la capacidad
Empieza por la operación que necesita la identidad, no por el nombre de un rol. Ejemplo: consultar datasets concretos, no “administrar BigQuery”.
Descubrir permisos
Determina qué permisos son realmente necesarios y elimina cualquier privilegio que no contribuya directamente al objetivo del workload.
Codificar el contrato
Versiona el Custom Role y sus bindings mediante Terraform para convertir IAM en una configuración reproducible y auditable.
Implementación práctica: Custom Role con Terraform
El siguiente patrón crea un rol personalizado a nivel de proyecto y separa la definición del rol de su asignación. Esta separación es importante: el contrato de permisos y el hecho de quién recibe ese contrato son dos decisiones de arquitectura distintas.
terraform {
required_version = ">= 1.5.0"
required_providers {
google = {
source = "hashicorp/google"
version = ">= 6.0"
}
}
}
variable "project_id" {
type = string
description = "Google Cloud project where the role is created."
}
variable "workload_member" {
type = string
description = "IAM member receiving the custom role."
}
resource "google_project_iam_custom_role" "data_reader" {
project = var.project_id
role_id = "controlledDataReader"
title = "Controlled Data Reader"
description = "Minimal read-only permissions for the approved data workflow."
stage = "GA"
permissions = [
"bigquery.datasets.get",
"bigquery.tables.get",
"bigquery.tables.getData",
"bigquery.jobs.create"
]
}
resource "google_project_iam_member" "data_reader_binding" {
project = var.project_id
role = google_project_iam_custom_role.data_reader.name
member = var.workload_member
}
El detalle importante no es únicamente la sintaxis Terraform. Es el hecho de que el conjunto de permisos se convierte en un contrato explícito. Un cambio de permisos deja de ser una modificación manual invisible y pasa a través del proceso habitual de revisión de código, aprobación y despliegue.
El conjunto de permisos anterior es ilustrativo de una capacidad de lectura y ejecución de jobs. En un entorno real debes validar las operaciones concretas que realiza el workload y comprobar dependencias indirectas antes de desplegar el rol.
La filosofía correcta es medir → reducir → probar → observar → revisar, no simplemente reemplazar Editor por un Custom Role que contiene casi los mismos privilegios.
Patrones de diseño para IAM empresarial
Separar Role Definition de Binding
Mantén la definición del conjunto de permisos separada de las identidades que reciben esos permisos. Esto permite reutilizar el contrato sin duplicar lógica.
- Custom Role = capacidad.
- IAM Binding = asignación.
- Service Account = identidad.
Aplicar mínimo alcance
La granularidad no termina en el rol. También importa dónde se concede. Siempre que sea posible, evita conceder acceso a nivel de organización o proyecto cuando el workload sólo necesita un recurso más específico.
- Preferir resource scope reducido.
- Evitar permisos administrativos.
- Separar workloads por identidad.
Tratar IAM como código
Terraform permite establecer un ciclo de vida controlado para IAM: revisión, aprobación, despliegue, rollback y auditoría.
- Pull Request obligatorio.
- Plan Terraform en CI.
- Revisión de seguridad.
FinOps y producción: el coste oculto de los permisos excesivos
IAM no suele aparecer como una línea directa en una factura de Cloud, pero una arquitectura de permisos deficiente puede amplificar el impacto financiero de errores humanos y automatizaciones.
Imagina un pipeline CI/CD con acceso de Editor a un proyecto de producción. Una modificación aparentemente inocente podría crear recursos costosos, modificar configuraciones de escalado, cambiar políticas o eliminar protecciones operativas.
El principio de menor privilegio funciona aquí como una medida de reducción de blast radius: si una identidad sólo puede ejecutar las acciones necesarias para su pipeline, una desviación accidental tiene un alcance mucho menor.
Un pipeline normalmente no necesita “acceso al proyecto”. Necesita un conjunto de capacidades: publicar un artefacto, desplegar un servicio, leer determinados secretos, consultar estado, modificar una configuración concreta, etc.
Modelar esas capacidades explícitamente permite que seguridad, plataforma y FinOps compartan una misma propiedad arquitectónica: limitar lo que una automatización puede hacer cuando algo sale mal.
Gobernanza: cómo evitar una jungla de Custom Roles
El argumento habitual contra los Custom Roles es correcto si se aplican sin disciplina: crear cientos de roles ligeramente diferentes puede ser peor que utilizar roles predefinidos. Por eso la solución no consiste en maximizar la personalización, sino en establecer un framework.
Convenciones de nombres
Utiliza nombres estables y orientados a capacidades. Evita nombres basados en individuos, tickets temporales o proyectos efímeros.
Ownership
Cada Custom Role debería tener un owner técnico y una justificación clara. Sin ownership, los permisos se vuelven deuda de seguridad.
Lifecycle
Define cómo se crean, modifican, deprecatean y eliminan los roles. Un rol sin consumidores debería entrar en revisión.
Framework de implementación paso a paso
- Identifica la identidad: determina qué usuario, grupo, workload o service account necesita acceso.
- Define el objetivo: escribe la operación que debe poder realizar la identidad en lenguaje funcional.
- Busca primero un rol predefinido: no crees un Custom Role si existe un rol suficientemente específico y mantenible.
- Enumera los permisos: determina las APIs y operaciones concretas requeridas por el flujo.
- Elimina privilegios innecesarios: cada permiso debe tener una justificación técnica.
- Define el scope: concede el acceso en el nivel mínimo razonable: recurso, proyecto, carpeta u organización según las necesidades reales.
- Implementa con Terraform: versiona roles y bindings junto con el resto de infraestructura.
- Valida en un entorno controlado: prueba operaciones permitidas y denegadas antes de producción.
- Automatiza CI/CD: ejecuta validaciones, Terraform plan y controles de seguridad antes de aplicar cambios.
- Observa y revisa: utiliza auditoría y feedback operacional para detectar permisos no utilizados o insuficientes.
- Gestiona el lifecycle: documenta owners, dependencias, consumidores y condiciones de retirada del rol.
Antipatrones que debes evitar
❌ “Funciona con Editor”
Es una prueba de autorización, no una solución arquitectónica. Sustituye el workaround por un rol predefinido adecuado o un Custom Role mínimo.
❌ Un rol por usuario
Genera una matriz IAM difícil de gobernar. Los roles deben representar capacidades reutilizables, mientras que las identidades se gestionan mediante grupos y service accounts.
❌ Terraform sin revisión
“IAM as Code” no significa automáticamente “IAM seguro”. Un PR que añade permisos administrativos sin revisión sólo automatiza el problema.
❌ No revisar roles antiguos
Los Custom Roles también generan deuda. Si desaparece el workload que los necesitaba, el rol debe entrar en un proceso de deprecación.
❌ Confundir rol con scope
Un rol granular concedido a nivel de organización puede seguir teniendo un blast radius innecesariamente grande. Rol y ámbito deben analizarse juntos.
❌ Dar permisos “por si acaso”
Cada permiso adicional aumenta la superficie de ataque. Si todavía no existe una necesidad, no debería formar parte del contrato de acceso.
Preguntas frecuentes sobre Custom Roles GCP + Terraform
¿Por qué evitar los roles primitivos Owner y Editor en Google Cloud?
Porque conceden capacidades muy amplias y pueden violar el principio de menor privilegio. Para entornos empresariales es preferible utilizar roles predefinidos suficientemente específicos o Custom Roles cuando los roles existentes no permiten representar correctamente la capacidad requerida.
¿Cómo se crea un Custom Role de Google Cloud con Terraform?
A nivel de proyecto puede utilizarse google_project_iam_custom_role, definiendo identificador, título, descripción, etapa y permisos. Después se asigna el rol mediante recursos IAM apropiados, manteniendo separadas la definición del rol y la asignación a identidades.
¿Qué estrategia de menor privilegio debería utilizar un equipo de plataforma?
Primero debe buscar roles predefinidos adecuados. Si ninguno ofrece la granularidad necesaria, se diseña un Custom Role basado en las operaciones reales del workload. El acceso debe concederse en el scope mínimo posible, gestionarse mediante Terraform, revisarse mediante Pull Requests y auditarse periódicamente.
Conclusión: IAM también es arquitectura
El principio de menor privilegio no consiste simplemente en sustituir Editor por otro nombre de rol. Es una disciplina de diseño que conecta identidad, permisos, scope, automatización, seguridad y operación.
Custom Roles en Google Cloud con Terraform proporcionan una forma potente de convertir esa disciplina en código. Pero el objetivo no es crear más roles: es crear contratos de acceso pequeños, comprensibles, reutilizables y gobernables.
La estrategia madura es sencilla de expresar, aunque exige disciplina para ejecutarla: rol predefinido específico primero; Custom Role cuando sea necesario; mínimo scope siempre; IAM como código y revisión continua.
