文件权限看着简单,出问题却往往很难查:服务读不到配置、上传的图片 404、脚本“手动能跑定时任务不行”——多数是权限。

rwx 三段与数字法

ls -l 输出的前 10 位是这样切的:

-rwxr-xr--  1 deploy deploy 1024 Sep 24 10:00 run.sh
│└┬┘└┬┘└┬┘
│ │  │  └── 其他人(other)
│ │  └───── 所属组(group)
│ └──────── 属主(user)
└────────── 类型:- 普通文件,d 目录,l 软链接

数字法就是把每段的三位当二进制读:r=4、w=2、x=1。

组合 数字 含义
rwx 7 读 + 写 + 执行
rw- 6 读 + 写
r-x 5 读 + 执行(目录需要有它才能进入)
r-- 4 只读
--- 0 无权限
chmod 644 config.yml     # 属主可读写,其他人只读 —— 配置文件的标准答案
chmod 600 .env           # 只有属主能读写 —— 密钥必须这样
chmod 755 run.sh         # 脚本要可执行
chmod +x script.sh       # 符号法:给所有人加执行位

目录的 x 位是“通行证”

这是最容易误解的一点:目录上的 x 不是“可执行”,而是“可进入”。

  • 只有 r 没有 x:能列出文件名,但不能 cd 进去,也不能读文件内容。
  • 只有 x 没有 r:能 cd 进去、能读已知路径的文件,但 ls 看不到列表。

所以“目录给 644”是典型的错误配置。

umask 决定新建文件的默认权限

新建文件的权限 = 666 - umask,新建目录 = 777 - umask。

umask          # 常见输出 0022
umask -S       # 符号形式:u=rwx,g=rx,o=rx
umask 027      # 临时收紧:新建文件 640,新建目录 750

0022 的含义是“从默认权限里去掉 group 和 other 的写位”,所以新建文件是 644、目录是 755。想永久生效要写进 ~/.bashrc(用户级)或 /etc/profile(系统级)。

常见事故与排查顺序

  1. 服务读不到文件 → sudo -u <服务用户> cat <文件> 复现,再对比属主/属组。
  2. “手动能跑、cron 不行” → cron 的环境变量与 umask 都与登录 shell 不同,在脚本里写绝对路径并显式设 umask。
  3. 上传目录 403 → Web 进程需要对目录有 x,对文件有 r;通常目录 755、文件 644。
  4. 改了权限仍然不行 → 检查 SELinux / AppArmor 或父目录链上的权限(任意一层缺 x 都进不去)。

排查用的万能句式:用“出问题的那个身份”去复现,而不是用 root。root 几乎什么都能读,用 root 试永远成功。