---
url: /courses/cloud-platform-build-management/02-linux-server-survival/index.md
---
# 第二次课：Linux 服务器基础巡检

## 进入本课环境

* `[Windows PowerShell] wsl ~`：打开本机默认的 WSL2 Ubuntu；出现 `用户名@主机名:~$` 后再执行标为 `[WSL]` 的命令。
* `[WSL] ssh root@你的ECS公网IP`：从 WSL 连接自己的 ECS；如果登录用户不是 `root`，请换成控制台显示的实际用户，看到远端提示符后再执行标为 `[ECS]` 的命令。

SSH 登录只是起点。接手一台 Linux 服务器之后，常规动作是：先确认当前用户、主机和目录，再检查文件、权限、软件、进程与资源状态。

本课把学过的 Linux 命令串成一套基础巡检流程：确认位置 → 检查文件与权限 → 检查软件、进程和资源 → 把整个过程写成可重复运行的脚本。

完成后应留下：

* `server-check.sh`：一份最小服务器巡检脚本；
* 一份带截图和解释的 Linux 服务器巡检报告；
* 一份权限错误的“现象—证据—修复—验证”说明。

## 2.1 确认用户、主机和当前目录

终端开多了，很容易在错误的机器或目录里敲错命令。动手前先确认三件事：

* `whoami`：当前使用哪个账号；登录、切换用户或准备改权限前使用。
* `hostname`：当前是哪台机器；同时连接 WSL 和多台 ECS 时使用。
* `pwd`：当前位于哪个目录；创建、移动、覆盖或删除文件前使用。

这三条命令构成每次变更前的“位置确认”：

```bash
[ECS] whoami
[ECS] hostname
[ECS] pwd
```

::: tip 关键提醒
身份、主机和目录没有确认清楚时，不执行删除、覆盖、改权限或安装软件等变更操作。
:::

### 绝对路径与相对路径

**绝对路径**（从根目录 / 开始，位置明确，不依赖当前工作目录） 例如：

```txt
/home/student/cloud-course/lab-02/server-check.sh
```

**相对路径**（从当前工作目录出发，需要结合 pwd 才能确定真实位置） 例如：

```txt
./server-check.sh
../lab-01/verify.sh
```

`./` 不是装饰，它明确告诉 Shell：”在当前目录找这个文件”。

Shell 通过 `PATH` 环境变量查找可执行命令，当前目录通常不在 `PATH` 中。所以直接输入 `server-check.sh` 会报 “command not found”，而 `./server-check.sh` 强制从当前目录执行。

`../` 表示”上一级目录”。`../lab-01/verify.sh` 的意思是：从当前目录向上一层，进入 `lab-01`，找 `verify.sh`。可以连续使用：`../../` 表示向上两级，依此类推。

## 2.2 常用目录与实验目录

Linux 中常见的目录包括：

* `/`：整个 Linux 文件系统的起点；
* `/home`：普通用户的个人目录；
* `/etc`：系统和服务配置；
* `/var`：日志、缓存和经常变化的数据；
* `/tmp`：临时文件，不能当作长期存储；
* `/usr`：大量命令、库和共享资源；
* `/opt`：第三方或自定义软件常用位置。

所有练习都放在自己的实验目录中，避免误改系统文件：

1. `mkdir -p`：创建实验目录；父目录不存在时一并创建。
2. `cd`：进入实验目录；后续相对路径都以这里为起点。
3. `pwd`：打印当前位置；确认自己确实进入了目标目录。

```bash
[ECS] mkdir -p ~/cloud-course/lab-02
[ECS] cd ~/cloud-course/lab-02
[ECS] pwd
```

其中 `~` 表示当前用户的家目录。执行后，`pwd` 的输出应以家目录路径开头。

## 2.3 文件与目录的基本检查

下面的例子会创建一个文件和一个证据目录，并演示复制与改名：

* `touch notes.txt`：创建空文件；常用于先准备一个占位文件。
* `mkdir -p evidence`：创建证据目录；后面把需要保留的结果放进去。
* `cp notes.txt evidence/notes-copy.txt`：复制文件；原文件仍然保留。
* `mv evidence/notes-copy.txt evidence/baseline.txt`：移动并改名；原路径中的 `notes-copy.txt` 不再存在。

