筆者在前文《Windows 支持 OpenSSH 了!》中介紹了 Windows 對 OpenSSH 支持的基本內容,本文在前文的基礎上介紹一些 OpenSSH Server 的配置和常見用法。
以域用戶身份登錄
之前我們介紹了如何通過 Windows 本地用戶的方式登錄遠程主機,下面看看如何以 Windows 域用戶的方式登錄:
> ssh domain\nickli@xa-crab > ssh nickli@domain@xa-crab > ssh -l nickli@domain xa-crab
上面的三種方式都可以通過域用戶的身份登錄的遠程主機。個人比較喜歡第一種,第三種方式中的 -l 選項用來指定登錄者的賬號。
配置域用戶通過公鑰認證登錄的方式與本地用戶相同,請參考《Windows 支持 OpenSSH 了!》一文。
控制哪些用戶和組可以連接到服務器
通過在 OpenSSH 服務的配置文件中添加 AllowGroups、AllowUsers、DenyGroups 和 DenyUsers 指令可以控制哪些用戶和組可以連接到服務器。這些指令被處理的順序為:DenyUsers、AllowUsers、DenyGroups,最后是 AllowGroups。這一點非常重要,如果我們只設置了一條 AllowGroups sshusers 記錄,那么不在 sshusers 組中的用戶將無法登陸。所以我們可以創建一個用戶組用來包含允許通過 ssh 登陸主機的用戶,並在配置文件 C:\ProgramData\ssh\sshd_config 中添加對應的 AllowGroups 記錄:
AllowGroups sshusers
注意:所有帳戶名稱必須是小寫字母。
除了上面的基本用法,我們還可以通更靈活的配置來允許或拒絕符合某些條件的用戶登錄主機,下面是些常見的例子:
# 阻止與用戶 contoso\nick 從 10.32.1.68 登錄主機 DenyUsers contoso\nick@10.32.1.68 # 阻止所有 contoso 域中的用戶登錄主機 DenyUsers contoso\* # 只允許 contoso\sshusers 域組中的用戶登錄主機 AllowGroups contoso\sshusers # 只允許本地用戶 nick 從 10.32.1.68 登錄主機 AllowUsers nick@10.32.1.68 # 只允許本地用戶組 sshusers 中的用戶登錄主機 AllowGroups sshusers
使用 scp 命令拷貝文件
以前在 Windows 之間傳遞文件事件很讓人抓狂的事情,現在有了 OpenSSH 加持,自然是能夠支持以 scp 的方式在主機間拷貝文件,再加公鑰認證,完美的支持自動化的文件拷貝操作。下面是一個簡單的用 scp 拷貝文件例子:
> scp D:\grafana.tar.gz nick@xa-crab:c:\testdir
sftp 服務器
OpenSSH Server 默認開啟 sftp 服務器功能,也就是說我們通過 22 號端口就可以通過 ftp 協議訪問遠程主機,下面是筆者通過 ftp 客戶端工具 FileZilla 瀏覽遠程主機文件系統的截圖:
當然,你也可以使用命令行客戶端 sftp,效果是一樣的。
遠程執行命令
筆者在《PowerShell 遠程執行任務》一文中介紹過如何在 Windows 平台上遠程執行 PowerShell 命令,相比通過 OpenSSH 遠程執行命令,PowerShell 的方式實在是讓人感覺笨拙!讓我們來看看通過 OpenSSH 遠程執行命令是何等的簡練:
> ssh nick@xa-crab hostname > ssh nick@xa-crab "hostname; pwd"
第一行命令遠程執行 hostname 命令,結果顯示遠程主機的名稱;第二行命令遠程執行分號分隔的兩條命令,顯示遠程主機的名稱和當前的路徑。
遠程執行本地的腳本
由於 PowerShell 中不能把文件 attach 到 stdin,所以下面的命令不能工作:
> ssh nick@xa-crab < test.sh
但是我們可以采取管道操作獲得類似的結果,在本地用戶 nickli 的家目錄中創建 mytask.ps1 文件,編輯其內容如下:
echo "Hello World!" systeminfo > remotetest.txt
在本地運行下面的命令(遠程主機的默認 shell 為 PowerShell):
> Get-Content mytask.ps1 | ssh nick@xa-crab
檢查遠程主機 xa-crab 上用戶 nick 的家目錄,可以看到 remotetest.txt 文件被創建,內容為 systeminfo 命令的輸出。這種方法的優點是腳本中所有命令是在一個 session 中執行的,這點可以通過下面的方法驗證。在本地用戶 nickli 的家目錄中創建 mytask2.ps1 文件,編輯其內容如下:
$p = Get-Process PowerShell $p.VirtualMemorySize
在本地運行下面的命令(遠程主機的默認 shell 為 PowerShell):
> ssh nick@xa-crab '$p = Get-Process PowerShell; $p.VirtualMemorySize' > Get-Content mytask2.ps1 | ssh nick@xa-crab
上面的輸出表明,腳本執行的過程中變量的上下文是整個腳本。
執行遠程主機上的腳本
在遠程主機 xa-crab 上的用戶 nick 的家目錄中創建 task.ps1 文件,編輯其內容如下:
echo "Hello Nick!" systeminfo > test.txt
在本地運行下面的命令(遠程主機的默認 shell 為 PowerShell):
> ssh nick@xa-crab powershell.exe -F task.ps1
檢查遠程主機 xa-crab 上用戶 nick 的家目錄,可以看到 test.txt 文件被創建,內容為 systeminfo 命令的輸出。
總結
當 Windows 支持 OpenSSH 后,我們就能夠用相同的工具在 Windows 平台和 Linux 平台上工作了,更進一步還可以用 ssh 客戶端跨平台地連接 ssh 服務器,想想就是一件開心的事情(雖然目前 bug 還很多:))!