> ## Documentation Index
> Fetch the complete documentation index at: https://docs.bicola.me/llms.txt
> Use this file to discover all available pages before exploring further.

# Linux 文件管理

> 文件操作、查看、查找、权限、压缩 —— 部署运维最核心的命令族

<Note>
  本页覆盖文件层面的所有操作：建立 / 复制 / 删除 / 查看 / 查找 / 权限 / 压缩。掌握这一组命令，相当于掌握了 60% 的日常运维工作。
</Note>

## 1. 文件操作日常

<AccordionGroup>
  <Accordion title="mkdir (make directory) / touch — 创建目录、空文件">
    ```bash theme={null}
    mkdir logs                   # 建一个目录
    mkdir -p data/2026/05        # -p = --parents，多级一起建，已存在不报错
    touch app.log                # 创建空文件（或更新已有文件的修改时间）
    ```

    **场景**：部署前先把日志目录、数据目录建好；`mkdir -p` 写在脚本里很安全，不会因为目录已存在而中断。
  </Accordion>

  <Accordion title="cp (copy) — 复制">
    ```bash theme={null}
    cp app.conf app.conf.bak             # 改配置前先备份
    cp -r src/ /opt/myapp/               # -r = --recursive，递归复制目录
    cp -a /etc/nginx /opt/backup/        # -a = --archive，连权限/时间戳/链接都保留
    ```

    **强烈推荐**：改任何配置文件前，先 `cp xxx xxx.bak`，出问题秒回滚。
  </Accordion>

  <Accordion title="mv (move) — 移动 / 重命名">
    ```bash theme={null}
    mv old.txt new.txt                   # 重命名
    mv app.log /var/log/                 # 移动到目录
    mv app.log{,.2026-05-02}             # 利用花括号扩展，等价 mv app.log app.log.2026-05-02
    ```
  </Accordion>

  <Accordion title="rm (remove) — 删除">
    ```bash theme={null}
    rm file.txt                  # 删单个文件
    rm -r olddir                 # -r = --recursive，删目录
    rm -rf olddir                # -f = --force，强制不提示
    ```

    <Warning>
      **三大忌**：

      1. **永远不要** `rm -rf /`、`rm -rf /*`、`rm -rf $UNSET_VAR/` —— 一旦变量为空就是删根
      2. 路径带变量时先 `echo` 确认：`echo "rm -rf $TARGET"` 看着对再去掉 `echo`
      3. 重要数据先 `mv` 到 `/tmp/trash` 而不是 `rm`
    </Warning>
  </Accordion>

  <Accordion title="ln (link) — 创建链接">
    ```bash theme={null}
    ln source hardlink              # 创建硬链接（很少用）
    ln -s /path/to/file symlink     # ⭐ -s = --symbolic，创建软链接
    ```

    **部署常用**：把 nginx 配置启用：

    ```bash theme={null}
    sudo ln -s /etc/nginx/sites-available/myapp /etc/nginx/sites-enabled/
    ```
  </Accordion>
</AccordionGroup>

## 2. 查看文件内容

```bash theme={null}
cat app.conf            # 整个文件输出（小文件用）
less app.log            # 大文件分页看（推荐）
head -n 20 app.log      # -n = --lines，看前 20 行
tail -n 20 app.log      # 看后 20 行
tail -f app.log         # ⭐ -f = --follow，实时跟踪日志
tail -f -n 100 app.log  # 先显示最后 100 行，再实时跟
```

**`cat` (concatenate) / `less` / `head` / `tail` 的英文含义都很直白**：连接、少量、头、尾。

**`less` 内部快捷键：**

| 键          | 作用          |
| ---------- | ----------- |
| `↑` `↓`    | 上下滚一行       |
| `Space`    | 下翻一页        |
| `b`        | 上翻一页        |
| `g` / `G`  | 跳到文件首 / 尾   |
| `/keyword` | 向下搜索        |
| `n` / `N`  | 下一个 / 上一个匹配 |
| `q`        | 退出          |

## 3. 查找与搜索

