SSH 完整指南:免密碼登入、金鑰管理、SSH 通道

SSH 如何運作?

SSH(Secure Shell)使用非對稱加密確保連線安全:

  你的電腦                       遠端伺服器
  ┌──────────────┐               ┌──────────────────┐
  │  私鑰(保密!)│               │  公鑰(可公開)   │
  │  id_ed25519  │               │  authorized_keys │
  └──────────────┘               └──────────────────┘
         │                              │
         └──────── SSH 握手協議 ─────────┘
                  1. 伺服器傳送挑戰
                  2. 客戶端用私鑰簽名
                  3. 伺服器用公鑰驗證
                  ✅ 驗證通過,建立加密通道

基本連線

$ ssh 使用者名稱@伺服器IP
$ ssh alice@192.168.1.100         # 密碼登入
$ ssh -p 2222 alice@server.com    # 指定 port(不是 22)
$ ssh alice@server "df -h && free -h"  # 執行單一指令

產生 SSH 金鑰對

推薦使用 Ed25519 演算法(現代、安全、速度快):

$ ssh-keygen -t ed25519 -C "alice@my-computer"
Generating public/private ed25519 key pair.
Enter file in which to save the key (~/.ssh/id_ed25519): (按 Enter 用預設路徑)
Enter passphrase (empty for no passphrase): (可設定密語,多一層保護)
Your identification has been saved in /home/alice/.ssh/id_ed25519
Your public key has been saved in /home/alice/.ssh/id_ed25519.pub

產生後你有兩個檔案:

$ cat ~/.ssh/id_ed25519.pub   # 查看公鑰
ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGO... alice@my-computer

複製公鑰到伺服器(免密碼登入)

方法一:使用 ssh-copy-id(最簡單)

$ ssh-copy-id alice@192.168.1.100
/usr/bin/ssh-copy-id: INFO: Source of key(s) to be installed: "~/.ssh/id_ed25519.pub"
alice@192.168.1.100's password: (最後一次輸入密碼)
Number of key(s) added: 1

Now try logging into the machine: ssh 'alice@192.168.1.100'
$ ssh alice@192.168.1.100   # 現在不需要密碼了!

方法二:手動複製(沒有 ssh-copy-id 時)

$ cat ~/.ssh/id_ed25519.pub | ssh alice@server "mkdir -p ~/.ssh && chmod 700 ~/.ssh && cat >> ~/.ssh/authorized_keys && chmod 600 ~/.ssh/authorized_keys"

設定 ~/.ssh/config(省去大量打字)

每次連線都要輸入一長串的指令很麻煩。~/.ssh/config 讓你定義別名:

$ vim ~/.ssh/config
# 生產伺服器
Host prod
    HostName production.example.com
    User deploy
    Port 2222
    IdentityFile ~/.ssh/id_ed25519

# 開發伺服器
Host dev
    HostName 192.168.1.100
    User alice
    IdentityFile ~/.ssh/id_ed25519

# 跳板機設定(需要透過 jump 連到 target)
Host target
    HostName 10.0.0.10
    User admin
    ProxyJump jump-server.com

# 常用設定(套用到所有主機)
Host *
    ServerAliveInterval 60   # 每 60 秒發送保持連線封包
    ServerAliveCountMax 3
    AddKeysToAgent yes       # 自動把金鑰加到 agent
$ chmod 600 ~/.ssh/config   # 確保設定檔權限正確

之後就可以這樣連線:

$ ssh prod     # 等同於 ssh -p 2222 -i ~/.ssh/id_ed25519 deploy@production.example.com

SSH 通道(Port Forwarding)

SSH 通道是 SSH 最強大的進階功能之一,可以安全地轉發 port:

本地 Port Forwarding(最常用)

將遠端的資料庫 port 轉到本機,讓本機程式可以「直接」連遠端資料庫:

$ ssh -N -L 5432:localhost:5432 alice@server

說明:-L 本機port:遠端主機:遠端port

實際場景:存取只對內開放的後台管理介面

$ ssh -N -L 8080:localhost:8080 alice@server
# 然後打開瀏覽器到 http://localhost:8080

遠端 Port Forwarding

讓外界可以透過伺服器連到你的本機(常用於臨時分享開發中的服務):

$ ssh -N -R 8080:localhost:3000 alice@server

外界訪問 server:8080 就等同於訪問你電腦的 localhost:3000。

檔案傳輸:scp 與 rsync

scp:簡單傳輸

$ scp report.pdf alice@server:/home/alice/  # 上傳
$ scp alice@server:/var/log/app.log .      # 下載
$ scp -r ./project/ alice@server:/var/www/ # 遞迴上傳目錄

rsync:高效同步(更推薦)

$ rsync -avz --delete ./dist/ alice@prod:/var/www/html/

rsync 的優勢:只傳輸差異的部分,大幅節省時間和流量。

SSH 安全加固

在設定好金鑰登入後,建議加強 SSH 安全性:

$ sudo vim /etc/ssh/sshd_config
# 建議的安全設定

# 1. 禁止 root 直接 SSH 登入
PermitRootLogin no

# 2. 禁止密碼登入(只允許金鑰)
PasswordAuthentication no

# 3. 限制可登入的使用者
AllowUsers alice deploy

# 4. 變更預設 port(偽安全,減少自動掃描)
Port 2222

# 5. 限制登入嘗試次數
MaxAuthTries 3

# 6. 閒置連線逾時
ClientAliveInterval 300
ClientAliveCountMax 2
$ sudo systemctl reload sshd   # 套用設定
⚠️ 在關閉密碼登入(PasswordAuthentication no)之前,務必先確認你的金鑰可以正常登入,並且保持另一個 SSH session 連線,防止設定錯誤後被鎖在外面。