使用Docker搭建私有PyPI镜像仓库的完整步骤教学

 更新时间:2025年09月15日 10:07:57   作者:东方佑  
在企业内网或离线开发环境中,我们常常需要一个稳定、快速且可控制的 Python 包管理方案,本文将详细介绍如何使用 devpi 和 Docker 构建一个私有的 PyPI 镜像服务器,有需要的小伙伴可以了解下

在企业内网或离线开发环境中,我们常常需要一个稳定、快速且可控制的 Python 包管理方案。本文将详细介绍如何使用 devpi 和 Docker 构建一个私有的 PyPI 镜像服务器,并实现对 Windows 与 Linux 平台的 64 位二进制包(wheel) 的自动下载、缓存和分发。

通过本教程,你可以:

  • 快速搭建本地 PyPI 缓存服务器;
  • 支持不同操作系统平台(win_amd64 / manylinux);
  • 自动从国内镜像源(阿里云)预下载指定依赖包;
  • 实现高效、安全的企业级 Python 包管理。

准备工作

1. 创建项目结构

首先,在你的项目目录中创建以下文件结构:

pypi-mirror/
├── init/
│   ├── Dockerfile
│   └── setup-devpi.sh
├── docker-compose.yml
├── requirements.txt          # 待安装的包列表
└── devpi-data/               # 数据持久化目录(自动生成)

注意:首次运行前需手动创建空的 devpi-data 目录用于存储 devpi 数据。

2. 编写 Dockerfile(./init/Dockerfile)

# 使用 Python 3.10 作为基础镜像(国内加速)
FROM python:3.10

# 设置环境变量,使用阿里云 PyPI 镜像
ENV PIP_DEFAULT_TIMEOUT=100 \
    PIP_RETRIES=5 \
    PIP_INDEX_URL=https://mirrors.aliyun.com/pypi/simple/ \
    PIP_TRUSTED_HOST=mirrors.aliyun.com

# 安装 devpi 相关组件
RUN pip install --no-cache-dir devpi-server devpi-web devpi-client passlib

# 创建数据目录
RUN mkdir -p /data/server

# 暴露端口
EXPOSE 3141

# 启动 devpi-server
CMD ["devpi-server", "--host", "0.0.0.0", "--port", "3141", "--serverdir", "/data/server"]

说明:

  • 使用阿里云镜像提升国内网络下载速度。
  • 安装了 devpi-server(服务端)、devpi-web(Web 界面)、devpi-client(命令行工具)。
  • 所有数据保存在 /data/server,通过卷挂载实现持久化。

3. 编写初始化脚本(./init/setup-devpi.sh)

该脚本负责配置 devpi 用户、索引,并根据 requirements.txt 下载并上传指定包及其依赖。

#!/bin/bash
set -e

echo "配置 devpi 客户端..."
devpi use http://localhost:3141

# 创建用户
echo "创建用户和索引..."
devpi user -c mirroruser password=securepassword123 || echo "用户已存在"

# 登录该用户(关键步骤!否则无法操作索引)
echo "登录新创建的用户..."
devpi login mirroruser --password=securepassword123

# 创建主索引
devpi index -c main bases=root/pypi || echo "索引已存在"

# 切换到主索引
devpi use mirroruser/main

# 创建临时目录
mkdir -p /tmp/packages

# 设置 pip 使用阿里云镜像
export PIP_INDEX_URL="https://mirrors.aliyun.com/pypi/simple/"
export PIP_TRUSTED_HOST="mirrors.aliyun.com"

echo "开始处理 requirements.txt 中的包..."

# 检查 requirements.txt 是否存在
if [ ! -f "/app/requirements.txt" ]; then
    echo "错误: /app/requirements.txt 文件不存在!"
    exit 1
fi