<AccordionGroup>
  <Accordion title="find — 找文件">
    ```bash theme={null}
    find /etc -name "nginx.conf"             # 按名字找
    find . -name "*.log"                     # 当前目录所有 .log
    find /var/log -size +100M                # 大于 100M 的文件
    find /tmp -mtime +7                      # -mtime = modification time，7 天以前
    find /tmp -mtime +7 -delete              # 找到就删（清理临时文件）
    find . -type f -name "*.pyc"             # -type f 只找文件（d 是目录）
    find . -type d -name "node_modules"      # 找叫 node_modules 的目录
    ```

    **场景**：忘记配置文件位置、找占空间的大文件、清理过期临时文件。
  </Accordion>

  <Accordion title="grep (global regular expression print) — 在文件里搜索关键词">
    ```bash theme={null}
    grep "error" app.log                # 含 error 的行
    grep -i "error" app.log             # -i = --ignore-case，不分大小写
    grep -n "TODO" main.py              # -n = --line-number，显示行号
    grep -r "DB_HOST" /etc/             # -r = --recursive，目录递归搜
    grep -v "DEBUG" app.log             # -v = --invert-match，"不包含"DEBUG 的行
    grep -E "warn|error" app.log        # -E = --extended-regexp，启用 | 等正则
    grep -A 3 "Exception" app.log       # -A = --after，匹配后再打 3 行（看堆栈）
    grep -B 3 "Exception" app.log       # -B = --before，匹配前 3 行（看上下文）
    grep -c "ERROR" app.log             # -c = --count，只输出匹配行数
    ```

    **黄金组合 `tail -f | grep`：**

    ```bash theme={null}
    tail -f app.log | grep --line-buffered "ERROR"
    # 实时盯日志，只看 ERROR 行
    # --line-buffered 防止 grep 缓冲导致延迟
    ```
  </Accordion>
</AccordionGroup>

## 4. 文件权限：看懂 + 修改

<Note>
  部署中至少 80% 的 "Permission denied" 问题来自这里。这章看懂了，就不会再瞎 `chmod 777` 了。
</Note>

### 4.1 用 `ls -l` 看权限

```text theme={null}
-rwxr-xr-x  1 alice  www-data  2048  Jul  3 10:15  start.sh
│└─┬─┘└─┬─┘└─┬─┘     │  └────┬────┘
│  u    g    o     所有者  所属组
│
└ 文件类型
```

**第一段 10 个字符拆开看：**

```
- rwx r-x r-x
│  │   │   │
│  │   │   └ others 其他用户的权限
│  │   └─── group   所属组的权限
│  └─────── user    所有者的权限
└────────── 文件类型
```

**文件类型字符**：

| 符号  | 含义            |
| --- | ------------- |
| `-` | 普通文件          |
| `d` | 目录（directory） |
| `l` | 软链接（link）     |

**rwx 的含义**：

| 字符  | 全称      | 对文件  | 对目录        |
| --- | ------- | ---- | ---------- |
| `r` | read    | 能读内容 | 能 `ls` 看里面 |
| `w` | write   | 能改内容 | 能在里面增删文件   |
| `x` | execute | 能执行  | 能 `cd` 进去  |

<Tip>
  目录的 `x` 权限是「能进入」，不是「能执行」 —— 这是新手最容易忽视的。没有 `x` 哪怕能 `ls` 也没法 `cd` 进去用。
</Tip>

### 4.2 chmod (change mode) — 改权限

#### 数字模式（最常用）

权重：**r=4, w=2, x=1**，把要给的权限相加：

| 想要         | 二进制 | 数字 |
| ---------- | --- | -- |
| `---` 啥都没  | 000 | 0  |
| `r--` 只读   | 100 | 4  |
| `r-x` 读+执行 | 101 | 5  |
| `rw-` 读+写  | 110 | 6  |
| `rwx` 全开   | 111 | 7  |

三位数字依次给 **u（所有者）、g（所属组）、o（其他人）**：

```bash theme={null}
chmod 755 start.sh
#       │ │ │
#       │ │ └─ o = 5 = r-x
#       │ └─── g = 5 = r-x
#       └───── u = 7 = rwx
```

**部署中最常见的几个数字组合：**

