AI Infra 训练营
总览
  • 总览
  • 完整安装
  • 核心 K8s
  • Cilium 网络
  • Longhorn 存储
  • 监控日志
  • CI / GitOps
  • 安全准入
  • CI/CD 实战(MySQL+Go+Vue)
  • HPA/Ingress/Hubble 实战
  • 面试速查 + 真实踩坑
  • Day 0 · 新手接管 Runbook
  • Day 1 · 集群起步 + CNI
  • Day 2 · 控制面 + etcd
  • Day 3 · CRD + Operator + Webhook
  • Day 4 · 存储深度
  • Day 5 · 卷扩容 + 安全
  • Day 6 · 调度 + 可观测
  • Day 7 · Harbor + ArgoCD + Mesh
  • Day 8 · AI Infra
  • Day 9 · Triton + GPU
  • Day 10 · MIG + HPA + 量化
  • Day 11 · AI Agent 端到端
  • Day 12 · 灾备
  • Day 13 · Operator + 联邦 + Mesh + RAG
  • Day 14 · CKA / CKS + 总结
  • LLM 训练手册
  • RAG + Agent 手册
  • 推理优化手册
  • 上下文工程手册
  • Agent 开发手册
  • 面试深度复盘
  • 训练 v2 深度手册
  • 心智模型
  • 看懂命令输出
  • 容器网络底层
  • K8s 网络深入
  • DNS 全套
  • 故障排查方法论
  • 心智模型
  • 容器挂载完整指南
  • K8s Volumes 大全
  • PV/PVC/CSI 深入
  • NFS 深入
  • 分布式存储概览
  • 故障排查 runbook
命令手册
HiHuo 主站
GitHub
总览
  • 总览
  • 完整安装
  • 核心 K8s
  • Cilium 网络
  • Longhorn 存储
  • 监控日志
  • CI / GitOps
  • 安全准入
  • CI/CD 实战(MySQL+Go+Vue)
  • HPA/Ingress/Hubble 实战
  • 面试速查 + 真实踩坑
  • Day 0 · 新手接管 Runbook
  • Day 1 · 集群起步 + CNI
  • Day 2 · 控制面 + etcd
  • Day 3 · CRD + Operator + Webhook
  • Day 4 · 存储深度
  • Day 5 · 卷扩容 + 安全
  • Day 6 · 调度 + 可观测
  • Day 7 · Harbor + ArgoCD + Mesh
  • Day 8 · AI Infra
  • Day 9 · Triton + GPU
  • Day 10 · MIG + HPA + 量化
  • Day 11 · AI Agent 端到端
  • Day 12 · 灾备
  • Day 13 · Operator + 联邦 + Mesh + RAG
  • Day 14 · CKA / CKS + 总结
  • LLM 训练手册
  • RAG + Agent 手册
  • 推理优化手册
  • 上下文工程手册
  • Agent 开发手册
  • 面试深度复盘
  • 训练 v2 深度手册
  • 心智模型
  • 看懂命令输出
  • 容器网络底层
  • K8s 网络深入
  • DNS 全套
  • 故障排查方法论
  • 心智模型
  • 容器挂载完整指南
  • K8s Volumes 大全
  • PV/PVC/CSI 深入
  • NFS 深入
  • 分布式存储概览
  • 故障排查 runbook
