grp en Python: consulta grupos Unix

Publicado el: 26/08/2026
Tempo de leitura: 5 minutos
Creative concept with coffee cup and paper question marks on a table.

El módulo grp consulta la base de grupos en sistemas Unix. Permite encontrar un grupo por GID numérico o nombre, listar miembros registrados explícitamente y convertir ownership de archivos en nombres legibles.

Los grupos Unix participan en el control de acceso a archivos, dispositivos, servicios y recursos. Sin embargo, la base de grupos no representa toda la autorización: también intervienen el grupo primario, los grupos suplementarios, mode bits, ACLs, capabilities, namespaces, SELinux, AppArmor y opciones de montaje.

Disponibilidad

grp está disponible en Unix, pero no en WASI, Android ni iOS. Windows usa otro modelo.

try:
    import grp
except ImportError:
    grp = None

En software multiplataforma, aísla este código y conserva el GID numérico cuando el nombre no sea esencial.

Campos de una entrada

Las funciones devuelven un objeto similar a una tupla:

gr_name, gr_passwd, gr_gid, gr_mem

gr_name es el nombre, gr_gid el ID numérico y gr_mem una lista de logins registrados explícitamente. gr_passwd es histórico y normalmente está vacío o no es útil.

Consultar por GID

import grp

try:
    grupo = grp.getgrgid(1000)
except KeyError:
    print("GID sin entrada")
else:
    print(grupo.gr_name, grupo.gr_mem)

Desde Python 3.10, un argumento no entero, como string o float, genera TypeError. Valida entradas de CLI y API.

Consultar por nombre

import grp

try:
    grupo = grp.getgrnam("developers")
except KeyError:
    print("Grupo inexistente")
else:
    print(grupo.gr_gid)

No utilices directamente un nombre no confiable para decisiones privilegiadas sin resolverlo y comprobar las credenciales efectivas del proceso.

Grupo primario y suplementarios

El grupo primario de una cuenta está en pw_gid del módulo pwd en Python. gr_mem contiene usuarios listados explícitamente en la entrada del grupo.

La documentación advierte que muchos usuarios no aparecen en gr_mem de su grupo primario. Por eso esa lista sola es incompleta.

Encontrar todos los grupos de un usuario

import grp
import pwd


def grupos_del_usuario(nombre):
    cuenta = pwd.getpwnam(nombre)
    gids = {cuenta.pw_gid}

    for grupo in grp.getgrall():
        if nombre in grupo.gr_mem:
            gids.add(grupo.gr_gid)

    return [grp.getgrgid(gid) for gid in sorted(gids)]

En sistemas con LDAP o muchos grupos, getgrall() puede ser costoso. Cuando exista, prefiere os.getgrouplist(nombre, gid_primario).

Grupos del proceso actual

os.getgid() devuelve el GID real, os.getegid() el efectivo y os.getgroups() los grupos suplementarios.

import os

print("Real:", os.getgid())
print("Efectivo:", os.getegid())
print("Suplementarios:", os.getgroups())

El kernel normalmente usa el GID efectivo y los grupos suplementarios para decidir permisos.

Convertir ownership de archivos

import grp
import os

info = os.stat("archivo.txt")
try:
    nombre_grupo = grp.getgrgid(info.st_gid).gr_name
except KeyError:
    nombre_grupo = str(info.st_gid)

print(nombre_grupo)

Mantén el GID numérico como fallback. Los archivos pueden sobrevivir a un grupo eliminado o venir de otro namespace.

gr_passwd no autentica

Las contraseñas de grupo son una característica histórica. gr_passwd suele estar vacío o contener un marcador.

No lo uses para validar credenciales. La autenticación y autorización deben depender de PAM, ACLs o políticas soportadas.

Listar todos los grupos

import grp

for grupo in grp.getgrall():
    print(grupo.gr_gid, grupo.gr_name, grupo.gr_mem)

El orden es arbitrario. NSS puede consultar LDAP, SSSD, NIS u otra fuente remota, haciendo la operación lenta.

NSS y proveedores remotos

Al igual que pwd, grp sigue Name Service Switch. Los datos pueden venir de /etc/group, LDAP, SSSD, NIS, containers o plugins.

Una llamada aparentemente local puede bloquear por red. No ejecutes getgrall() en cada request web.

Referencias NIS

Nombres que comienzan con + o - pueden ser referencias YP/NIS y no siempre están disponibles mediante getgrnam() o getgrgid().

Cache con expiración

Consultas frecuentes pueden utilizar cache de corta duración.

import time

_cache = {}

def grupo_por_gid(gid, ttl=60):
    ahora = time.monotonic()
    item = _cache.get(gid)
    if item and ahora - item[0] < ttl:
        return item[1]

    valor = grp.getgrgid(gid)
    _cache[gid] = (ahora, valor)
    return valor

Usa reloj monotónico y no caches errores para siempre.

Containers y namespaces

En un container, un GID puede no tener entrada en /etc/group. Kubernetes también puede añadir grupos suplementarios sin nombres.

No falles al mostrar ownership: conserva el número. Para autorización, utiliza las credenciales efectivas del kernel.

Volúmenes compartidos

El mismo GID puede tener nombres distintos en hosts diferentes. En NFS o volúmenes compartidos, la consistencia numérica es más importante que el nombre.