| 数字    | 字母          | 用途                           |
| ----- | ----------- | ---------------------------- |
| `644` | `rw-r--r--` | 普通配置 / 文档（默认）                |
| `755` | `rwxr-xr-x` | 可执行脚本、二进制、目录                 |
| `600` | `rw-------` | 私密文件（如 `~/.ssh/id_rsa`）      |
| `700` | `rwx------` | 私人目录 / 私人脚本                  |
| `777` | `rwxrwxrwx` | ⚠️ 慎用！等于"全世界都能改"，几乎一定有更安全的方案 |

#### 字母模式（精细修改）

```bash theme={null}
chmod +x start.sh           # 给所有人加执行权限
chmod u+x start.sh          # 只给所有者加执行
chmod g-w app.conf          # 去掉组的写权限
chmod o= secret.txt         # 把 others 的权限清空
chmod -R 755 /opt/myapp     # -R = --recursive，递归改整个目录
```

**字母模式语法**：`[谁][操作][什么]`

| 谁              | 操作     | 什么     |
| -------------- | ------ | ------ |
| `u` user 所有者   | `+` 加  | `r` 读  |
| `g` group 所属组  | `-` 减  | `w` 写  |
| `o` others 其他人 | `=` 设为 | `x` 执行 |
| `a` all 所有人    |        |        |

### 4.3 chown (change owner) — 改归属

```bash theme={null}
chown alice file              # 改文件所有者为 alice
chown alice:dev file          # 同时改所有者为 alice、所属组为 dev
chown :dev file               # 只改所属组（用户名留空）
chown -R www-data:www-data /var/www   # 递归把整个目录改成 nginx 用户
chgrp developers file         # chgrp = change group，仅修改所属组
```

**部署典型场景**：

```bash theme={null}
# 上传完代码后，改成 nginx 用户能读：
sudo chown -R www-data:www-data /var/www/myapp
sudo chmod -R 755 /var/www/myapp
```

## 5. 压缩与解压

部署包通常是 `.tar.gz` 或 `.zip`，必须能熟练解压。

### 5.1 tar (tape archive) — 字母逐个拆解

`tar` 的参数像天书，但其实只是字母组合。**记住 5 个核心字母** 就够：

| 字母  | 全称      | 含义                     |
| --- | ------- | ---------------------- |
| `c` | create  | 创建归档（打包）               |
| `x` | extract | 解开归档                   |
| `t` | list    | 仅列出内容（不解压）             |
| `v` | verbose | 显示过程（看每个文件）            |
| `f` | file    | 指定文件名（**必须**，且必须紧跟文件名） |

再加压缩格式：

| 字母  | 含义                          |
| --- | --------------------------- |
| `z` | gzip 格式（`.tar.gz` / `.tgz`） |
| `j` | bzip2 格式（`.tar.bz2`）        |
| `J` | xz 格式（`.tar.xz`）            |

**部署最常用四条命令**：

```bash theme={null}
tar -czvf app.tar.gz ./app/      # 打包目录为 .tar.gz
tar -xzvf app.tar.gz             # ⭐ 解压 .tar.gz
tar -xzvf app.tar.gz -C /opt/    # -C 解压到指定目录（注意大写！）
tar -tzvf app.tar.gz             # 不解压，只看里面有啥
```

**怎么读 `-xzvf`**：x 解压、z 用 gzip、v 详细、f 后面跟文件名。换 bzip2 就把 `z` 换成 `j`。

### 5.2 zip / unzip

```bash theme={null}
zip -r app.zip ./app/            # -r = recursive，递归压缩目录
unzip app.zip                    # 解压到当前目录
unzip app.zip -d /opt/           # -d = directory，解压到指定目录
unzip -l app.zip                 # -l = list，看里面有啥
unzip -o app.zip                 # -o = overwrite，覆盖不提示
```

<Card title="编辑文件 → vim 编辑器" icon="pen-to-square" href="/linux/vim">
  改配置离不开 vim。最低要会：进入插入模式 (`i`)、退出 (`Esc`)、保存退出 (`:wq`)、不保存退出 (`:q!`)。详细看 vim 专题。
</Card>
