Chapter 08 · 树莓派与嵌入式 Linux

网络与 SSH 远程

树莓派多半是"无头"运行——插电就藏进角落。学会 SSH 密钥登录、固定 IP、传文件、远程桌面和内网穿透,从任何地方安全地掌控它。

课程进度67%

关键概念

SSH(安全外壳协议)
Secure Shell,通过加密通道远程登录并执行命令的标准协议,默认 22 端口。ssh pi@raspberrypi.local 即可进入树莓派的命令行,所有流量加密。它是无头树莓派的生命线——不用接显示器键盘,从笔记本就能全权操控。
密钥对认证(公钥/私钥)
比密码更安全的登录方式。你生成一对密钥:私钥留在本机(绝不外泄),公钥放到树莓派的 ~/.ssh/authorized_keys。登录时靠非对称加密验证身份,免密码、抗暴力破解。配好后可禁用密码登录,安全性大增。
静态 IP vs DHCP
默认树莓派用 DHCP 自动从路由器获取 IP,但每次可能变,不利于长期远程。设静态 IP(固定地址)后 SSH 目标永远不变。bookworm 用 NetworkManager(nmcli)配置,取代了旧的 dhcpcd.conf。也可在路由器里绑定 MAC→IP。
主机名与 mDNS(.local)
主机名是设备在网络上的名字(默认 raspberrypi)。借助 mDNS(Avahi 服务),同一局域网内可用 raspberrypi.local 直接访问,无需记 IP。改主机名用 hostnamectl set-hostname,多台树莓派务必改成不同名字避免冲突。
SCP / SFTP / rsync
在本机与树莓派间传文件的工具,都走 SSH 加密通道。scp 简单拷贝单个文件/目录;sftp 交互式文件管理;rsync 增量同步(只传变化部分,适合大目录和反复部署)。部署代码到树莓派靠它们。
VNC 远程桌面
SSH 给命令行,VNC 给图形桌面。启用后可在电脑上看到并操作树莓派的完整桌面环境,适合需要 GUI 的场景(浏览器、图形化配置)。树莓派用 RealVNC/wayvnc,raspi-config 一键开启。日常运维优先 SSH,GUI 才用 VNC。
防火墙 ufw
Uncomplicated Firewall,Linux 上简单易用的防火墙前端。用 ufw allow 22 放行端口、ufw deny 拒绝,控制哪些端口可被外部访问。暴露到公网的树莓派务必开防火墙,只放行必要端口(SSH、Web),关闭其余,减少攻击面。
内网穿透与端口转发
树莓派在家庭内网(私有 IP),公网无法直接访问。要从外网连回,可在路由器做端口转发(有安全风险),或用内网穿透工具(Tailscale/frp/Cloudflare Tunnel)建立安全隧道,无需公网 IP、无需改路由器,更安全。Tailscale 基于 WireGuard,配置最省心。

网络访问全景

从"同一房间"到"地球另一端",访问树莓派有三个层次,安全性与复杂度递增:

远程访问树莓派的三个层次 ═══════════════════════════════════════════════════════════════ ① 局域网内(最简单) 笔记本 ──同一 WiFi/网线──► 树莓派 ssh pi@raspberrypi.local 或 ssh pi@192.168.1.50 适合:家里、办公室,设备同网段 ② 内网穿透(推荐,安全) 笔记本 ──► Tailscale/Cloudflare 隧道 ──► 树莓派 双方装客户端,组虚拟局域网,走加密隧道 适合:出门在外访问家里的派,无需公网IP/改路由器 ③ 端口转发(有风险,慎用) 公网 ──► 路由器(开放22端口) ──► 树莓派 直接把 SSH 暴露公网,会被全球扫描爆破! 必须:密钥登录 + 改端口 + fail2ban + 防火墙

SSH 密钥登录:告别密码

密码可被暴力破解,密钥对是黄金标准。在本机(不是树莓派)生成密钥,把公钥传给树莓派:

