3. Docker 与 Podman 环境搭建:安装 Docker Engine、配置非 root 用户、安装 Podman、验证环境

容器运行环境是镜像安全项目的基础设施层。本章将指导你完成 Docker Engine 与 Podman 的安装、非 root 用户权限配置以及环境验证。Docker 作为行业标准容器引擎,Podman 作为无守护进程、支持 rootless 模式的替代方案,两者在安全项目中各有适用场景。

3.1 环境概览与组件关系

下图展示了 Docker 与 Podman 在镜像安全项目中的部署位置及组件关系。Docker 采用客户端-守护进程架构,Podman 采用无守护进程的 fork-exec 模型,两者均支持 OCI 标准镜像格式。

Docker 与 Podman 环境组件关系图 Docker 与 Podman 环境组件关系 Docker 架构 docker CLI 客户端 dockerd 守护进程 containerd / runc Podman 架构 podman CLI(无守护进程) 直接 fork 容器进程 crun / runc 两者均支持 OCI 镜像标准,镜像可互用;Podman 原生支持 rootless 模式,安全性更高

3.2 安装 Docker Engine

Docker Engine 是运行容器的核心组件。以下步骤基于 Ubuntu 22.04 LTS 环境,其他 Linux 发行版请参考官方文档调整包管理器命令。

3.2.1 卸载旧版本并设置仓库

# 卸载可能存在的旧版本
sudo apt-get remove docker docker-engine docker.io containerd runc

# 更新包索引并安装依赖
sudo apt-get update
sudo apt-get install -y ca-certificates curl gnupg lsb-release

# 添加 Docker 官方 GPG 密钥
sudo mkdir -p /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg

# 设置稳定版仓库
echo \
  "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu \
  $(lsb_release -cs) stable" | sudo tee /etc/apt/sources.list.d/docker.list > /dev/null

3.2.2 安装 Docker Engine 与 containerd

# 更新包索引并安装最新版本
sudo apt-get update
sudo apt-get install -y docker-ce docker-ce-cli containerd.io docker-compose-plugin

# 验证安装
sudo docker --version
# 输出示例:Docker version 24.0.7, build afdd53b

# 启动并设置开机自启
sudo systemctl enable docker
sudo systemctl start docker

# 验证守护进程状态
sudo systemctl status docker --no-pager
安全提示:在生产环境中,建议锁定 Docker 版本以避免意外升级导致兼容性问题。使用 apt-mark hold docker-ce docker-ce-cli containerd.io 锁定版本。

3.3 配置非 root 用户运行 Docker

默认情况下,Docker 守护进程绑定到 Unix socket(/var/run/docker.sock),该 socket 属于 root 用户和 docker 组。将用户加入 docker 组可避免每次使用 sudo,但需注意这等同于授予用户 root 权限。

3.3.1 创建 docker 组并添加用户

# 创建 docker 组(通常安装后已存在)
sudo groupadd docker

# 将当前用户加入 docker 组
sudo usermod -aG docker $USER

# 刷新组成员身份(或重新登录)
newgrp docker

# 验证非 root 用户权限
docker run hello-world
安全警告:加入 docker 组的用户拥有与 root 同等的容器管理权限,可挂载宿主机文件系统、执行特权操作。在镜像安全项目中,建议仅在受控的开发/测试环境使用此配置,生产环境应使用 Podman 的 rootless 模式或 Docker 的 rootless 模式。

3.3.2 安全替代方案:Docker Rootless 模式

Docker 也支持 rootless 模式,无需 root 权限即可运行守护进程和容器。安装步骤如下:

# 安装 rootless 依赖
sudo apt-get install -y uidmap dbus-user-session

# 停止并禁用系统级 Docker
sudo systemctl disable --now docker.service docker.socket

# 以当前用户安装 rootless Docker
dockerd-rootless-setuptool.sh install

# 设置环境变量
export PATH=/usr/bin:$PATH
export DOCKER_HOST=unix:///run/user/$UID/docker.sock

# 验证 rootless 模式
docker info | grep -i rootless

3.4 安装 Podman

Podman 由 Red Hat 主导开发,无守护进程、支持 rootless 模式,与 Docker CLI 命令兼容。在镜像安全项目中,Podman 的 rootless 特性可降低容器逃逸风险。

3.4.1 通过包管理器安装

