为什么权限问题这么常见
“Permission denied”——这可能是Linux新手遇到最多的报错了。我刚开始用Linux的时候,解决方案永远是chmod 777,后来才知道这有多危险。
今天来彻底搞懂Linux的权限体系,以后遇到权限问题不再抓瞎。
理解权限表示
查看文件权限
1
2
3
4
5
6
| $ ls -la /var/www/
total 12
drwxr-xr-x 3 root root 4096 Jan 9 10:00 .
drwxr-xr-x 14 root root 4096 Jan 9 10:00 ..
drwxr-xr-x 2 www-data www-data 4096 Jan 9 10:00 html
-rw-r--r-- 1 www-data www-data 612 Jan 9 10:00 index.html
|
每一列的含义:
| 列 | 示例 | 含义 |
|---|
| 第1列 | -rw-r--r-- | 权限位 |
| 第2列 | 1 | 硬链接数 |
| 第3列 | www-data | 属主(owner) |
| 第4列 | www-data | 属组(group) |
| 第5列 | 612 | 文件大小(字节) |
| 第6-8列 | Jan 9 10:00 | 修改时间 |
| 第9列 | index.html | 文件名 |
权限位解析
1
2
3
4
5
6
7
| -rw-r--r--
│├──┤├──┤├──┤
│ │ │ │
│ │ │ └── 其他用户权限(other): r-- = 只读
│ │ └────── 属组权限(group): r-- = 只读
│ └────────── 属主权限(owner): rw- = 读写
└───────────── 文件类型: - = 普通文件, d = 目录, l = 链接
|
三种基本权限:
| 符号 | 数字 | 含义 | 对文件 | 对目录 |
|---|
r | 4 | 读 | 查看内容 | 列出目录内容 |
w | 2 | 写 | 修改内容 | 创建/删除文件 |
x | 1 | 执行 | 运行脚本 | 进入目录 |
chmod命令:修改权限
数字模式(推荐)
数字模式更直观,把权限转换成三位数字:
1
2
3
4
5
6
7
8
9
10
11
| # 权限计算:r=4, w=2, x=1,相加即可
# 755 = rwxr-xr-x(属主全权限,其他只读+执行)
# 644 = rw-r--r--(属主读写,其他只读)
$ chmod 755 script.sh
$ ls -l script.sh
-rwxr-xr-x 1 root root 1234 Jan 9 10:00 script.sh
$ chmod 644 config.txt
$ ls -l config.txt
-rw-r--r-- 1 root root 567 Jan 9 10:00 config.txt
|
常用权限组合:
| 权限值 | 含义 | 适用场景 |
|---|
755 | rwxr-xr-x | 目录、可执行脚本 |
644 | rw-r–r– | 普通文件、配置文件 |
600 | rw——- | 私钥、敏感配置 |
700 | rwx—— | 私密目录(如.ssh) |
777 | rwxrwxrwx | 永远不要用! |
符号模式
1
2
3
4
5
6
7
8
9
10
11
| # u=属主, g=属组, o=其他, a=所有
# +=添加, -=移除, ==设置
# 给属主添加执行权限
$ chmod u+x script.sh
# 移除其他用户的写权限
$ chmod o-w file.txt
# 给所有用户添加读权限
$ chmod a+r file.txt
|
递归修改
1
2
3
4
5
6
| # 递归修改整个目录
$ chmod -R 755 /var/www/html/
# 更精细的做法:目录755,文件644
$ find /var/www/html/ -type d -exec chmod 755 {} \;
$ find /var/www/html/ -type f -exec chmod 644 {} \;
|
chown命令:修改属主和属组
1
2
3
4
5
6
7
8
9
10
11
12
13
| # 修改属主
$ sudo chown www-data file.txt
# 同时修改属主和属组
$ sudo chown www-data:www-data file.txt
# 只修改属组
$ sudo chown :www-data file.txt
# 或者用chgrp
$ sudo chgrp www-data file.txt
# 递归修改
$ sudo chown -R www-data:www-data /var/www/html/
|
实际输出:
1
2
3
4
5
6
7
| $ ls -l /var/www/html/index.html
-rw-r--r-- 1 root root 612 Jan 9 10:00 index.html
$ sudo chown www-data:www-data /var/www/html/index.html
$ ls -l /var/www/html/index.html
-rw-r--r-- 1 www-data www-data 612 Jan 9 10:00 index.html
|
实战场景
场景1:Nginx 403 Forbidden
这是最常见的权限问题:
1
2
3
4
5
6
7
8
| # Nginx默认以www-data用户运行
$ ps aux | grep nginx
root 1234 0.0 0.1 65432 1234 ? Ss 10:00 0:00 nginx: master
www-data 1235 0.0 0.3 65432 3456 ? S 10:00 0:00 nginx: worker
# 确保网站文件属于www-data
$ sudo chown -R www-data:www-data /var/www/mysite/
$ sudo chmod -R 755 /var/www/mysite/
|
场景2:SSH密钥权限
1
2
3
4
5
6
7
8
9
| # SSH对密钥权限要求非常严格
$ chmod 700 ~/.ssh
$ chmod 600 ~/.ssh/id_ed25519 # 私钥
$ chmod 644 ~/.ssh/id_ed25519.pub # 公钥
$ chmod 600 ~/.ssh/authorized_keys
# 如果权限不对,会报错:
# WARNING: UNPROTECTED PRIVATE KEY FILE!
# Permissions 0644 for '/home/user/.ssh/id_ed25519' are too open.
|
场景3:Shell脚本无法执行
1
2
3
4
5
6
7
8
9
10
| $ ./deploy.sh
-bash: ./deploy.sh: Permission denied
$ ls -l deploy.sh
-rw-r--r-- 1 root root 1234 Jan 9 10:00 deploy.sh
# 缺少执行权限,添加它
$ chmod +x deploy.sh
$ ./deploy.sh
Deploying...
|
特殊权限位
| 权限 | 数字 | 作用 | 示例 |
|---|
| SUID | 4xxx | 以文件属主身份执行 | /usr/bin/passwd |
| SGID | 2xxx | 以文件属组身份执行 | 共享目录 |
| Sticky | 1xxx | 只有属主能删除 | /tmp |
1
2
3
4
5
6
7
8
| # 查看特殊权限
$ ls -l /usr/bin/passwd
-rwsr-xr-x 1 root root 68208 Jan 9 10:00 /usr/bin/passwd
# ^ 这个s就是SUID
$ ls -ld /tmp
drwxrwxrwt 15 root root 4096 Jan 9 10:00 /tmp
# ^ 这个t就是Sticky bit
|
权限排查清单
遇到"Permission denied"时,按这个顺序检查:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
| # 1. 查看当前用户
$ whoami
deploy
# 2. 查看文件权限和属主
$ ls -la /path/to/file
# 3. 查看用户所属组
$ groups deploy
deploy : deploy www-data sudo
# 4. 检查目录链路上每一级的权限
$ namei -l /var/www/mysite/index.html
f: /var/www/mysite/index.html
dr-xr-xr-x root root /
drwxr-xr-x root root var
drwxr-xr-x root root www
drwxr-xr-x www-data www-data mysite
-rw-r--r-- www-data www-data index.html
|
总结
权限管理的核心原则是最小权限:只给必要的权限,不要图省事用777。记住常用的几个数字组合就行:目录755、文件644、私密文件600。
如果你想更深入地了解用户和权限管理,推荐阅读Linux用户与权限管理详解。关于SSH密钥的权限配置,可以参考SSH远程连接完全指南。