命令手册
HiHuo 主站
GitHub
  • 命令手册总览
  • SSH 与远程执行

    • ssh —— 远程登录与远程执行
    • ssh-config —— ~/.ssh/config 客户端配置文件
    • ssh-keygen —— 密钥对生成与 known_hosts 维护
    • sshd —— SSH 服务端守护进程与硬化
    • sshpass —— 密码登录自动化(仅限"首次推 key"场景)
    • scp / rsync —— 远程文件拷贝
    • nsenter —— 进入 Linux namespace 的"传送门"
  • 系统状态与诊断

    • systemd-detect-virt —— 探测当前运行环境的虚拟化类型
    • systemctl —— systemd 服务管理的总入口
    • journalctl —— systemd 日志查询
    • hostnamectl / timedatectl —— 改主机名与时区
    • ss —— socket statistics(替代 netstat)
    • lsblk / df / du —— 三个被混淆的"看磁盘"命令
  • 进程与资源

    • ps —— 看进程
    • top / htop —— 实时进程资源监控
    • lsof —— 列出打开的文件(list open files)
    • strace —— 系统调用追踪
    • dmesg —— 看内核环形缓冲日志
    • iostat —— 磁盘 I/O 性能分析
    • iotop —— 进程级 I/O 实时监控
  • 文本与文件批处理

    • grep —— 文本搜索
    • sed —— 流编辑器
    • awk —— 按字段处理文本
    • jq —— JSON 命令行处理器
    • find —— 按各种条件找文件
    • xargs —— 把 stdin 喂给下一个命令
    • tee —— 一边输出、一边写文件
  • 磁盘与存储

    • mount / umount —— 挂载文件系统
    • mkfs —— 格式化文件系统
    • /etc/fstab —— 持久化挂载配置
    • parted / fdisk —— 分区表管理
    • LVM —— pvcreate / vgcreate / lvcreate 三件套
    • findmnt —— 现代化的"看挂载"命令
    • nfsstat / showmount —— NFS 状态与性能
    • smartctl —— 盘健康检查与坏盘预警
  • 网络诊断

    • curl —— HTTP 客户端的瑞士军刀
    • ip —— 现代 Linux 网络配置工具(替代 ifconfig / route)
    • iptables —— Linux 内核包过滤 / NAT 规则
    • tcpdump —— 命令行抓包
    • dig —— DNS 查询工具
    • mtr —— traceroute + ping 合体
    • iperf3 —— 网络带宽测试
    • nc (netcat) —— 网络瑞士军刀
    • ethtool —— 物理网卡参数 / 速率 / offload
  • 内核 / 包管理 / 时间

    • modprobe / lsmod —— 内核模块加载
    • sysctl —— 内核运行时参数
    • apt / apt-get / dpkg —— Debian / Ubuntu 包管理
    • chrony / chronyc —— NTP 时间同步
  • K8s / 容器工具链

    • kubectl —— K8s 的瑞士军刀
    • kubeadm —— K8s 集群引导工具
    • helm —— K8s 应用包管理器
    • crictl —— 容器运行时命令行(CRI 层)
    • etcdctl —— 直连 K8s 元数据存储
    • docker —— 单机容器(构建和本地开发)
  • 监控 / GitOps / 备份

    • argocd —— GitOps CLI
    • velero —— K8s 集群备份恢复
    • prometheus / promtool —— 监控数据查询和工具
    • cilium / cilium-cli / hubble —— eBPF CNI 排错
    • grafana / grafana-cli —— 可视化平台运维
    • alertmanager / amtool —— 告警分组、抑制、路由
  • 开发 / 构建 / 终端

    • git —— 版本控制 + GitOps 的底座
    • make / Makefile —— 任务编排
    • openssl —— 证书 / 密钥 / TLS 调试工具箱
    • tmux —— 终端复用 / 长跑任务防掉线
    • vim —— 远程编辑必备最小集
    • cron / crontab —— 定时任务

tee —— 一边输出、一边写文件

一句话定义

tee 把 stdin 同时输出到 stdout(屏幕)+ 写入文件。名字来自 T 字形管道——一进、二出。在脚本里"看着跑 + 留日志"是它的核心场景。

典型场景

  • 看长跑命令的输出 + 同时写日志:cmd | tee log.txt
  • sudo 写权限:echo "..." | sudo tee /etc/x.conf
  • 同时写多个文件
  • 流式追加(K8s 装机脚本里很常见)

基础

echo "hello" | tee file.txt
# 屏幕显示 hello
# file.txt 内容 = hello
# 写多个文件
echo "hello" | tee file1.txt file2.txt file3.txt
# 实时看长跑 + 留日志
make build | tee build.log
helm install ... | tee install.log

-a 追加(不是覆盖)

echo "line1" | tee file.txt                       # 覆盖
echo "line2" | tee -a file.txt                    # 追加

-a = append,类似 >>。

cat file.txt
# line1
# line2

sudo tee —— 写需要 root 权限的文件

经典坑:

sudo echo "x" > /etc/some.conf
# bash: /etc/some.conf: Permission denied

echo 有 sudo 权限、但 > 是 shell 在做(非 root shell),还是被拒。

修:

echo "x" | sudo tee /etc/some.conf
# tee 拿到 sudo 权限、写文件 OK
# 同时屏幕也显示 "x"

echo "x" | sudo tee -a /etc/some.conf             # 追加
echo "x" | sudo tee /etc/some.conf > /dev/null    # 不要屏幕回显

这是 tee 在运维场景的最主要用法。


