Podman 安裝和使用初體驗

Docker 是我日常開發工作中離不開的環境工具軟件。不僅是本地搭建開發環境,在一些項目的線上部署中也會用到。不過最近我注意到 Docker 背後公司的一些舉動有些不太對勁,爲以防萬一,我開始提前瞭解它的替代品:Podman。

起因

開始 Podman 的介紹之前,先說說 Docker 讓我覺得不對勁的事情。爲了看起來直觀一點,我列了個簡單的時間線:

我之前一直認爲 Docker 有社區版,所以沒太在意它背後的商業行爲。而且上面發生的任何一件事,單獨看好像都沒什麼大不了的。但如果連在一起,就有點意思了。

危言聳聽的總結一下:Docker 已經經歷了資本進入,創始人決裂,公司易手。現在爲了想賺錢的法子,開始薅程序員開發者的羊毛。

Docker Desktop 是什麼?簡單說就是一個靠虛擬機運行 Docker 的界面化容器管理軟件。我之前在 macOS 系統上爲了使用 Docker 安裝過。但基於這個軟件實現的 Docker 環境因爲虛擬機文件系統的原因,性能實在太弱。所以我放棄了 macOS 系統,回到了 Linux。Linux 系統上不需要這個軟件,大規模應用 Docker 的線上環境也是。

Docker Desktop 收費對我來說目前雖然沒有任何影響。但這是一個信號,意味着接下來 Docker 爲了利潤進行更加深入嘗試的可能性會很大。

所以我決定開始瞭解 Docker 的開源替代品: Podman。

安裝 Podman

作爲 Docker 的替代品,Podman 的操作和 Docker 高度兼容。俺官方文檔的說法,直接把 podman 映射爲 docker 命令來使用也沒問題。但我覺得沒必要,同樣還是 6 個字母,沒有減輕任何輸入負擔。而且在運行方式上, Docker 依賴於守護進程,Podman 不需要守護進程。這種區別決定了所謂的高度兼容,一定會存在一些使用方式上的差異。爲了避免認知上的混淆,我覺得還是有必要把 Podman 當成一個全新的工具。

在 Arch Linux 上安裝 Podman 很簡單,直接使用 Pacman 包管理命令:

sudo pacman -S podman

然後編輯 /etc/containers/registries.conf 文件,添加一個可用的容器鏡像庫地址:

unqualified-search-registries = ["docker.io"]

接着就可以正常運行容器了:

sudo podman run --rm hello-world

執行結果如下:

使用普通帳號

我不太習慣以 sudo 特權方式來運行容器,而且也沒必要。Docker 可以通過把當前帳號加入 docker 用戶組的方式來解決這個問題。Podman 稍微麻煩一點,因爲它有一個用戶命名空間的概念。

關於 Podman 用戶命名空間,我目前還不是十分明白。淺顯的一點理解是針對運行中容器的權限管理機制。可以防止容器進程出現逾越權限的安全隱患。更具體的內容還需要後面瞭解並實踐,所以還是先分享操作過程。

先看看不用 sudo 執行的結果:

提示 user namespace 中的用戶 ID 和用戶組 ID 不可用。最後還提示要檢查 /etc/subuid/etc/subgid 這兩個文件。系統默認情況下沒有它們,定義所謂的用戶命名空間就是要創建這兩個文件。

先創建這兩個空文件:

sudo touch /etc/subuid /etc/subgid

目前沒有任何內容,給它們填充點東西:

sudo usermod --add-subuids 100000-165535 --add-subgids 100000-165535 $USER

再執行以下命令使文件中的用戶映射信息在容器中生效:

podman system migrate

然後再次以普通用戶運行容器就沒問題了。

小於 1024 端口的映射

以上面運行的 Nginx 容器爲例,如果想映射容器內的 80 端口到本機的 80 端口,會出現以下報錯:

這個報錯的提示很詳細,指明瞭問題的原因和解決方案。Linux 系統限制了非特權用戶可以使用的最小端口。也就是默認只能選擇 1024 往上的。如果要使用 80 這種小於 1024 的端口號,只有兩個方案:

  1. 使用 sudo 以特權方式執行命令。
  2. 修改 /etc/sysctl.conf 文件的 net.ipv4.ip_unprivileged_port_start 配置項。比如把值改成 80。

這兩種方案需要自己根據情況來選擇,我的建議是如果能用特權方式來執行的就優先選擇這個方法,情況實在特殊再考慮改系統配置的方案。

開機啓動

Docker 因爲有守護進程,所以自身就能實現開機啓動功能。Podman 沒有守護進程,需要配合 Systemd 來實現。

還是以運行 Nginx 容器來舉例,先把容器運行起來:

sudo podman run --rm -p 80:80 --name nginx nginx:alpine

運行的命令加了一個 --name 參數,並定義了名稱爲 nginx ,這是爲了方便後面生成 Systemd 配置文件。

容器運行成功後,執行下面的命令生成 Systemd 的配置文件:

sudo podman generate systemd --new nginx > nginx.service
sudo mv nginx.service /usr/lib/systemd/system/

然後就可以通過 systemctl 命令來管理這個容器開機自啓動了。

總結

從我目前的嘗試來看,Podman 在本地開發環境下替代 Docker 問題不大。只是目前這個用戶命名空間的概念還需要再瞭解一下。

和 Docker 依賴 Docker Engine 守護進程的方式對比一下,我也更喜歡 Podman 這種無守護進程的執行方式。不僅節省系統資源,而且也讓容器進程的跟蹤溯源更加清晰明瞭。

喜歡歸喜歡,關鍵還是需要用起來。目前我已經開始在嘗試了,使用中應該還會碰到一些其他的問題,等遇到了再補充到本文。

本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源https://zhuanlan.zhihu.com/p/414259768