```bash
[ECS] touch notes.txt
[ECS] mkdir -p evidence
[ECS] cp notes.txt evidence/notes-copy.txt
[ECS] mv evidence/notes-copy.txt evidence/baseline.txt
```

文件准备好后，用下面几条只读命令检查：

* `ls -lah`：列出当前目录全部文件（含隐藏文件），并以易读单位展示大小。接手新目录时习惯先跑一次；
* `file notes.txt`：判断文件真实类型，适合在扩展名不可信或文件打不开时排查；
* `stat notes.txt`：打印文件所有者、权限位、字节大小与三类时间戳，常用于排查文件变更；
* `du -sh .`：统计当前目录总空间占用，在清理或打包前确认体积；
* `find . -maxdepth 2 -type f -print`：打印两层深度的所有文件，用来核对交付结构是否完整。

在终端中执行并观察输出：

```bash
[ECS] ls -lah
[ECS] file notes.txt
[ECS] stat notes.txt
[ECS] du -sh .
[ECS] find . -maxdepth 2 -type f -print
```

删文件前要养成三确认习惯：核对当前路径、核对文件名、确认数据是否已备份。在路径尚未看清前，绝不要随意执行带有 `-rf`（递归且强制）参数的删除命令。

## 2.4 Linux 文件权限

运行：

```bash
[ECS] ls -l
```

你可能看到：

```txt
-rwxr-x--- 1 student cloud 420 Jul 27 10:20 server-check.sh
```

可以把权限拆成三组：

```txt
rwx   r-x   ---
所有者  所属组  其他人
```

* `r`：读取；
* `w`：写入；
* `x`：执行。对目录来说，`x` 还关系到能否进入和访问目录中的对象。

符号模式遵循 `[谁][操作][权限]` 格式：

* **谁**：`u`=所有者，`g`=所属组，`o`=其他人，`a`=全部；
* **操作**：`+`=增加，`-`=移除，`=`=设为确切值；
* **权限**：`r`=读取，`w`=写入，`x`=执行。

两个例子：

* `chmod u+x server-check.sh`：给所有者增加执行权限；脚本内容可信、所有者只缺执行权限时使用。
* `chmod go-rwx private-note.txt`：移除所属组和其他人的读、写、执行权限；保护只允许本人访问的文件时使用。

明确目标对象和所需权限后执行：

```bash
[ECS] chmod u+x server-check.sh
[ECS] chmod go-rwx private-note.txt
```

::: warning 安全边界
遇到 Permission denied 时，不要直接 chmod 777。先用 id、ls -l 和 stat 确认执行者、文件所有者与真正缺少的权限，只补最小的一项。
:::

{{guided-demo:lesson-02-permission-repair}}

### 真实运行案例：只补真正缺少的权限

下面的错误来自云主机 B 中一个独立临时目录。脚本最初是 `640`，所有者可以读写但不能执行；增加 `u+x` 后，脚本正常运行。

这个案例遵循“现象—证据—修改—验证”的排查逻辑：

1. 现象是 `Permission denied`；
2. `stat` 证明当前模式为 `640`，缺少所有者执行权限；
3. 修改只有 `chmod u+x`；
4. 再次查看权限并运行脚本，才算完成验证。

## 2.5 Ubuntu 软件包检查

课程统一使用 Ubuntu。以 `curl`（网络请求工具）为例，检查一个软件包可以从三个角度入手：命令在不在、软件包装没装、版本对不对。

* `command -v curl`：Shell 能否找到 `curl` 命令；准备使用命令前先做快速确认。
* `dpkg -l | grep '^ii' | grep curl`：`dpkg -l` 列出所有软件包状态，每行开头是两字母状态码——第一个字母表示期望状态（`i`=应安装），第二个表示当前状态（`i`=已安装）。`^ii` 中的 `^` 是正则锚点，表示"行必须以 `ii` 开头"，合起来就是过滤出已安装的包。
* `apt-cache policy curl`：已安装版本和软件源候选版本是什么；比较当前版本与可用版本时使用。

在终端中验证这三种检查方式：

```bash
[ECS] command -v curl
[ECS] dpkg -l | grep '^ii' | grep curl
[ECS] apt-cache policy curl
```

