很多个人站长在服务器上吃过权限的亏:网站被挂马,一查发现是上传目录给了 777 权限;程序报「Permission denied」,折腾半天不知道问题出在哪;多个用户一起维护一台服务器,文件互相覆盖、权限混乱。这些问题的根源,都是对 Linux 文件权限和用户管理理解不透彻。这篇文章从最基础的概念讲起,把 chmod、chown、ACL 这些工具彻底讲明白,并给出个人站长在实际运维中的安全用法。
一、先看懂文件权限的三组九位
在终端执行 ls -l,每一行的最前面就是权限位,例如 -rw-r--r--。这一串字符可以拆成四部分:第一个字符表示文件类型(- 普通文件、d 目录、l 软链接),后面九个字符分成三组,分别代表属主(user)、属组(group)、其他用户(other)的权限。每组三个字符依次是 r(读,4)、w(写,2)、x(执行,1)。
所以 -rw-r--r-- 的含义是:属主可读写,属组和其他用户只能读。而 -rwxr-xr-x 表示属主可读写执行,其他人可读可执行但不可写。理解了这一点,就能看懂任何文件的权限状态。
二、目录权限和文件权限完全不同
新手最容易忽略的是目录权限的特殊性。对目录来说:r 表示可以列出目录内容(ls),w 表示可以在目录里创建和删除文件,x 表示可以进入目录(cd)。注意,只有 r 没有 x 的目录,你虽然能 ls 看到文件名,但无法进入,也无法访问里面的文件,实际使用中非常别扭。所以常见目录权限是 755 或 750,而不是 644。
这里有个安全知识点:目录的 w 权限允许删除目录下的任何文件,哪怕这个文件本身是只读的。因为删除操作看的是目录权限,不是文件权限。这也是为什么共享目录要慎用 777。
三、chmod:修改权限的两种写法
chmod 有两种常用写法。数字法:rwx 分别对应 4、2、1,把三组权限的数字加起来,就得到 755、644 这样的三位数。例如 chmod 644 文件,等价于把文件设为 -rw-r--r--。符号法:用 u(属主)、g(属组)、o(其他)、a(全部)配合 +、-、= 来增减权限,例如 chmod u+x 脚本.sh、chmod o-w 配置文件。
实战中我推荐优先用数字法,直观且不容易写错。几个最常用的组合:644 是普通文件的标准权限,755 是脚本和目录的标准权限,600 是私钥、密码等敏感文件的权限,700 是私有目录权限。
chmod 644 index.php
chmod 755 /var/www/blog
chmod 600 ~/.ssh/id_rsa
chmod -R 755 /var/www/blog/usr/uploads注意 -R 参数会递归修改目录下所有文件,批量操作时要谨慎,最好先想清楚目录和文件的权限是否需要不同。
四、chown:修改属主和属组
权限的判定基于「我是谁、我在哪个组」。如果文件的属主和你登录的用户不一致,就会遇到明明有权限却打不开的怪问题。chown 用来修改属主和属组:
chown www:www /var/www/blog -R
chown root:root /etc/nginx/nginx.conf
chgrp developers /srv/project第一个命令把 /var/www/blog 整个目录的属主和属组都改成 www(Nginx 和 PHP-FPM 的运行用户),这是部署网站时最常用的一步。注意顺序是「属主:属组」,别写反了。chgrp 只改属组,用得少一些。
五、网站目录的权限标准姿势
个人网站最常见的权限问题,就是图省事把整个网站目录 chmod -R 777。777 意味着任何人(包括被入侵后获得低权限的攻击者)都能读写你的文件,这是挂马和篡改的温床。正确的做法是遵循最小权限原则:
- 所有程序文件(PHP、HTML、JS):644,属主为运行用户
- 所有目录:755,属主为运行用户
- 需要程序写入的目录(上传目录、缓存目录):属主改为 www 且给 755 或 750,不要用 777
- 配置文件、数据库密码文件:640 甚至 600
以 Typecho 博客为例,usr/uploads 目录需要 PHP 写入,把它的属主设为 www 即可:chown www:www usr/uploads,权限保持 755 就够了,没必要 777。如果程序报写入失败,优先检查属主对不对,而不是无脑加权限。
六、特殊权限:SUID、SGID 与粘滞位
除了 rwx,还有三个特殊权限位。SUID(4)让程序运行时以属主身份执行,典型例子是 /usr/bin/passwd,普通用户执行它时临时获得 root 权限来修改密码。SGID(2)让目录下新建的文件自动继承目录的属组,适合团队共享目录。粘滞位 Sticky Bit(1)只对目录有意义,设置后目录里的文件只能被属主或 root 删除,最典型的就是 /tmp,权限显示为 drwxrwxrwt。
chmod 4755 程序文件
chmod 2770 /srv/team
chmod 1777 /tmp
find / -perm -4000 -type f 2>/dev/null最后一条命令用于审计:找出系统里所有带 SUID 的文件。正常系统只有 passwd、sudo 等少数程序带 SUID,如果发现可疑的 SUID 文件,很可能是入侵者留下的后门。建议定期执行这条命令并把结果保存下来作为基线,改动系统配置前先比对一次,排查入侵时就有据可查。
七、用户与用户组管理
服务器上每个运行中的服务都应该有自己的用户,而不是全都用 root。创建用户的常用命令:
useradd -m -s /bin/bash blog
useradd -r -s /usr/sbin/nologin www
usermod -aG developers blog
passwd blog
userdel -r blog第一个命令创建带家目录的普通用户 blog;第二个创建系统用户 www,并禁止登录(-s /usr/sbin/nologin),这是服务账号的标准做法,即使被拿下也无法直接登录 shell。管理用户组用 groupadd、groupdel,把用户加入附加组用 usermod -aG。注意 -a 千万别漏,漏掉会把用户从原有附加组里踢出去。
部署网站时,让 Nginx、PHP-FPM 都使用 www 用户运行,网站文件属主也是 www,整个链路权限就统一了,既安全又好排查。
八、umask:控制新文件的默认权限
为什么新建的文件默认是 644、目录默认是 755?因为 umask 默认值是 022,它从完整权限里「扣掉」对应位。umask 022 表示新文件去掉组写和其他写权限。如果服务器上创建的文件默认带 777,检查一下 /etc/profile 或 ~/.bashrc 里的 umask 是不是被改成了 000。安全起见,保持 022 即可,特殊场景(如共享目录)才需要 002。
九、ACL:更精细的权限控制
当多个用户需要以不同权限访问同一个目录时,传统的属主/属组/其他三组权限就不够用了。ACL(访问控制列表)可以给任意用户或组单独授权:
setfacl -m u:alice:rwx /srv/blog
setfacl -m g:developers:rx /srv/blog
setfacl -m d:u:alice:rwx /srv/blog # 默认 ACL,子文件自动继承
getfacl /srv/blog第一个命令让 alice 对 /srv/blog 有完整权限,第二个让 developers 组可读可执行,互不影响。d: 前缀设置默认 ACL,新建的子文件和子目录会自动继承,团队协作时非常好用。查看权限用 getfacl,删除用 setfacl -b。注意 ACL 需要文件系统支持,ext4、xfs 默认都支持,执行 setfacl 前可以用 mount 输出确认没有挂载参数 noacl。
十、Permission denied 的排查思路
遇到权限报错,按下面顺序排查,基本都能解决:
- 先看当前用户是谁:whoami、id,确认自己在哪个组
- 再看文件属主属组:ls -l,属主对不对?chown 修正
- 再看权限位:ls -l 的 rwx,用 chmod 调整
- 检查 ACL:getfacl 文件,看是否有 ACL 覆盖了传统权限
- 检查目录链路:访问 /var/www/blog/a.txt 时,/var /var/www /var/www/blog 每一级的 x 权限都要有,缺一级就进不去
- 最后检查 SELinux:getenforce 查看状态,如果是 Enforcing,查看 /var/log/audit/audit.log 里的 avc 拒绝记录,或者用 restorecon 恢复上下文
这条链路检查法能解决九成以上的权限问题。PHP 上传目录写不进去,绝大多数情况是目录属主不是 PHP-FPM 的运行用户,而不是权限不够。另外,stat 命令可以看到文件完整的权限、属主、时间戳等信息,比 ls -l 更详细,遇到看不明白的情况可以先 stat 一下文件,确认是否被意外改动过。
十一、安全建议清单
最后总结几条个人站长可以直接落地的安全建议:第一,永远不要对网站目录执行 chmod -R 777;第二,服务账号用 nologin 禁止登录;第三,私钥、数据库密码等敏感文件权限设为 600;第四,定期用 find 检查异常权限文件(SUID、777);第五,多个维护者协作时用 ACL 而不是开放 777;第六,权限变更后立即验证服务是否正常,避免改完才发现网站打不开。
文件权限看似基础,却是服务器安全的基石。把这一块吃透,很多「莫名其妙」的故障都能一眼看穿,网站的安全性也会上一个台阶。