EnumDict: personaliza Enums con validación

Publicado el: 11/10/2026
Tempo de leitura: 4 minutos
Código Python en pantalla representando EnumDict y enumeraciones avanzadas

EnumDict es una clase especializada del módulo enum. Se utiliza como espacio de nombres controlado mientras se ejecuta el cuerpo de una enumeración. La mayoría de los proyectos no necesita crearla directamente, pero resulta útil al desarrollar metaclases basadas en EnumType, validar miembros o construir APIs declarativas.

Qué hace EnumDict

Cuando Python ejecuta el cuerpo de una clase, guarda las definiciones en un mapeo temporal. Las clases normales suelen usar un diccionario. Las enumeraciones necesitan reglas adicionales para el orden, los alias, los nombres reservados y el seguimiento interno. EnumDict aplica esas reglas antes de crear la clase final.

No es un reemplazo general para dict. Su objetivo está ligado al proceso de construcción de enumeraciones.

Por qué es importante

El caso de uso principal es una metaclase personalizada derivada de EnumType. Esa metaclase puede revisar declaraciones, rechazar nombres inválidos, generar metadatos o normalizar valores sin perder el comportamiento esperado por el módulo enum.

Para enumeraciones comunes, sigue usando Enum, IntEnum, StrEnum o Flag. Utiliza EnumDict solo cuando las funciones estándar no sean suficientes.

Ejemplo básico

from enum import Enum, EnumType, EnumDict

class MetaEnum(EnumType):
    @classmethod
    def __prepare__(metacls, cls, bases, **kwargs):
        return EnumDict(cls)

class Estado(Enum, metaclass=MetaEnum):
    ACTIVO = "activo"
    INACTIVO = "inactivo"

print(Estado.ACTIVO.value)

El método __prepare__ selecciona el mapeo usado durante la ejecución del cuerpo de la clase. Al devolver EnumDict, la metaclase conserva la validación y el seguimiento de miembros.

Por qué no usar un diccionario normal

Un diccionario simple puede funcionar en un ejemplo pequeño, pero puede omitir detalles relacionados con el orden, los alias, los nombres ignorados y los atributos especiales. El riesgo es crear una clase que parece correcta, pero falla en casos límite.

Validación de nombres

Una metaclase puede exigir convenciones, por ejemplo nombres en mayúsculas.

from enum import Enum, EnumType, EnumDict

class MetaMayusculas(EnumType):
    @classmethod
    def __prepare__(metacls, cls, bases, **kwargs):
        return EnumDict(cls)

    def __new__(metacls, cls, bases, namespace, **kwargs):
        for nombre in namespace.member_names:
            if nombre != nombre.upper():
                raise ValueError(f"Miembro inválido: {nombre}")
        return super().__new__(metacls, cls, bases, namespace, **kwargs)

class Color(Enum, metaclass=MetaMayusculas):
    ROJO = 1
    AZUL = 2

La validación ocurre antes de que exista la clase final, por lo que el error aparece al importar el módulo.

member_names

Las versiones recientes de Python exponen member_names en el espacio de nombres de la enumeración. La lista conserva el orden de declaración y puede usarse para validación, documentación o generación de esquemas.

No la modifiques sin comprender su papel. Cambios incorrectos pueden producir miembros inconsistentes.

Metadatos declarativos

Los miembros pueden incluir más información que un valor básico, como código, etiqueta o descripción.

from enum import Enum

class CodigoHTTP(Enum):
    OK = (200, "Éxito")
    NO_ENCONTRADO = (404, "Recurso ausente")

    def __init__(self, codigo, descripcion):
        self.codigo = codigo
        self.descripcion = descripcion

Este ejemplo no necesita EnumDict, pero muestra el tipo de diseño declarativo que una metaclase puede ampliar.

Alias y valores duplicados

Una enumeración puede crear alias cuando varios nombres comparten el mismo valor. Una metaclase puede prohibirlo, aunque primero conviene evaluar el decorador @unique, que resuelve el caso habitual con menos código.

Compatibilidad