Comprobar membresía del proceso

import os


def proceso_en_grupo(gid):
    return gid == os.getegid() or gid in os.getgroups()

Esta comprobación responde sobre el proceso actual y suele ser más útil que reconstruir membresía desde archivos.

Deja que el kernel decida

Aunque el proceso pertenezca al grupo, el acceso puede fallar por ACL, mode bits, SELinux, AppArmor, filesystem read-only o mount options.

Intenta la operación y maneja PermissionError. La consulta sirve para diagnóstico, no sustituye la syscall.

Cambiar el grupo de un archivo

import grp
import os

objetivo = grp.getgrnam("developers")
os.chown("archivo.txt", -1, objetivo.gr_gid)

La operación necesita permisos. Valida rutas y evita seguir symlinks no confiables.

Cambiar el grupo efectivo

Procesos privilegiados pueden usar os.setgid() u os.setegid(). Son operaciones sensibles y pueden ser irreversibles.

Es preferible que el supervisor inicie el servicio con el usuario y grupo correctos.

initgroups()

os.initgroups(usuario, gid_primario) inicializa grupos suplementarios según la configuración del sistema.

import os
import pwd

cuenta = pwd.getpwnam("appuser")
os.initgroups(cuenta.pw_name, cuenta.pw_gid)
os.setgid(cuenta.pw_gid)
os.setuid(cuenta.pw_uid)

Llama initgroups() antes de perder privilegios. Un orden incorrecto puede conservar grupos privilegiados o impedir la configuración.

Limpiar grupos heredados

Cambiar solo UID y GID primario puede dejar grupos suplementarios heredados. Usa initgroups() o os.setgroups([]) según la política.

Race conditions

La membresía puede cambiar entre consulta y uso. Para seguridad, confía en el resultado de la operación real y maneja el fallo.

Privacidad

Las listas de miembros revelan nombres y estructura organizacional. No expongas getgrall() en APIs o logs sin necesidad.

Logs

Al registrar errores con syslog en Python, usa GID numérico y nombre sanitizado. No incluyas todos los miembros.

Aislamiento

Usuarios y grupos sin privilegios complementan los límites de resource en Python, pero no forman una sandbox completa.

Pruebas

Prueba grupo existente y ausente, argumentos no enteros, usuario cuyo grupo primario no lo lista en gr_mem, grupos suplementarios, container sin nombres, LDAP lento, NIS, volumen compartido, permisos reales y reducción de privilegios.

Los tests unitarios no deben depender de la base real del host. Usa wrappers y registros fake.

Errores comunes

Los fallos frecuentes son tratar gr_mem como lista completa, usar gr_passwd para autenticar, asumir nombre para todo GID, llamar getgrall() en hot path, olvidar grupos suplementarios y creer que la membresía garantiza acceso.

Conclusión

grp resuelve grupos Unix por nombre o GID y ayuda a interpretar ownership y membresía. Combínalo con pwd y los grupos efectivos del proceso.

Conserva IDs numéricos, considera NSS y containers, no uses la base para autenticar y deja que el kernel decida el acceso final. Consulta la documentación oficial de grp y group(5).

Compartilhe:

Facebook
WhatsApp
Twitter
LinkedIn

Contenido del artículo

    Artículos relacionados

    A developer typing code on a laptop with a Python book beside in an office.
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    pwd en Python: consulta usuarios Unix

    Aprende pwd en Python para consultar usuarios Unix por UID o login, obtener home, shell y ownership sin usar la

    Ler mais

    Tempo de leitura: 6 minutos
    26/08/2026
    Close-up of stacked logs showing natural textures and patterns, suitable for firewood or decor.
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    syslog en Python: envía logs a Unix

    Aprende syslog en Python para enviar logs Unix con prioridades, facilities, máscaras, contenido estructurado y protección contra log injection.

    Ler mais

    Tempo de leitura: 4 minutos
    26/08/2026
    A CPU and RAM sticks displayed on a white surface, showcasing computer hardware components.
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    resource en Python: límites de CPU y memoria

    Aprende resource en Python para medir CPU, pico de memoria y page faults, y limitar archivos, procesos, descriptors y address

    Ler mais

    Tempo de leitura: 5 minutos
    26/08/2026
    Close-up of a person using a metro card machine for public transport payment indoors.
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    pty en Python: automatiza terminales Unix

    Aprende pty en Python para ejecutar y probar programas interactivos, controlar pseudo-terminales, EOF, resize, señales y timeouts.

    Ler mais

    Tempo de leitura: 5 minutos
    25/08/2026
    Detailed view of programming code in a dark theme on a computer screen.
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    tty en Python: modos raw y cbreak

    Aprende tty en Python para modos raw y cbreak, lectura de teclas, secuencias, Unicode y restauración segura del terminal Unix.

    Ler mais

    Tempo de leitura: 5 minutos
    25/08/2026
    Laptop displaying code with reflection, perfect for tech and programming themes.
    Python Avanzado
    Foto de perfil de Leandro Hirt da Academify

    termios en Python: control seguro del terminal

    Aprende termios en Python para modo canónico, echo, lectura de teclas, baud rate, colas, ventana y restauración segura del TTY.

    Ler mais

    Tempo de leitura: 5 minutos
    25/08/2026