刷新软件包索引：

```bash
[ECS] sudo apt update
```

`apt update` 刷新的是“可用软件清单”，不会自动把已安装的软件全部升级。磁盘、网络和变更影响都没检查之前，不要直接跑全系统升级。

## 2.6 查看和停止进程

**进程**（程序运行后形成的活动实例，拥有 PID、账号和资源占用）（PID 即进程编号，是系统分配给每个进程的唯一数字标识）可以从三个角度查看：

* `ps -ef`：查看较完整的进程清单（`-e`=所有进程，`-f`=完整格式）；刚接手服务器、还不知道目标进程名称时使用。
* `pgrep -a sshd`：按名称查找进程并显示完整命令；确认某个已知程序是否运行时使用。
* `ps -eo ... --sort=-%mem | head`：按内存占用排序；寻找当前高内存进程时使用。

执行以下命令查看进程状态：

```bash
[ECS] ps -ef
[ECS] pgrep -a sshd
[ECS] ps -eo pid,user,comm,%cpu,%mem --sort=-%mem | head
```

找一个属于自己的临时进程来练习查找与停止：

1. `sleep 300 &`：在后台启动一个 300 秒测试进程。
2. `demo_pid=$!`：把刚启动进程的 PID 保存到变量。
3. `ps -p ...`：核对 PID、用户、状态、运行时间和命令。
4. `kill "$demo_pid"`：向已经核对过的测试进程发送普通终止信号。
5. 再次运行 `ps -p ...`：找不到该 PID，才说明它已经退出。

```bash
[ECS] sleep 300 &
[ECS] demo_pid=$!
[ECS] ps -p "$demo_pid" -o pid,user,stat,etime,cmd
[ECS] kill "$demo_pid"
[ECS] ps -p "$demo_pid"
```

::: tip 关键提醒
停止进程前先核对 PID、所属用户和命令。普通终止信号没有效果时再分析原因，不把 kill -9 当作第一选择。
:::

## 2.7 检查 CPU、内存与磁盘

2 核 2 GiB 的 ECS 资源有限，巡检时要能分清 CPU、内存、文件系统和进程各自在说什么。常用命令如下：

* `uptime`：查看运行时长和 1、5、15 分钟负载；判断系统是否持续繁忙时使用。
* `nproc`：查看可用 CPU（中央处理器）核数；解释负载前先确认它。
* `free -h`：查看内存整体状态；重点读取 `available`。
* `df -hT /`：查看根文件系统类型、容量和使用率（`-h`=易读单位，`-T`=显示文件系统类型）；判断哪个文件系统空间紧张。
* `lsblk -f`：查看磁盘、分区、文件系统和挂载点；分清“磁盘”和“已挂载文件系统”。
* `du -xh --max-depth=1 "$HOME"`：比较家目录下一级目录的占用；继续定位大目录。
* `ps -eo ... --sort=-%mem | head`：查看当前高内存进程；把资源现象追到具体进程。

执行以下命令采集资源状态：

```bash
[ECS] uptime
[ECS] nproc
[ECS] free -h
[ECS] df -hT /
[ECS] lsblk -f
[ECS] du -xh --max-depth=1 "$HOME" 2>/dev/null | sort -h
[ECS] ps -eo pid,user,comm,%cpu,%mem --sort=-%mem | head
```

分析输出时留几个心：

* `uptime` 的负载要结合 CPU 核数和持续时间看；
* `free -h` 重点关注 `available`，不能把缓存简单理解为“被浪费”；
* `df` 看文件系统整体占用，`du` 看目录和文件累计占用；
* 单次进程列表只说明当前时刻，不能单凭一张截图断定持续泄漏。

::: tip 关键提醒
磁盘空间紧张时，先用 df 确认哪个文件系统紧张，再用 du 和 find 缩小范围。没有找到占用来源前，不随机删除 /var 或系统目录。
:::

### 真实运行案例：同一时刻的资源证据

下面几组输出来自云主机 B 的同一次巡检。它们描述的是一个时间点，不代表服务器永远保持这个状态。

根据上面这组数据，可以得出：