# 第一阶段:解析所有包及依赖
all_packages=()
while IFS= read -r package; do
  [[ -z "$package" || "$package" =~ ^# ]] && continue
  echo "分析包: $package"
  
  # 获取依赖(模拟安装但不实际安装)
  dependencies=$(pip install --no-deps --dry-run "$package" 2>&1 | grep 'Collecting' | awk '{print $2}' | sed 's/[<=>].*//')

  all_packages+=("$package")
  while IFS= read -r dep; do
    [[ -z "$dep" ]] && continue
    all_packages+=("$dep")
  done <<< "$dependencies"
done < /app/requirements.txt

# 去重排序
unique_packages=($(printf "%s\n" "${all_packages[@]}" | sort -u))

# 第二阶段:下载 64 位平台 wheel 包
echo "正在下载 64 位平台二进制包..."
for package in "${unique_packages[@]}"; do
  echo "处理 $package..."
  rm -f /tmp/packages/*  # 清空临时目录

  # 下载 Windows 64-bit 包(Python 3.13 兼容)
  echo "  下载 win_amd64 版本..."
  pip download --only-binary=:all: --python-version 313 --platform win_amd64 \
    -i https://mirrors.aliyun.com/pypi/simple/ -d /tmp/packages "$package" > /dev/null 2>&1

  # 下载 Linux x86_64 包(manylinux)
  echo "  下载 manylinux_2_17_x86_64 版本..."
  pip download --only-binary=:all: --python-version 313 --platform manylinux_2_17_x86_64 \
    -i https://mirrors.aliyun.com/pypi/simple/ -d /tmp/packages "$package" > /dev/null 2>&1

  # 上传到 devpi
  for whl in /tmp/packages/*.whl; do
    if [ -f "$whl" ]; then
      echo "  上传 $whl 到私有仓库..."
      devpi upload "$whl"
    fi
  done
done

# 第三阶段:创建平台专用索引
echo "创建平台过滤索引..."

devpi index -c win_amd64 bases=main \
    mirrorsync=1 \
    platform=win_amd64 \
    python_version=3.13 || echo "索引 win_amd64 已存在"

devpi index -c linux_x86_64 bases=main \
    mirrorsync=1 \
    platform=manylinux_2_17_x86_64 \
    python_version=3.13 || echo "索引 linux_x86_64 已存在"

echo "✅ 初始化完成!DevPI 私有仓库已就绪。"

echo ""
echo "📌 使用方式如下:"
echo "   Windows 用户:"
echo "     pip install -i http://<YOUR_LOCAL_IP>:3141/mirroruser/win_amd64/+simple/ <package>"
echo ""
echo "   Linux 用户:"
echo "     pip install -i http://<YOUR_LOCAL_IP>:3141/mirroruser/linux_x86_64/+simple/ <package>"
echo ""
echo "💡 提示:请将 <YOUR_LOCAL_IP> 替换为宿主机 IP 地址(如 192.168.1.100)"

安全建议:

  • 生产环境下应修改默认密码;
  • 可启用 HTTPS 和认证机制增强安全性。

4. 配置 Docker Compose(docker-compose.yml)

version: '3.8'

services:
  devpi:
    build:
      context: .
      dockerfile: init/Dockerfile
    container_name: pypi-mirror
    ports:
      - "3141:3141"
    volumes:
      - ./devpi-data:/data/server
      - ./init/setup-devpi.sh:/setup-devpi.sh
      - ./requirements.txt:/app/requirements.txt
    environment:
      - DEVPISERVER_SERVERDIR=/data/server
    restart: unless-stopped
    entrypoint: >
      sh -c "
        if [ ! -f /data/server/.serverversion ]; then
          devpi-init --serverdir /data/server;
        fi;
        devpi-server --host 0.0.0.0 --port 3141 --serverdir /data/server &
        sleep 20 &&
        /setup-devpi.sh &&
        wait
      "

功能说明:

  • 第一次启动时自动初始化 devpi 数据目录;
  • 后续启动直接复用已有数据;
  • 脚本延迟执行确保服务已就绪;
  • 支持容器重启后自动恢复服务。

获取热门包列表并生成 requirements.txt

为了构建一个实用的私有镜像,我们可以基于 PyPI 上最受欢迎的包 来填充初始内容。

步骤一:下载 top-pypi-packages.csv

访问 https://hugovk.github.io/top-pypi-packages/

点击 “Download CSV” 下载最新的 top-pypi-packages.csv 文件。

步骤二:使用 gen_requirements.py 生成 requirements.txt

假设你有一个脚本 gen_requirements.py,其功能是从 CSV 中提取前 N 个最流行包名,输出为 requirements.txt

示例代码(gen_requirements.py):

import csv

# 读取 top-pypi-packages.csv,提取前 50 个包
with open('top-pypi-packages.csv', newline='', encoding='utf-8') as f:
    reader = csv.DictReader(f)
    packages = [row['project'] for row in reader]

# 写入 requirements.txt
with open('requirements.txt', 'w') as f:
    for pkg in packages[:50]:  # 取前 50 名
        f.write(f"{pkg}\n")

print("✅ 已生成 requirements.txt,包含前 50 个热门 PyPI 包")

运行后生成的 requirements.txt 示例:

requests
urllib3
certifi
idna
charset_normalizer
click
flask
...

启动服务

第一步:构建并启动容器

docker-compose up --build

首次运行会经历以下过程:

  • 构建镜像;
  • 初始化 devpi 数据目录;
  • 启动 devpi-server;
  • 执行 setup-devpi.sh 脚本,下载并上传包;
  • 创建平台专用索引。

时间消耗:取决于 requirements.txt 中包的数量和网络速度,可能需要数分钟。

第二步:查看 Web 界面

打开浏览器访问:

http://localhost:3141/mirroruser/main/+simple/

你将看到所有已上传包的简单索引页面。

客户端安装测试

Windows 用户

pip install -i http://192.168.1.100:3141/mirroruser/win_amd64/+simple/ requests

Linux 用户

pip install -i http://192.168.1.100:3141/mirroruser/linux_x86_64/+simple/ pandas

成功标志:

  • 不再连接公网 PyPI;
  • 直接从本地服务器下载 .whl 文件;
  • 安装速度快,稳定性高。

日常使用命令

命令说明
docker-compose up启动服务(无需重建)
docker-compose down停止并移除容器
docker-compose logs查看日志调试问题

数据已挂载至 ./devpi-data,即使删除容器也不会丢失已缓存的包。

高级特性与扩展建议

支持更多平台

可以扩展脚本支持其他平台,例如:

  • macosx_11_0_arm64(M1/M2 Mac)
  • linux_aarch64

只需添加对应的 --platform 参数即可。

定期更新包

可通过定时任务拉取新版本包,保持私有仓库同步。

添加身份验证与权限控制

devpi 支持细粒度用户权限管理,可用于团队协作场景。

集成 CI/CD 流程

在内部 CI 环境中设置此镜像为默认源,避免外部依赖风险。

总结

本文介绍了一种完整的解决方案,利用 devpi + Docker + 阿里云镜像 + 多平台 wheel 分发 技术栈,打造了一个高性能、跨平台、可持久化的私有 PyPI 仓库。

适用场景:

  • 企业内网隔离环境;
  • 开发团队统一依赖管理;
  • 提升 CI/CD 构建效率;
  • 减少对外部源的依赖与安全风险。

核心优势:

  • 自动化初始化流程;
  • 支持平台差异化索引;
  • 国内镜像加速下载;
  • 易于部署与维护。

现在就开始搭建属于你自己的私有 PyPI 仓库吧!

GitHub 参考资源:

到此这篇关于使用Docker搭建私有PyPI镜像仓库的完整步骤教学的文章就介绍到这了,更多相关Docker搭建私有PyPI镜像仓库内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Docker安装并使用Mysql的详细教程(实测可用!)

    Docker安装并使用Mysql的详细教程(实测可用!)

    在日常的工作中经常会需要将数据存在服务器,经常用到的数据库是mysql,下面这篇文章主要给大家介绍了关于Docker安装并使用Mysql的详细教程,文中通过实例代码介绍的非常详细,需要的朋友可以参考下
    2023-01-01
  • docker常用命令及设置开机自启方式

    docker常用命令及设置开机自启方式

    这篇文章主要介绍了docker常用命令及设置开机自启方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-06-06
  • docker容器添加对外映射端口的实现

    docker容器添加对外映射端口的实现

    本文主要介绍了docker容器添加对外映射端口的实现 ,从而实现容器与外部网络的通信,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-09-09
  • Docker启动RabbitMQ实现生产者与消费者的详细过程

    Docker启动RabbitMQ实现生产者与消费者的详细过程

    这篇文章主要介绍了Docker启动RabbitMQ,实现生产者与消费者,通过Docker拉取镜像并启动RabbitMQ,本文结合实例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2023-02-02
  • 一文详解如何获取docker镜像中的jar包

    一文详解如何获取docker镜像中的jar包

    本人在工作中遇到了需要在docker查看jar这种操作,查看了许多资料,终于还是找到了,下面这篇文章主要给大家介绍了关于如何获取docker镜像中jar包的相关资料,需要的朋友可以参考下
    2024-05-05
  • Docker搭建Nginx图片服务器的方法

    Docker搭建Nginx图片服务器的方法

    这篇文章主要介绍了Docker搭建Nginx图片服务器的方法,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-03-03
  • docker的一些基本指令

    docker的一些基本指令

    这篇文章主要介绍了docker的一些常用操作,帮助大家更好的理解和学习使用docker,感兴趣的朋友可以了解下
    2021-04-04
  • Docker使用阿里加速器安装centos教程

    Docker使用阿里加速器安装centos教程

    这篇文章主要介绍了Docker使用阿里加速器安装centos教程,需要的朋友可以参考下
    2017-04-04
  • docker安装pxc集群的详细教程

    docker安装pxc集群的详细教程

    这篇文章主要介绍了docker安装pxc集群的详细教程,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2021-02-02
  • 如何搭建docker虚拟机测试服

    如何搭建docker虚拟机测试服

    文章介绍如何搭建Docker虚拟机测试服,通过隔离环境、安装CentOS镜像并映射端口,配置安全组和域名转发,实现本地开发测试连接测试服数据库和Redis,感兴趣的朋友跟随小编一起学习吧
    2025-08-08

最新评论