How to Manage Groups on Linux With groupadd and usermod
Create groups with groupadd, add users with usermod -aG and gpasswd, list memberships with id, and learn why a new group needs a fresh login to take effect.

Groups are the usual way to share files and permissions without making everything world-readable. The commands are short, and one flag, -a, decides whether a command adds a group or wipes the list. The examples use shadow-utils 4.14 on Linux, and run as root or with sudo. The permission side is in Linux file permissions.
Create a group and add members
sudo groupadd dev
sudo usermod -aG dev alice
sudo usermod -aG dev,docker bob
getent group devdev:x:1002:alice,bob
-G sets the supplementary groups and -a keeps the existing ones. Running usermod -G dev alice without -a removes Alice from every other supplementary group, including sudo, which has locked administrators out of their own machines. Always write -aG as one unit.
Check a user's groups
id alice
groups aliceuid=1001(alice) gid=1001(alice) groups=1001(alice),1002(dev)
id shows numeric IDs and the primary group. The primary group is set at account creation, described in adding users on Linux, and changed with usermod -g.
Why the change does not work yet
A process receives its group list at login. After usermod, an existing terminal or SSH session still has the old groups, so ls /srv/project still says "Permission denied". Log out and back in, or start a subshell with the new group:
newgrp dev
id -nGLong-running services need a restart, and a desktop session needs a full logout. Verify with id in the shell that is failing, not in another terminal.
Remove a member and delete a group
sudo gpasswd -d alice dev
sudo groupdel devgpasswd -d removes one user from one group. groupdel refuses to delete a group that is some user's primary group. Files owned by the deleted group keep the numeric ID, so reassign them with chgrp first; the chown guide shows the commands.
A shared directory that works
sudo mkdir /srv/project
sudo chgrp dev /srv/project
sudo chmod 2775 /srv/projectThe setgid bit in 2775 makes new files inherit the dev group, so teammates do not fight over ownership. See setuid, setgid and the sticky bit. Pair it with umask 002 so group members can write new files, as explained in the umask guide.
What a group is, in files
Group membership lives in two plain files. /etc/group lists each group with its numeric id and its members, and /etc/gshadow holds the optional group password and the list of administrators. A user's primary group comes from the fourth field of /etc/passwd, and it is not necessarily listed in /etc/group as a member at all. When someone says a user "is in" a group, that can mean primary or supplementary membership, and the kernel treats them the same when checking file access. The commands groupadd, usermod and gpasswd are front ends that edit those files with locking, which is safer than editing by hand. If you must edit them directly, use vigr, which takes the lock and checks the syntax.
Numeric ids matter more than names. The kernel compares the number stored on a file with the numbers in the process's credentials, so two machines with different names for id 1002 give different people access to the same files on a shared disk. On NFS and on removable media, keep ids consistent across hosts, or map them with a directory service.
System groups and range conventions
Distributions reserve low numbers for system groups. Ids below 1000 on most Linux systems, defined by SYS_GID_MIN and SYS_GID_MAX in /etc/login.defs, belong to services and built-in roles, and ordinary groups start at 1000. A service that needs its own identity uses groupadd --system to get a number from the lower range. Mixing the ranges leads to collisions when a package later claims the same id, so create team groups with the ordinary command and leave the low range alone.
Sudo and special groups
Several groups carry privilege beyond file sharing. On Debian and Ubuntu, sudo grants the right to run commands as root, and on Red Hat family systems the equivalent is wheel. The adm group can read most logs, systemd-journal can read the journal, docker can start containers as root in effect, and disk can read raw devices. Adding someone to one of these is a deliberate grant, so record it somewhere the team can see, such as a configuration management repository, and review it when roles change. Listing who holds a sensitive group is a one-line check: getent group sudo docker.
Changing a user's primary group
The primary group decides the group of files the user creates, unless a directory has the setgid bit. usermod -g changes it, and the user's existing files keep their old group, so a team that moves to a shared primary group often follows with a find /home/alice -group alice -exec chgrp devs {} +. Think before doing that: for personal home directories, the private group per user is the default for a reason, because it lets a umask of 002 stay safe. With a shared primary group and that umask, files in the home directory become writable by everyone in the group.
Auditing and automation
For a fleet, do not run usermod by hand. A configuration management tool such as Ansible has a user and group module that expresses the desired membership and is idempotent, so running it twice changes nothing the second time. Combined with a code review, membership changes get a history. For a one-off check on a single machine, lid -g dev or getent group dev | cut -d: -f4 | tr ',' '\n' lists members one per line, ready for a diff against the expected list. Compare it to the people who should have access and remove anyone who left the project, because old group memberships are among the most common findings in access reviews.
Checking effective access before blaming groups
When access still fails after the group change and a fresh login, test the path rather than guessing. namei -l /srv/project/file shows the owner, group and mode of every directory along the way, and a single directory without the execute bit for the group blocks everything below it. sudo -u alice test -r /srv/project/file && echo ok checks readability as that user. If the file lives on a network mount, a restrictive export option or a root-squash rule can override local group membership, and the fix belongs on the server. Access control lists, shown by getfacl, may also grant or deny access beyond the plain mode bits.
Where this does not apply
With central directories such as LDAP or Active Directory, group membership is managed there and local usermod will not change it. Granting a group such as docker or disk is a privilege decision, since membership in either is effectively root access. The limit on supplementary groups is 65536 on modern kernels, which is rarely reached, but NFS with AUTH_SYS historically honoured only 16. The commands are documented in usermod(8) and gpasswd(1).


