从新手到老手的差距
刚学 Linux 时,我只会用 adduser 创建用户,因为它是交互式的、简单。但换了台 CentOS 服务器,adduser 不见了。查了才知道,Debian 系的 adduser 是 shell 脚本封装,Red Hat 系默认没有。
后来我发现,真正的高手都用 useradd。它参数灵活、可脚本化、一台服务器上创建几百个用户都不是问题。
useradd:创建用户的核心参数
基础用法:创建普通用户
# 创建一个标准用户(最简单形式)
sudo useradd zhangsan
这条命令做了几件事:
- ·在 /etc/passwd 添加一条记录
- ·在 /etc/shadow 添加密码记录(没有密码,登录不了)
- ·创建同名的用户组添加到 /etc/group
- ·在 /home 下创建家目录 /home/zhangsan
- ·复制 /etc/skel 下的文件到新家目录
但有个坑:useradd 默认不设置密码。你得再执行 passwd zhangsan 设置密码。
指定家目录
# 指定自定义家目录位置
sudo useradd -d /data/users/lisi lisi
-d(home directory,家目录路径)指定家目录路径。如果路径不存在,可以配合 -m 自动创建。
# 指定家目录并自动创建
sudo useradd -m -d /data/users/wangwu wangwu
指定登录Shell
# 创建用户并指定 bash 作为登录shell
sudo useradd -s /bin/bash zhaoliu
# 创建不能登录的系统用户(shell设为 nologin 或 /sbin/nologin)
sudo useradd -s /sbin/nologin mysql
-s(shell,登录shell路径)是安全运维的重要参数。比如你创建 MySQL 的运行用户,它不需要登录系统,用 nologin 更安全。防止有人通过 su 切换到这个用户来登录。
指定UID
# 手动指定UID为1500
sudo useradd -u 1500 sunqi
# 创建系统用户(UID在系统范围内,通常是1-999)
sudo useradd -r sysuser
# 检查UID
id sunqi
# 输出类似 uid=1500(sunqi) gid=1500(sunqi) groups=1500(sunqi)
UID(User ID,用户标识号)在迁移用户时会用到。比如你从旧服务器迁移用户,要保持 UID 一致,否则文件权限会因为 UID 不匹配而错乱。
指定用户组
# 指定主要组(primary group,用户所属的主组)
sudo useradd -g devteam lichao
# 附加组(supplementary groups,额外的附加组)
sudo useradd -G docker,www-data liuyi
# 不创建同名组(用默认组代替)
sudo useradd -N chenqi
-g 是主组,-G 是附加组。这点容易被搞混。附加组是 "这个人还是哪些组的成员"。比如把开发者加进 docker 组,他就能免 sudo 执行 docker 命令。
不创建家目录(适合系统用户)
# 创建系统服务用户,不生成家目录
sudo useradd -M -s /sbin/nologin nginx
# 加上 -r 创建系统用户
sudo useradd -r -M -s /sbin/nologin postgres
-M(no create home,不创建家目录)适合运行服务的系统用户。它们不需要家目录,有反而浪费磁盘。
设置账户过期
# 创建临时账户,2026年12月31日自动过期
sudo useradd -e 2026-12-31 tempuser
-e(expire date,过期日期)适合实习生账号、临时工账号。到期后账户自动锁定,不用手动去管理。
usermod:修改用户属性
usermod(user modify,修改用户)和 useradd 的参数几乎一样,只是功能从"创建"变成"修改"。
修改登录Shell
# 把用户的shell从bash改成zsh
sudo usermod -s /usr/bin/zsh zhangsan
变更立即生效,用户下次登录就用新 shell。
锁定和解锁账户
# 锁定用户(在密码前加!)
sudo usermod -L zhangsan
# 解锁用户
sudo usermod -U zhangsan
-L(lock,锁定)实际上是在 /etc/shadow 的密码字段前加了一个感叹号,让密码验证失效。和 passwd -l 效果相同。
修改用户组
# 修改主要组
sudo usermod -g admins zhangsan
# 追加附加组(注意-a要和-G一起用,否则会替换已有的附加组)
sudo usermod -aG docker zhangsan
# 清空附加组
sudo usermod -G "" zhangsan
这里有个经典错误:用 -G 不加 -a。我第一次用 usermod 改组时,直接 usermod -G docker zhangsan,结果 zhangsan 原先所在的所有组都被替换了,导致他进不了自己的项目目录。-a(append,追加)是保命选项,一定要记住。
修改UID和家目录
# 修改UID为2000
sudo usermod -u 2000 zhangsan
# 修改家目录并移动文件
sudo usermod -d /newhome/zhangsan -m zhangsan
-m(move contents of home directory,移动家目录内容)配合 -d 使用,会把原家目录的文件搬过去。
修改账户过期
# 账户永不过期
sudo usermod -e "" zhangsan
# 设置30天后过期
sudo usermod -e $(date -d "+30 days" +%Y-%m-%d) tempuser
userdel:删除用户
# 删除用户但保留家目录和邮件池
sudo userdel zhangsan
# 连家目录和邮件池一起删除
sudo userdel -r zhangsan
# 强制删除(即使用户还在登录)
sudo userdel -f zhangsan
-r(remove home,移除家目录)要慎用。有一次手快用了 -r,结果用户的家目录下有没备份的重要代码。后来养成了习惯:删除前先 tar 打包家目录。
查看用户信息
# 查看用户ID信息
id zhangsan
# 输出:uid=1001(zhangsan) gid=1001(zhangsan) groups=1001(zhangsan),999(docker)
# 查看用户详细信息
finger zhangsan
# 如果 finger 未安装: sudo apt install finger 或 sudo yum install finger
# 查看登录相关
who
last
id 命令我每天至少用十次。调试权限问题第一步就是 id 用户名,看用户到底在哪些组里。
安全提醒
useradd 和 adduser 不是同一个命令。 在 Debian/Ubuntu 上 adduser 是一个 Perl 脚本,会交互式引导。而 useradd 是原生二进制工具。CentOS/RHEL 上 adduser 只是 useradd 的符号链接。跨平台脚本文档要写 useradd。
批量创建用户时要小心 UID 冲突。 如果用脚本批量 useradd,UID 耗尽的情况虽然少见,但一旦发生,新创建的用户可能和已有用户共用 UID,导致权限错乱。
# 检查当前最大UID
awk -F: '{if($3>max) max=$3} END{print max}' /etc/passwd
删除用户前先检查进程。 确保用户没有正在运行的进程:
# 查看用户是否还有进程在跑
pgrep -u zhangsan
# 或者
ps -u zhangsan
家目录权限继承。 /etc/skel(skeleton,骨架目录)下的文件会被复制到新用户的家目录。如果你希望新用户有特定的配置(如 .bashrc 别名、环境变量),可以修改 /etc/skel/ 下的模板文件。
用户管理是 Linux 运维的基础能力。掌握了这些命令,在日常运维和自动化部署脚本中会顺手很多。