# === 在本机(Mac/Linux/Windows)生成密钥对 ===
ssh-keygen -t ed25519 -C "my-laptop"
# 一路回车(默认存 ~/.ssh/id_ed25519,可设密码短语加固)
# 生成两个文件:id_ed25519(私钥,保密) id_ed25519.pub(公钥,可公开)

# === 把公钥拷到树莓派(一条命令搞定)===
ssh-copy-id pi@raspberrypi.local
# 输入一次密码后,公钥自动写入树莓派 ~/.ssh/authorized_keys

# === 之后免密码登录 ===
ssh pi@raspberrypi.local
# 直接进入,无需密码(私钥自动完成认证)

# 若 ssh-copy-id 不可用(如 Windows),手动追加:
cat ~/.ssh/id_ed25519.pub | ssh pi@raspberrypi.local "mkdir -p ~/.ssh && cat >> ~/.ssh/authorized_keys"

密钥能用后,在树莓派上禁用密码登录,彻底堵住暴力破解:

# 编辑 SSH 服务端配置
sudo nano /etc/ssh/sshd_config

# 找到并修改这几行(去掉行首 # 并改值):
#   PasswordAuthentication no      ← 禁用密码登录
#   PubkeyAuthentication yes       ← 允许密钥
#   PermitRootLogin no             ← 禁止 root 直接登录

# 重启 SSH 服务生效
sudo systemctl restart ssh
# ⚠️ 改前务必确认密钥能登录,否则会把自己锁在门外!
用 ~/.ssh/config 简化登录

在本机 ~/.ssh/config 里给树莓派起别名,就不用每次敲长命令。写入:Host pi /   HostName 192.168.1.50 /   User pi /   Port 22。之后一句 ssh pi 即可登录。多台设备各起别名,管理清爽。

设置静态 IP(NetworkManager)

bookworm 起用 NetworkManager 管理网络,静态 IP 用 nmcli 配置(旧教程的 dhcpcd.conf 已不适用):

# 查看当前连接名(通常是 "Wired connection 1" 或 WiFi 名)
nmcli connection show

# 给有线连接设静态 IP(示例网段 192.168.1.x)
sudo nmcli connection modify "Wired connection 1" \
    ipv4.method manual \
    ipv4.addresses 192.168.1.50/24 \
    ipv4.gateway 192.168.1.1 \
    ipv4.dns "192.168.1.1 8.8.8.8"

# 重新激活连接使配置生效
sudo nmcli connection up "Wired connection 1"

# 验证 IP 已固定
ip addr show      # 或 hostname -I

改主机名(多台派务必区分):

# 改主机名为 pi-livingroom
sudo hostnamectl set-hostname pi-livingroom
# 重启后即可用 pi-livingroom.local 访问
sudo reboot

传文件:scp / rsync

把本机代码部署到树莓派,或把树莓派上的日志/照片拉回来:

# === scp:单次拷贝 ===
# 本机 → 树莓派(上传单个文件)
scp app.py pi@raspberrypi.local:/home/pi/project/

# 本机 → 树莓派(-r 递归传整个目录)
scp -r ./myproject pi@raspberrypi.local:/home/pi/

# 树莓派 → 本机(下载,注意顺序反过来)
scp pi@raspberrypi.local:/home/pi/photo.jpg ./

# === rsync:增量同步(推荐,反复部署高效)===
# -a 保留属性 -v 显示进度 -z 压缩传输 --delete 删除目标多余文件
rsync -avz ./myproject/ pi@raspberrypi.local:/home/pi/myproject/

# 只同步 .py 文件,排除缓存和虚拟环境
rsync -avz --exclude='__pycache__' --exclude='env' \
    ./myproject/ pi@raspberrypi.local:/home/pi/myproject/
开发工作流:本机写代码,rsync 推到派

