Linux/运维面试题
Linux/运维面试题
简介
Linux 是服务器端的主流操作系统,掌握 Linux 基础命令、权限管理、网络配置和故障排查是后端开发和运维工程师的必备技能。本篇涵盖 Linux 常用命令、文件系统、进程管理、网络排查等高频面试话题。
特点
面试题目
1. Linux 常用的文件和目录操作命令有哪些?
答: 文件和目录操作是 Linux 最基础的操作,以下是常用命令分类:
# 目录操作
pwd # 显示当前目录
ls -la # 列出所有文件(含隐藏文件,详细信息)
ls -lhS # 按文件大小排序
ls -lht # 按修改时间排序
mkdir -p /a/b/c # 递归创建目录
tree -L 2 /path # 以树形结构显示目录(2层)
# 文件操作
cp -r src/ dest/ # 递归复制目录
cp -a src/ dest/ # 归档模式复制(保留属性)
mv old new # 移动/重命名
rm -rf directory # 递归强制删除(谨慎使用!)
ln -s target link # 创建软链接
ln target link # 创建硬链接
# 文件查看
cat file # 查看完整文件内容
head -n 20 file # 查看前 20 行
tail -n 20 file # 查看后 20 行
tail -f /var/log/syslog # 实时跟踪日志文件
less file # 分页查看(支持搜索 /pattern)
wc -l file # 统计行数
# 文件查找
find / -name "*.log" -mtime +7 # 查找7天前的 .log 文件
find /var -size +100M -type f # 查找大于100MB的文件
find . -name "*.cs" | xargs grep "TODO" # 在 .cs 文件中搜索 TODO
grep -rn "error" /var/log/ --include="*.log" # 递归搜索日志中的 error
grep -E "ERR|WARN|FATAL" app.log # 使用正则搜索多种模式
# 文件压缩
tar -czf backup.tar.gz /path/to/dir # 压缩目录
tar -xzf backup.tar.gz # 解压 .tar.gz
tar -cjf backup.tar.bz2 /path/to/dir # 压缩为 .tar.bz2(更小)
unzip archive.zip # 解压 zip2. Linux 文件权限如何管理?
答: Linux 使用 rwx(读/写/执行)权限模型,每个文件有三组权限:所有者(u)、所属组(g)、其他用户(o)。
# 权限表示法
# -rwxr-xr-- => 所有者: rwx(7), 组: r-x(5), 其他: r--(4)
# drwxr-xr-x => 目录, 权限 755
# 修改权限
chmod 755 script.sh # 数字法: rwxr-xr-x
chmod u+x script.sh # 符号法: 给所有者加执行权限
chmod g-w file.txt # 符号法: 给组去除写权限
chmod -R 644 /var/www/ # 递归修改目录权限
# 修改所有者
chown user:group file # 同时修改所有者和组
chown -R www-data:www-data /var/www/ # 递归修改
# 特殊权限
chmod +s /usr/bin/passwd # SUID: 以文件所有者身份执行
chmod g+s /shared/dir # SGID: 新文件继承组
chmod +t /tmp # Sticky Bit: 只有所有者能删除
# 查看权限
stat file # 查看文件详细属性
id username # 查看用户的 UID/GID
groups username # 查看用户所属组
# ACL(访问控制列表)- 更精细的权限控制
setfacl -m u:nginx:rx /var/www/html # 给 nginx 用户设置读执行权限
setfacl -m g:dev:rw file.txt # 给 dev 组设置读写权限
getfacl file.txt # 查看 ACL 权限3. 如何管理 Linux 的进程和服务?
答: 进程管理包括查看、终止、优先级调整和后台运行等操作。
# 进程查看
ps aux # 查看所有进程(BSD 格式)
ps -ef # 查看所有进程(标准格式)
ps aux --sort=-%mem # 按内存使用排序
ps aux --sort=-%cpu # 按 CPU 使用排序
pgrep -f "dotnet" # 按名称查找进程 ID
pidof nginx # 查找 nginx 的 PID
# 实时监控
top # 实时进程监控
htop # 增强版 top(需安装)
# top 中常用快捷键:
# M - 按内存排序
# P - 按 CPU 排序
# k - 杀死进程
# q - 退出
# 终止进程
kill PID # 发送 SIGTERM(优雅终止)
kill -9 PID # 发送 SIGKILL(强制终止)
killall nginx # 按名称终止所有 nginx 进程
pkill -f "dotnet MyApp" # 按命令行模式终止
# 后台运行
nohup ./myapp & # 后台运行,不挂断
nohup ./myapp > output.log 2>&1 & # 后台运行,重定向输出
jobs # 查看当前终端的后台任务
fg %1 # 将后台任务调到前台
bg %1 # 将暂停的任务放回后台
# 系统服务管理(systemd)
systemctl start nginx # 启动服务
systemctl stop nginx # 停止服务
systemctl restart nginx # 重启服务
systemctl reload nginx # 重新加载配置(不中断服务)
systemctl enable nginx # 开机自启动
systemctl disable nginx # 取消开机自启动
systemctl status nginx # 查看服务状态
systemctl list-units --type=service # 列出所有服务
# 查看系统资源
free -h # 内存使用情况
df -h # 磁盘使用情况
du -sh /var/log/* # 查看目录大小
iostat -x 1 # IO 统计
vmstat 1 # 虚拟内存统计
uptime # 系统运行时间和负载4. 如何排查 Linux 系统的网络问题?
答: 网络排查遵循从底层到高层的系统化方法。
# 1. 接口和连接检查
ip addr show # 查看 IP 地址(替代 ifconfig)
ip link show # 查看网络接口状态
ethtool eth0 # 查看网卡详细信息和速率
# 2. 连通性测试
ping -c 4 8.8.8.8 # 测试网络连通性
ping -c 4 example.com # 测试域名解析 + 连通性
traceroute example.com # 路由追踪
mtr --report example.com # 持续路由追踪(更强大)
# 3. DNS 排查
nslookup example.com # DNS 查询
dig example.com # 详细 DNS 查询
dig @8.8.8.8 example.com # 指定 DNS 服务器查询
cat /etc/resolv.conf # 查看 DNS 配置
cat /etc/hosts # 查看本地 DNS 映射
# 4. 端口和服务检查
netstat -tlnp # 查看监听端口(传统)
ss -tlnp # 查看监听端口(推荐)
lsof -i :80 # 查看占用 80 端口的进程
lsof -i -u www-data # 查看某用户的所有网络连接
nmap -sT localhost # 扫描本机开放端口
# 5. 抓包分析
tcpdump -i eth0 port 80 # 抓取 80 端口的数据包
tcpdump -i eth0 -w capture.pcap # 保存为 pcap 文件(Wireshark 分析)
tcpdump -i eth0 host 192.168.1.100 # 抓取特定主机的流量
# 6. HTTP 请求测试
curl -v https://api.example.com # 详细输出请求过程
curl -I https://example.com # 只获取响应头
curl -X POST -H "Content-Type: application/json" \
-d '{"key":"value"}' https://api.example.com
wget -O output.html https://example.com # 下载文件
# 7. 防火墙检查
iptables -L -n # 查看防火墙规则
iptables -L -n -v # 详细规则(含包计数)
# firewalld(CentOS 7+)
firewall-cmd --list-all
firewall-cmd --add-port=8080/tcp --permanent
firewall-cmd --reload
# ufw(Ubuntu)
ufw status
ufw allow 80/tcp5. 如何编写 Shell 脚本进行自动化运维?
答: Shell 脚本是自动化运维的核心工具,以下是实用的脚本示例。
#!/bin/bash
# 服务器健康检查脚本
# 配置
LOG_FILE="/var/log/health_check.log"
ALERT_EMAIL="admin@example.com"
THRESHOLD_CPU=80
THRESHOLD_MEM=90
THRESHOLD_DISK=85
# 日志函数
log() {
echo "[$(date '+%Y-%m-%d %H:%M:%S')] $1" | tee -a "$LOG_FILE"
}
# 发送告警
send_alert() {
local subject="[ALERT] $(hostname) - $1"
local body="$2"
echo "$body" | mail -s "$subject" "$ALERT_EMAIL"
log "ALERT: $1"
}
# 1. CPU 检查
check_cpu() {
local cpu_usage=$(top -bn1 | grep "Cpu(s)" | awk '{print $2}' | cut -d. -f1)
if [ "$cpu_usage" -gt "$THRESHOLD_CPU" ]; then
local top_procs=$(ps aux --sort=-%cpu | head -6)
send_alert "CPU 使用率过高: ${cpu_usage}%" "$top_procs"
else
log "CPU 使用率: ${cpu_usage}% - 正常"
fi
}
# 2. 内存检查
check_memory() {
local mem_usage=$(free | grep Mem | awk '{printf("%.0f", $3/$2 * 100)}')
if [ "$mem_usage" -gt "$THRESHOLD_MEM" ]; then
local mem_detail=$(free -h)
send_alert "内存使用率过高: ${mem_usage}%" "$mem_detail"
else
log "内存使用率: ${mem_usage}% - 正常"
fi
}
# 3. 磁盘检查
check_disk() {
while read -r line; do
local usage=$(echo "$line" | awk '{print $5}' | sed 's/%//')
local partition=$(echo "$line" | awk '{print $6}')
if [ "$usage" -gt "$THRESHOLD_DISK" ]; then
send_alert "磁盘空间不足: ${partition} ${usage}%" "$line"
else
log "磁盘 ${partition}: ${usage}% - 正常"
fi
done <<< "$(df -h | grep '^/dev/')"
}
# 4. 关键服务检查
check_services() {
local services=("nginx" "docker" "sshd")
for service in "${services[@]}"; do
if systemctl is-active --quiet "$service"; then
log "服务 $service: 运行中"
else
send_alert "服务 $service 已停止" "请检查服务状态"
# 尝试自动重启
systemctl restart "$service"
log "已尝试重启 $service"
fi
done
}
# 5. 检查应用日志中的错误
check_errors() {
local error_count=$(grep -c "ERROR\|FATAL\|Exception" /var/log/app/app.log 2>/dev/null || echo "0")
log "应用错误数: $error_count"
}
# 执行所有检查
log "========== 开始健康检查 =========="
check_cpu
check_memory
check_disk
check_services
check_errors
log "========== 健康检查完成 =========="6. 如何进行系统性能分析和调优?
答: 性能分析需要从 CPU、内存、磁盘 I/O 和网络四个维度系统化排查。
# === CPU 分析 ===
# 查看整体 CPU 使用情况
mpstat 1 5 # 每 1 秒采样,共 5 次
sar -u 1 5 # CPU 使用率历史
# 查看每个 CPU 核心的使用情况
mpstat -P ALL 1 3 # 每个核心的使用率
# 分析进程级别的 CPU 消耗
pidstat -u 1 5 # 每秒输出进程 CPU 使用情况
perf top # 实时性能分析(类似 top 但显示函数级)
# CPU 调优建议:
# - 检查是否有单进程占满单核(考虑多线程/多进程架构)
# - 检查上下文切换频率(vmstat 的 cs 列)
# - 使用 taskset 绑定 CPU 亲和性
taskset -cp 0-3 $(pidof myapp) # 将进程绑定到 CPU 0-3
# === 内存分析 ===
# 查看内存使用详情
cat /proc/meminfo # 详细的内存信息
vmstat 1 5 # 虚拟内存统计
free -h --si # 人类可读的内存使用
# 进程级内存分析
pidstat -r 1 5 # 每秒输出进程内存使用
pmap -x $(pidof myapp) # 查看进程内存映射
smem -t -k # 按进程显示内存使用(需安装)
# 内存调优建议:
# - 关注 available 而不是 free(Linux 会用空闲内存做缓存)
# - 检查 Swap 使用量,频繁 swap 说明内存不足
# - 调整 swappiness:echo 10 > /proc/sys/vm/swappiness
# - 使用 cgroup 限制进程内存使用
# === 磁盘 I/O 分析 ===
iostat -x 1 5 # 扩展 I/O 统计
iotop # 按进程显示 I/O 使用(需安装)
pidstat -d 1 5 # 进程级 I/O 统计
# 关键指标:
# %util > 80%:磁盘繁忙,可能成为瓶颈
# await > 10ms:I/O 等待时间过长
# svctm:实际服务时间
# I/O 调优:
# - 使用 deadline 或 noop 调度器(SSD 用 noop)
# echo noop > /sys/block/sda/queue/scheduler
# - 调整文件系统挂载参数:noatime, nodiratime
# - 考虑使用 XFS 替代 ext4 处理大文件场景
# === 网络性能分析 ===
sar -n DEV 1 5 # 网络设备流量统计
nicstat 1 5 # 网卡流量详情(需安装)
ss -s # 连接统计摘要
netstat -s # 网络协议栈统计
# 网络调优:
# - 增大 TCP 缓冲区
sysctl net.core.rmem_max=16777216
sysctl net.core.wmem_max=16777216
# - TIME_WAIT 优化
sysctl net.ipv4.tcp_tw_reuse=1
sysctl net.ipv4.tcp_fin_timeout=15
# - 连接队列大小
sysctl net.core.somaxconn=65535
sysctl net.ipv4.tcp_max_syn_backlog=655357. 如何排查 Java/dotnet 应用线上问题?
答: 线上问题排查需要从日志、进程状态和资源消耗三个方向入手。
# 1. 应用无法启动
# 检查日志
journalctl -u myapp --since "10 minutes ago" # systemd 服务日志
tail -200 /var/log/app/error.log # 应用错误日志
# 常见原因:
# - 端口被占用:ss -tlnp | grep 8080
# - 权限不足:ls -la /path/to/app
# - 配置文件错误:检查 application.yml / appsettings.json 语法
# - 内存不足:dmesg | grep -i "out of memory"
# 2. 应用响应慢
# 查看进程资源占用
top -p $(pidof myapp) # 监控特定进程
pidstat -p $(pidof myapp) 1 10 # CPU、内存、IO 详细统计
# 线程 Dump(Java)
jstack $(pidof java) > thread_dump.txt
# 线程 Dump(dotnet)
dotnet-trace collect -p $(pidof myapp)
# GC 日志分析
# Java: 查看 GC 频率和停顿时间
jstat -gcutil $(pidof java) 1000 10
# 3. 内存泄漏
# Java 堆 Dump
jmap -dump:format=b,file=heap.hprof $(pidof java)
# dotnet 内存 Dump
dotnet-gcdump collect -p $(pidof myapp)
# 查看进程内存映射
cat /proc/$(pidof myapp)/smaps | head -100
# 4. CPU 飙高
# 找到高 CPU 线程
top -H -p $(pidof myapp) # 显示线程级 CPU 使用
# 将线程 ID 转为十六进制
printf "%x\n" THREAD_ID
# 在线程 Dump 中搜索对应的线程
grep "nid=0xHEX_ID" thread_dump.txt -A 30
# 5. 网络连接问题
# 查看进程的所有连接
ss -tnp | grep $(pidof myapp)
# 查看连接状态分布
ss -tan | awk '{print $1}' | sort | uniq -c | sort -rn8. Docker 常用命令和最佳实践是什么?
# 容器管理
docker run -d --name myapp -p 8080:80 nginx:latest # 后台运行容器
docker ps -a # 查看所有容器
docker logs -f myapp # 查看容器日志
docker exec -it myapp bash # 进入容器
docker stop myapp && docker rm myapp # 停止并删除容器
# 镜像管理
docker build -t myapp:1.0 . # 构建镜像
docker images # 查看镜像列表
docker rmi myapp:1.0 # 删除镜像
docker push registry/myapp:1.0 # 推送镜像到仓库
# Docker Compose
docker-compose up -d # 启动所有服务
docker-compose down # 停止并删除所有服务
docker-compose logs -f api # 查看服务日志
docker-compose restart api # 重启服务
# 清理
docker system prune -a # 清理未使用的容器、镜像、网络
docker volume prune # 清理未使用的卷7-15. 更多 Linux/运维面试题简答
9. 什么是 inode? inode 是 Linux 文件系统的索引节点,存储文件的元数据(权限、所有者、大小、时间戳、数据块位置),但不包含文件名。文件名存储在目录项中。df -i 查看 inode 使用情况。inode 耗尽(小文件过多)会导致"磁盘空间还有但无法创建新文件"的问题。解决方法:删除无用小文件或重新格式化文件系统增加 inode 数量。
10. 什么是软链接和硬链接? 软链接(符号链接)是指向文件路径的指针,删除源文件后失效;硬链接是指向 inode 的指针,与源文件共享数据块,删除源文件不影响硬链接。硬链接不能跨文件系统。实际使用场景:软链接用于版本切换(如 current -> releases/v1.2.3),硬链接用于节省磁盘空间(如备份工具 Borg 使用硬链接去重)。
11. 如何查看系统日志? /var/log/syslog(Ubuntu)或 /var/log/messages(CentOS)是系统主日志;journalctl 查看 systemd 日志(journalctl -u nginx --since "1 hour ago");dmesg 查看内核日志(硬件和驱动问题);/var/log/nginx/ 等是应用日志。日志轮转由 logrotate 管理,配置在 /etc/logrotate.d/。
12. crontab 如何使用? crontab -e 编辑定时任务。格式:分 时 日 月 周 命令。例如 0 2 * * * /path/backup.sh 每天凌晨 2 点执行备份。*/5 * * * * 表示每 5 分钟。0 9 * * 1-5 表示工作日早上 9 点。注意事项:crontab 环境变量与交互式 Shell 不同,建议在脚本开头 source /etc/profile;输出默认发邮件,建议重定向到日志文件。
13. 如何查看和分析系统性能? sar 收集系统活动报告(需要 sysstat 包);perf 分析 CPU 性能热点函数;strace 跟踪系统调用(排查启动失败和 I/O 问题);lsof 查看打开的文件(排查文件被占用无法删除的问题)。综合使用这些工具定位性能瓶颈。
14. SSH 密钥认证如何配置? ssh-keygen -t ed25519 生成密钥对;将公钥复制到远程主机的 ~/.ssh/authorized_keys(可用 ssh-copy-id user@host);设置权限 600(密钥)和 644(公钥),目录 700(~/.ssh/)。安全加固:禁用密码登录(PasswordAuthentication no),禁用 root 登录(PermitRootLogin no),使用 fail2ban 防暴力破解。
15. 什么是 Swap?如何管理? Swap 是磁盘上的虚拟内存空间,当物理内存不足时使用。使用 swapon --show 查看,swapoff -a && swapon -a 重置。swappiness 参数(/proc/sys/vm/swappiness)控制使用倾向:值越低越倾向保留内存数据(数据库服务器建议设为 1-10),值越高越积极使用 Swap。创建 Swap 文件:fallocate -l 4G /swapfile && chmod 600 /swapfile && mkswap /swapfile && swapon /swapfile。
16. 如何配置防火墙? CentOS 使用 firewalld(zone 概念),Ubuntu 使用 ufw。生产环境建议:默认拒绝入站、只开放必要端口、使用白名单 IP、配置连接速率限制。例如 ufw 配置:ufw default deny incoming && ufw allow 22/tcp && ufw allow 80,443/tcp && ufw enable。注意:配置防火墙前确保 SSH 端口已开放,避免锁死自己。
17. 什么是 systemd? systemd 是 Linux 的初始化系统和服务管理器,替代传统的 init.d。通过 .service 文件定义服务,支持依赖管理、并行启动、日志管理(journald)和定时器(timer)等功能。自定义服务文件放在 /etc/systemd/system/,修改后执行 systemctl daemon-reload 重载。
进阶运维脚本示例
#!/bin/bash
# 自动化日志清理脚本
LOG_DIR="/var/log/app"
RETENTION_DAYS=30
ARCHIVE_DIR="/var/log/archive"
# 创建归档目录
mkdir -p "$ARCHIVE_DIR"
# 压缩超过 7 天的日志
find "$LOG_DIR" -name "*.log" -mtime +7 -type f | while read -r file; do
gzip -c "$file" > "$ARCHIVE_DIR/$(basename "$file").$(date +%Y%m%d).gz"
truncate -s 0 "$file"
echo "[$(date)] 已压缩: $file"
done
# 删除超过保留天数的归档
find "$ARCHIVE_DIR" -name "*.gz" -mtime +$RETENTION_DAYS -delete
echo "[$(date)] 已清理超过 ${RETENTION_DAYS} 天的归档"
# 检查磁盘空间
usage=$(df -h "$LOG_DIR" | awk 'NR==2{print $5}' | sed 's/%//')
if [ "$usage" -gt 80 ]; then
echo "[WARN] 磁盘使用率: ${usage}%,请及时清理"
fi#!/bin/bash
# 进程监控与自动重启脚本
PROCESS_NAME="myapp"
MAX_RESTART=3
RESTART_INTERVAL=60
LOG_FILE="/var/log/process_monitor.log"
restart_count=0
while true; do
if ! pgrep -f "$PROCESS_NAME" > /dev/null; then
echo "[$(date)] 检测到 $PROCESS_NAME 已停止" >> "$LOG_FILE"
if [ "$restart_count" -lt "$MAX_RESTART" ]; then
echo "[$(date)] 正在重启 $PROCESS_NAME (第 $((restart_count+1)) 次)" >> "$LOG_FILE"
systemctl restart "$PROCESS_NAME"
restart_count=$((restart_count + 1))
# 重启后检查
sleep 10
if pgrep -f "$PROCESS_NAME" > /dev/null; then
echo "[$(date)] 重启成功" >> "$LOG_FILE"
else
echo "[$(date)] 重启失败" >> "$LOG_FILE"
fi
else
echo "[$(date)] 已达到最大重启次数,发送告警" >> "$LOG_FILE"
# 发送告警通知
# echo "$PROCESS_NAME 连续重启失败" | mail -s "进程告警" admin@example.com
break
fi
else
restart_count=0 # 进程正常运行时重置计数
fi
sleep "$RESTART_INTERVAL"
done优点
缺点
总结
Linux/运维面试需要展示对系统管理的全面理解和故障排查能力。重点掌握文件系统操作、权限管理、进程管理、网络排查和 Shell 脚本编写。建议通过实际操作(搭建服务器、部署应用、排查问题)积累经验,在面试中结合实际案例展示系统化的问题解决思路。
这组题真正考什么
- 这类题真正想看的是你能否支撑稳定交付,而不是只会敲命令。
- 高频追问一般会落到回滚、审计、权限、监控和灾备。
- 如果答案里有完整链路,通常比零散命令更打动人。
60 秒答题模板
- 先说目标和场景。
- 再说关键流程和涉及的工具。
- 最后补失败恢复、监控和回滚方案。
容易失分的点
- 只讲部署成功,不讲失败恢复。
- 把测试环境经验直接当成生产最佳实践。
- 没有说明权限和审计控制。
刷题建议
- 把发布链路拆成代码、构建、制品、环境、监控五段来记。
- 练习时多说回滚、审计、权限和故障恢复,不要只讲部署成功路径。
- 每类工具都准备一个实际落地案例。
高频追问
- 如果发布失败或监控报警,你会如何快速止损?
- 这个工具或方案如何保证幂等、可观测和可回滚?
- 在多人协作和多环境下,最大的治理难点是什么?
复习重点
- 把每道题的关键词整理成自己的知识树,而不是只背原句。
- 对容易混淆的概念要做横向比较,例如机制差异、适用边界和性能代价。
- 复习时优先补“为什么”,其次才是“怎么用”和“记住什么术语”。
面试作答提醒
- 回答运维题时,优先交代目标、流程、风险和回滚。
- 不要把测试环境经验直接当成生产最佳实践。
- 提到自动化时,最好补一条审计或权限控制措施。