# Ubuntu 22.04 官方源安装
sudo apt-get update
sudo apt-get install -y podman

# 验证安装
podman --version
# 输出示例:podman version 3.4.4

# 查看系统信息
podman info

3.4.2 安装最新版本(Kubic 仓库)

Ubuntu 官方源的 Podman 版本可能较旧,建议使用 Kubic 仓库获取最新稳定版:

# 添加 Kubic 仓库
source /etc/os-release
echo "deb https://download.opensuse.org/repositories/devel:/kubic:/libcontainers:/stable/xUbuntu_${VERSION_ID}/ /" | sudo tee /etc/apt/sources.list.d/devel:kubic:libcontainers:stable.list

# 导入 GPG 密钥
curl -fsSL "https://download.opensuse.org/repositories/devel:kubic:libcontainers:stable/xUbuntu_${VERSION_ID}/Release.key" | sudo gpg --dearmor -o /etc/apt/keyrings/devel_kubic_libcontainers_stable.gpg

# 安装最新版
sudo apt-get update
sudo apt-get install -y podman

# 验证
podman --version
# 输出示例:podman version 4.9.3

3.5 环境验证与对比测试

完成安装后,需验证两个容器引擎均能正常工作,并对比其关键差异。

3.5.1 基础功能验证

# Docker 验证
docker run --rm hello-world

# Podman 验证(无需 sudo)
podman run --rm hello-world

# 拉取镜像并查看
docker pull alpine:latest
podman pull alpine:latest

# 列出镜像
docker images
podman images

# 运行容器并查看进程
docker run -d --name test-docker alpine sleep 60
podman run -d --name test-podman alpine sleep 60

# 查看运行中容器
docker ps
podman ps

# 清理测试容器
docker rm -f test-docker
podman rm -f test-podman

3.5.2 Docker 与 Podman 关键差异对比

特性 Docker Podman
架构模型 客户端-守护进程(C/S) 无守护进程(fork-exec)
Rootless 支持 需额外配置 rootless 模式 原生支持,默认 rootless
守护进程权限 通常以 root 运行 无守护进程,进程级隔离
命令兼容性 标准 docker 命令 alias docker=podman 可兼容
镜像格式 OCI 标准 OCI 标准,镜像可互用
Kubernetes 集成 通过 dockershim(已弃用) 原生生成 Pod YAML
安全隔离 依赖守护进程沙箱 进程级隔离,无中心进程

3.5.3 安全相关配置验证

# 验证 Docker 非 root 用户运行
docker info | grep -E "Security|Rootless"

# 验证 Podman rootless 模式
podman info | grep -i rootless

# 查看容器默认 seccomp 配置
docker info --format '{{.SecurityOptions}}'
podman info --format '{{.SecurityOptions}}'

# 验证 cgroup 版本(v2 更安全)
docker info | grep -i cgroup
podman info | grep -i cgroup
镜像安全项目建议:在 CI/CD 流水线中,建议同时安装 Docker 和 Podman。Docker 用于与现有工具链集成,Podman 用于需要更高安全隔离的生产环境部署。两者共享同一 OCI 镜像仓库,镜像构建一次即可在两种环境中运行。

3.6 常见问题与排错

  • Docker socket 权限拒绝:确认用户已加入 docker 组并重新登录。使用 groups 命令验证组成员身份。
  • Podman 拉取镜像失败:检查 /etc/containers/registries.conf 中的镜像仓库配置,确保 docker.io 在 unqualified-search-registries 列表中。
  • cgroup 版本不匹配:Ubuntu 22.04 默认使用 cgroup v2,若 Podman 报错,检查 /sys/fs/cgroup 文件系统类型。
  • 存储驱动冲突:Docker 默认使用 overlay2,Podman 默认使用 overlay。确保内核支持 overlay 文件系统。

3.7 环境清理与重置

如需重置环境进行重新安装,执行以下清理命令:

# 停止所有容器并清理
docker stop $(docker ps -aq) 2>/dev/null
docker system prune -a --volumes -f

# 卸载 Docker
sudo apt-get purge -y docker-ce docker-ce-cli containerd.io docker-compose-plugin
sudo rm -rf /var/lib/docker /etc/docker

# 卸载 Podman
sudo apt-get purge -y podman
sudo rm -rf /var/lib/containers /etc/containers

# 删除 docker 组(可选)
sudo groupdel docker