树莓派上写代码体验差(性能弱、无好用编辑器)。推荐在本机用 VS Code 写,用 rsync 或 VS Code 的 Remote-SSH 插件(直接在本地编辑器里操作远程文件、开远程终端)同步到树莓派运行。Remote-SSH 体验最佳:装插件、连 pi@raspberrypi.local,就像编辑本地文件一样。

VNC 远程桌面

需要图形界面时(如调试摄像头预览、用浏览器),开启 VNC:

# 方式一:raspi-config 图形菜单启用
sudo raspi-config
# → 3 Interface Options → VNC → Yes

# 方式二:命令行一键启用
sudo raspi-config nonint do_vnc 0

# 查看树莓派 IP,供 VNC 客户端连接
hostname -I

然后在本机装 RealVNC Viewer,输入 raspberrypi.local 或 IP 即可看到桌面。若是无显示器的 headless 派,需在 /boot/firmware/config.txt 设虚拟分辨率,否则桌面尺寸异常。

防火墙 ufw:只开必要端口

联网的树莓派应开防火墙,遵循"默认拒绝,按需放行"原则:

# 安装 ufw
sudo apt install -y ufw

# 默认策略:拒绝所有入站,允许所有出站
sudo ufw default deny incoming
sudo ufw default allow outgoing

# 放行必要端口(⚠️ 先放 SSH,否则开防火墙就断连!)
sudo ufw allow 22/tcp        # SSH
sudo ufw allow 1883/tcp      # MQTT(第11章要用)
sudo ufw allow 8000/tcp      # 自己的 Web 服务

# 只允许特定网段访问(更严格)
sudo ufw allow from 192.168.1.0/24 to any port 22

# 启用防火墙
sudo ufw enable

# 查看规则状态
sudo ufw status verbose

内网穿透:Tailscale 最省心

出门在外访问家里树莓派,Tailscale(基于 WireGuard)无需公网 IP、不用改路由器、自动加密打洞:

# 在树莓派上安装 Tailscale
curl -fsSL https://tailscale.com/install.sh | sh

# 登录(会给一个链接,浏览器授权)
sudo tailscale up

# 查看分配到的 Tailscale IP(100.x.x.x 网段)
tailscale ip -4

在你的手机/笔记本也装 Tailscale 并登录同一账号,双方就组成虚拟局域网。之后无论在哪,都能用 ssh pi@100.x.x.x 安全连回树莓派,像在同一房间一样。

远程方案需公网IP需改路由器安全性适用场景
局域网直连同网段(家/办公室)
Tailscale高(WireGuard)异地访问,首选
Cloudflare Tunnel暴露 Web 服务
frp 自建需云服务器看配置有 VPS,要完全掌控
路由器端口转发低(易被爆破)不推荐
切勿裸奔把 SSH 暴露公网

直接在路由器把 22 端口转发到公网,几分钟内就会被全球僵尸网络扫描爆破。若非要开放公网 SSH,至少做到:① 只用密钥登录、禁用密码;② 改默认端口(如 2222,减少扫描噪音);③ 装 fail2ban(多次失败自动封 IP);④ 开 ufw 只放行必要来源。更好的选择永远是 Tailscale 等内网穿透,根本不暴露端口到公网。

本章小结

无头树莓派靠远程访问掌控。SSH 是命令行生命线,务必配密钥对登录ssh-keygen 生成、ssh-copy-id 上传公钥)并在 sshd_config禁用密码登录;用 ~/.ssh/config 起别名简化。静态 IP 用 bookworm 的 nmcli 配置(不再是 dhcpcd.conf),或改主机名用 .local 访问。传文件用 scp(单次)或 rsync(增量高效);开发推荐本机 VS Code + Remote-SSH。需要图形界面开 VNC。联网必开ufw 防火墙(默认拒绝、只放行 SSH/MQTT/Web,先放 22 再 enable)。异地访问首选 Tailscale 内网穿透(WireGuard 加密、免公网 IP),绝不裸奔把 SSH 暴露公网。下一章我们让程序开机自启、常驻后台——systemd 服务。