* 4 核 CPU 对应的 1 分钟负载约为 `0.54`，截图时没有表现出 CPU 排队压力；
* `available` 内存约为 `1.7 GiB`，不能因为 `free` 只有 `166 MiB` 就说内存已经耗尽；
* 根文件系统使用率为 `38%`，截图时没有空间告警迹象；
* 进程列表只说明当前谁占用较高，还不能凭一次截图断定发生内存泄漏。

## 2.8 编写服务器巡检脚本

在 `~/cloud-course/lab-02` 中创建 `server-check.sh`：

```bash
#!/usr/bin/env bash

set -u

section() {
  printf '\n===== %s =====\n' "$1"
}

section "检查时间"
date -Is

section "身份与主机"
whoami
hostname
pwd

section "系统与负载"
uname -a
uptime
nproc

section "内存"
free -h

section "根文件系统"
df -hT /

section "家目录占用"
du -sh "$HOME"

section "内存占用较高的进程"
ps -eo pid,user,comm,%cpu,%mem --sort=-%mem | head -n 6
```

脚本保存后，按以下步骤检查并运行：

1. `bash -n server-check.sh`：只检查 Shell 语法，不执行脚本。
2. `ls -l server-check.sh`：查看当前权限，保留修改前证据。
3. `chmod u+x server-check.sh`：只给所有者增加执行权限。
4. `./server-check.sh | tee server-check.txt`：运行脚本，同时把输出保存到文件。

在终端中依次执行：

```bash
[ECS] bash -n server-check.sh
[ECS] ls -l server-check.sh
[ECS] chmod u+x server-check.sh
[ECS] ./server-check.sh | tee server-check.txt
```

脚本跑完后，根据输出至少写出三条结论——比如内存紧不紧张、根文件系统空间安不安全、哪个进程吃内存最多。

## 2.9 实训：服务器基础巡检

打开[实训 02：服务器基础巡检](./lab-02.md)，按指导书中的截图位置和验收步骤完成下面四项任务。

实训包含三个分站任务和一个综合任务：

1. **路径与文件站**：在指定实验目录中创建、复制、移动并检查文件；
2. **权限修复站**：定位一个脚本为什么不能执行，只补充真正缺少的权限；
3. **进程与资源站**：找到自己的测试进程，并用 `free`、`df`、`du` 说明资源状态；
4. **综合巡检**：完成 `server-check.sh`，保存输出并解释结果。

ECS 可用的同学在 `[ECS]` 完成；ECS 仍不可用的同学可以先在 `[WSL]` 完成同样任务，但 Word 中必须标明运行位置，服务器可用后再补一次 ECS 巡检。

提交前清理实验环境：

```bash
[ECS] rm -rf ~/cloud-course/lab-02
```

最终提交：

```txt
班级_学号_姓名_第02次课_Linux服务器巡检.docx
```

Word 中依次放入目录与文件证据、权限修复前后对比、进程检查、资源检查、巡检脚本和验收结果。每张截图都要说明命令位置、关键输出和结论。

{{reflection-checkpoint:lesson-02-inspection-ready}}

{{chat-lab:lesson-02-linux-evidence}}

::: tip 关键提醒
整理完成后，将一个最终 .docx 上传到智慧职教在线平台“第02次课”对应的作业收集中。server-check.sh 的代码以文本形式粘贴进 Word，不单独上传含个人环境信息的目录。
:::

## 2.10 第二次课小测

小测检查以下判断能力：

* 路径是否明确；
* 权限修改是否最小；
* 进程和资源证据是否支持结论；
* 巡检脚本是否可重复、可解释。

{{assessment:lesson-02-check}}

## 2.11 小结

本课把零散的 Linux 命令串成了一次完整的服务器巡检：

* 操作前先确认账号、主机和目录；
* 用绝对路径与相对路径说明对象到底在哪里；
* 权限问题先判断主体、对象和缺少的动作，不使用 `chmod 777` 逃避分析；
* 安装软件前先确认命令、包和版本状态；
* 停止进程前核对 PID、用户和命令；
* `free`、`df`、`du` 和进程列表分别回答不同的资源问题；
* 把检查写进脚本，再用输出形成可复核证据。

下一次课接着检查服务状态、监听端口和日志，并部署本课程的第一个 Nginx 服务。

{{assistant-invite:lesson-02-finish}}
