Volver al inicio

10 errores de gestión de config en producción

El artículo desglosa 10 errores de gestión de configuración de aplicaciones basados en proyectos reales. Desde hardcoding de parámetros hasta falta de documentación — cómo evitar fallos en prod. Ejemplos de código y recomendaciones para desarrolladores seniors.

Top-10 errores de configuración de app en prod
Advertisement 728x90

Gestión de la configuración de aplicaciones: 10 errores sutiles que causan fallos en producción

Configuraciones incorrectas de tiempos de espera, credenciales o límites de recursos provocan caídas más rápido que los errores lógicos. A diferencia del código, la configuración suele saltarse las revisiones por pares, las pruebas automatizadas y las tuberías de CI, generando riesgos silenciosos: servicios que escriben en la base de datos equivocada, agotamiento de grupos de conexiones o filtración de credenciales. El análisis de incidentes reales reveló 10 malas prácticas de configuración que permanecen ocultas hasta que ocurre el fallo.

Tiempos de espera codificados de forma fija: más de 30 instancias en el código

Codificar tiempos de espera directamente en el código exige reconstruir toda la aplicación para ajustarlos. Una búsqueda con grep de Duration.ofSeconds encontró más de 30 instancias dispersas con valores inconsistentes: 10 s en NotificationService, 30 s en SearchService, 15 s en ApiRoutes.

private static final Duration TIMEOUT = Duration.ofSeconds(10);  // NotificationService
private static final Duration TIMEOUT = Duration.ofSeconds(30);  // SearchService
private static final Duration TIMEOUT = Duration.ofSeconds(10);  // AuthFilter
private static final Duration TIMEOUT = Duration.ofSeconds(15);  // ApiRoutes

Bajo carga, ajustar los tiempos de espera es crítico, pero su codificación fija anula la agilidad. Solución: Externalizarlos en archivos de configuración con sobrescritura mediante variables de entorno.

Google AdInline article slot

Falta de validación: borrado accidental de bases de datos de producción

Una clase de configuración de 695 líneas valida solo un parámetro. Todos los demás se aceptan sin comprobación: grupo de conexiones = 0, tiempo de espera = -1, URL de base de datos vacía.

String authType = config.getString("authType");
if (!Set.of("kerberos", "jwt").contains(authType)) {
    throw new IllegalArgumentException("Tipo de autenticación inválido. Valores posibles: kerberos, jwt");
}

Ejemplos peligrosos incluyen http.server.parsing.max-content-length = 10g: una sola petición consume 10 GB de RAM. O dropAll = ${?DROP_ALL} de Liquibase, que elimina todo el esquema sin confirmación. Detenerse al inicio ante cualquier error evita incidentes graves.

Valores predeterminados que enmascaran fallos

Los valores por defecto ocultan claves ausentes hasta el momento de ejecución. Al habilitar SSO:

Google AdInline article slot
Duration maxResponseDelay = ssoEnabled
    ? config.getDuration("sso.maxResponseDelay")
    : Duration.ofMinutes(10);
long responseCacheSize = ssoEnabled
    ? config.getLong("sso.responseCacheSize")
    : 10_000;

Claves faltantes provocan fallos en producción. Asimismo, tokenTtl pasa de forma silenciosa de 1 min (configuración) a 3 min (código), violando políticas de seguridad.

  • La trampa del valor por defecto: Las malas configuraciones permanecen invisibles hasta que se activa la funcionalidad.
  • Solución: Validar todas las claves obligatorias al arrancar; registrar advertencias cuando se use un valor alternativo.

Deriva de configuración entre entornos de prueba y producción

Las configuraciones de prueba difieren drásticamente de las de producción:

| Parámetro | Producción | Prueba |

Google AdInline article slot

|-----------|------------|--------|

| api.responseLimit | 10 MB | 1 GB |

| api.contextLimit | 10 MB | 1 MB |

Una respuesta de 50 MB pasa las pruebas, pero falla en producción. Por otro lado, configuraciones más restrictivas en pruebas generan falsos negativos.

Nomenclatura inconsistente de parámetros

Un único archivo application.conf mezcla estilos de nomenclatura:

fileStoragePath = "/opt/storage"          # camelCase
retention-days = 7                        # kebab-case
createdump-interval-seconds = 240         # híbrido
usage-threshold = 80                      # kebab-case
compressHeapDump = true                   # camelCase

Los booleanos varían enormemente: sslValidationEnabled, smtpSslEnable, saml.enabled, isUseSecureCookieJWT. Las sobrescrituras por entorno fallan en silencio: smtpSslEnableSMTP_SSL_ENABLED (pero EnableEnabled).

  • Mezclar camelCase y kebab-case en un mismo archivo.
  • Desajustes entre claves HOCON y variables de entorno.
  • Cuatro convenciones distintas para banderas booleanas.

Banderas de funciones zombis sin gestión de ciclo de vida

16 banderas en la clase Config: ws-cache-enabled=false en todas partes, history-import-enabled=true siempre activa. Sin fechas de creación, responsables ni justificación de obsolescencia: la carga cognitiva aumenta.

  • Añadir: Fecha de creación, responsable, propósito y fecha límite de retirada.
  • Eliminar: Banderas inmortales —siempre true/false y nunca usadas.

Orden incorrecto de sobrescritura en HOCON

En HOCON, el último valor prevalece. Correcto:

key = "default-value"
key = ${?ENV_OVERRIDE}

Incorrecto:

dump {
  enabled = ${?DUMP_ENABLED}
  enabled = false
  directory = ${?DUMP_DIR}
  directory = "opt/myapp/dumps/auto"
}

La sobrescritura desde entorno se anula con false: los volcados permanecen deshabilitados.

Configuración sin documentar: más de 100 parámetros, cero claridad

docker.md enumera variables de entorno como EMAIL_ENABLED=false/true, sin descripciones. AppConfig.java tiene 695 líneas y cero Javadoc. ¿Qué controla sync-request-timeout-seconds=600? ¿Qué ocurre si workflowStepLimit=200 alcanza 0 o 100000?

URLs externas y niveles de registro codificados de forma fija

Puntos finales de API integrados directamente en el código exigen reconstrucciones completas para cambiarlos. Los niveles de registro empaquetados en imágenes Docker obligan a montajes de volúmenes o nuevas construcciones solo para activar DEBUG.

Conclusiones clave:

  • Externalizar todos los parámetros —y validarlos rigurosamente al arrancar.
  • Imponer una única convención de nomenclatura coherente entre HOCON y variables de entorno.
  • Documentar cada parámetro: tipo, rango válido, valor por defecto e impacto empresarial.
  • Priorizar el fallo inmediato frente a alternativas silenciosas.
  • Gestionar banderas de funciones con disciplina de ciclo de vida: responsable, propósito y fecha de retirada.

— Editorial Team

Advertisement 728x90

Leer después