写到 stderr(少见但有用)

echo "warning" | tee /dev/stderr | grep -v xxx
# tee 同时把 warning 输出到 stderr
# stdout 继续往下游 grep

-i 忽略 SIGINT

long-command | tee log.txt
# Ctrl-C → tee 也死、可能丢最后一行
long-command | tee -i log.txt
# tee 忽略 SIGINT,让上游 command 自己处理 Ctrl-C

主要用于"长跑命令 + 想保证日志写完整"。


实战例子

1. 装机脚本里"写配置 + 显示"

cat <<'EOF' | sudo tee /etc/sysctl.d/99-k8s.conf
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1
EOF
# 配置写进去了、屏幕也显示了一遍(提供 audit trail)

2. 跑测试 + 留日志

make test | tee test-$(date +%F).log

或者并行:

make test 2>&1 | tee test.log                     # stderr 也捕获

3. K8s 部署 + 留 trail

helm upgrade -i my-app ./chart -f values.yaml 2>&1 | tee deploy.log
# 既看屏幕、又留 deploy.log 排查

4. 给追加配置 + 显示

echo "Host m1" | sudo tee -a ~/.ssh/config
# 屏幕显示 + 追加到 config

5. 接管 ssh 的输出

ssh m1 'kubectl get pods -A' | tee pods-snapshot.txt
# 把远端命令输出留本地

6. 中间观察 + 不影响管道

kubectl get pods | tee /tmp/pods.txt | grep -c Running
# 既看到完整列表保存到文件、又能继续 grep 计数

tee 在中间是透明的——不改变管道数据流。

7. 同时写本地 + 远程文件

echo "log entry" | tee >(ssh m1 'cat >> /var/log/remote.log') >> /var/log/local.log
# 进程替换 + tee 同时本地 + ssh 远程

复杂但能用。


进程替换 >(...) 配合 tee

echo "data" | tee >(command1) >(command2) > output.txt
# tee 把 data 同时给:
#   - command1 的 stdin
#   - command2 的 stdin
#   - output.txt 文件

K8s 经典:同时给多个处理器:

journalctl -u kubelet -f \
  | tee >(grep ERROR > errors.log) \
        >(grep WARN > warns.log) \
        > all.log

一份 stdin、三路输出。


常见踩坑

坑 1:> 没 sudo 权限

sudo echo "x" > /etc/x.conf
# Permission denied

经典错误。改 tee:

echo "x" | sudo tee /etc/x.conf

坑 2:默认覆盖、想追加忘加 -a

echo "line1" | tee file.txt
echo "line2" | tee file.txt                       # ❌ 覆盖了 line1
echo "line2" | tee -a file.txt                    # ✅

坑 3:stderr 没捕获

make build | tee build.log
# 但 build error 没在 log 里(错误走 stderr)
make build 2>&1 | tee build.log
# 2>&1 把 stderr 合并到 stdout

坑 4:管道在 strict mode 行为

set -o pipefail
fails-cmd | tee log
# tee 成功 → 整个管道退出码看 fails-cmd

pipefail 让管道任一失败就整体失败。tee 总是 0、是中性的。

坑 5:写多个文件、权限不同

echo "x" | sudo tee /etc/file1 /home/user/file2
# /etc/file1 owner = root(OK)
# /home/user/file2 owner = root(用户的家、不应该 root 拥有)

要分两步:

echo "x" | sudo tee /etc/file1
echo "x" | tee /home/user/file2

坑 6:tee 输出到 fifo / pipe 卡住

cmd | tee >(slow-consumer)
# tee 写到 slow-consumer 慢、整个管道卡

>(...) 子进程慢会反向 backpressure。要异步:

cmd | tee >(slow-consumer &)

或者用文件中转。

坑 7:tee 不能进容器 / 不能 ssh

echo "x" | tee | ssh m1 "cat >> /etc/file"
# 这里 tee 没意义、可以直接 |

tee 的价值是同时写文件 + 继续管道。单纯传输用 | 或 ssh ... < /file。


关联命令

  • > / >> —— shell 自带 redirect(写一个文件、不显示)
  • script —— 录制整个 shell session(更全面的"tee")
  • xargs —— xargs 之后 tee 留日志
  • mktemp —— 配合 tee 写临时文件
  • multitail —— 同时跟多个日志
在 GitHub 上编辑此页
Prev
xargs —— 把 stdin 喂给下一个命令