EnumDict es un punto de extensión avanzado. Usa solo el comportamiento documentado para la versión de Python compatible con tu proyecto. Evita atributos privados y ejecuta pruebas en varias versiones.

import enum

EnumDict = getattr(enum, "EnumDict", None)
if EnumDict is None:
    raise RuntimeError("EnumDict no está disponible")

Pruebas recomendadas

Prueba el orden, los alias, la herencia, auto(), StrEnum, IntEnum, serialización, comparación y mensajes de error. Incluye nombres especiales como _ignore_, _missing_ y métodos declarados en el cuerpo.

Las pruebas de regresión son importantes porque el código de metaclase se ejecuta durante la importación y puede impedir que toda la aplicación arranque.

Errores frecuentes

Los errores más comunes son tratar EnumDict como un diccionario genérico, devolver un dict normal desde __prepare__, modificar estructuras internas, crear una metaclase sin pruebas y usar metaprogramación cuando bastaría con @unique, auto(), una propiedad o un decorador.

Cuándo evitarlo

Evita EnumDict si solo necesitas constantes, etiquetas o validación sencilla. Una enumeración normal con propiedades suele ser más clara. Las metaclases aumentan la complejidad y dificultan el mantenimiento.

Buenas prácticas

Mantén la metaclase pequeña, documenta cada regla, genera excepciones claras, evita detalles privados y prueba todas las versiones soportadas. Si la transformación es grande, considera una función fábrica o un decorador de clase.

Recursos relacionados

Consulta enums en Python, programación orientada a objetos, type hints y decoradores en Python.

Revisa también la documentación oficial de enum y el modelo de datos de Python.

Conclusión

EnumDict permite controlar la creación de enumeraciones sin descartar las reglas de la biblioteca estándar. Es útil para validaciones y extensiones declarativas, pero debe reservarse para necesidades reales y acompañarse de pruebas completas.

Compartilhe:

Facebook
WhatsApp
Twitter
LinkedIn

Contenido del artículo

    Artículos relacionados

    Rack de servidores que representa el balanceo de conexiones con SO_REUSEPORT_LB en Python
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    SO_REUSEPORT_LB: reparte conexiones entre workers

    Aprende SO_REUSEPORT_LB en Python para distribuir conexiones entre workers con pruebas, portabilidad y cierre ordenado.

    Ler mais

    Tempo de leitura: 5 minutos
    11/10/2026
    Código Python asíncrono en un portátil para inspect.markcoroutinefunction
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    markcoroutinefunction: detecta wrappers async

    Aprende inspect.markcoroutinefunction en Python para identificar wrappers asíncronos, integrar frameworks y evitar detecciones incorrectas.

    Ler mais

    Tempo de leitura: 5 minutos
    10/10/2026
    Código Python para recorrer carpetas y archivos con Path.walk
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    Path.walk: recorre directorios con seguridad

    Aprende Path.walk en Python para recorrer directorios, filtrar archivos, tratar errores y controlar la travesía con seguridad.

    Ler mais

    Tempo de leitura: 5 minutos
    10/10/2026
    Depuración de un proceso Python en terminal con código
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    pdb -p: depura procesos Python en ejecución

    Aprende a conectar pdb a un proceso Python en ejecución, inspeccionar la pila y diagnosticar bloqueos de forma segura.

    Ler mais

    Tempo de leitura: 6 minutos
    09/10/2026
    Código Python para representar fracciones exactas
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    fractions.from_number: convierte números en fracciones

    Aprende fractions.from_number en Python para convertir números en fracciones exactas, controlar precisión, validar entradas y evitar redondeos inesperados.

    Ler mais

    Tempo de leitura: 4 minutos
    09/10/2026
    Desarrollador configurando un servidor HTTPS y certificado TLS con Python
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    HTTPSServer: crea un servidor HTTPS local en Python

    Aprende HTTPSServer en Python para crear servicios HTTPS locales, configurar certificados, usar hilos y comprender sus límites.

    Ler mais

    Tempo de leitura: 4 minutos
    08/10/2026