Skip to content

vansour/ghproxy

Repository files navigation

GitHub 文件代理加速器 (ghproxy)

CI Rust License Docker

一个高性能的 GitHub 文件代理服务,用于加速 GitHub 文件下载,支持 Vue 3 Web UI、REST API、Prometheus 指标和只读 Docker Registry 代理功能。

📘 正式版基线文档

为了推进正式版发布,仓库内维护以下基线文档:

补充维护文档:

📁 项目结构

ghproxy/
├── backend/           # 后端 Rust 代码 (axum + hyper)
├── frontend/          # 前端 Vue 3 + Vite + TypeScript
└── docs/              # 基线文档

🌟 主要特性

  • 高性能代理: 基于 Rust 和 Tokio 异步运行时,统一使用 hyper HTTP 客户端
  • 轻量前端: Vue 3 + Vite,纯 JS/CSS 产物,无 WASM 二进制
  • 多格式支持: 支持原始文件、压缩包等多种下载格式
  • REST API: 灵活的 API 接口,满足不同使用场景
  • IP 限流: 基于 IP 的请求限流保护(默认 100 请求/分钟/IP)
  • Prometheus 指标: 丰富的监控指标(按状态码、方法、路径类型分类)
  • 优雅关闭: graceful shutdown,确保请求完成
  • 日志系统: 完整的日志记录和追踪功能
  • Docker 支持: 开箱即用的 Docker 部署
  • Docker Registry 代理: 集成 Docker Registry V2 只读代理,支持 docker pull/v2/* 读路径

🚀 快速开始

使用 Docker Compose(推荐)

docker compose up -d

首次启动时,容器使用内置默认值运行,所有配置均可通过环境变量覆盖。

本地构建

# 构建前端
cd frontend
npm install
npm run build

# 运行后端测试
cd ..
cargo test -p ghproxy

# 运行后端
cargo run -p ghproxy

本地运行后,后端会优先读取 /app/web,如果不存在则回退到 frontend/dist 下的 Vite 构建产物。

⚙️ 配置指南

所有配置均可通过环境变量覆盖,未设置的变量使用内置默认值。

Docker/Compose 部署时,编辑 compose.yml 中的 environment 部分即可。

如需在本地验证容器镜像能否完整启动并暴露核心接口,可以直接运行:

bash docker/smoke-test.sh

环境变量列表

所有配置均可通过环境变量覆盖,未设置的变量使用内置默认值。

环境变量 默认值 说明
GHPROXY_HOST 0.0.0.0 监听地址
GHPROXY_PORT 8080 监听端口
GHPROXY_SIZE_LIMIT 2048 文件大小上限 (MB)
GHPROXY_REQUEST_TIMEOUT 60 请求超时 (秒)
GHPROXY_MAX_CONCURRENT 100 最大并发请求数
GHPROXY_REQUEST_SIZE_LIMIT 10 请求体大小上限 (MB)
GHPROXY_SERVER_POOL_IDLE_TIMEOUT 90 连接池空闲连接超时 (秒)
GHPROXY_SERVER_POOL_MAX_IDLE_PER_HOST 32 每个 host 最大空闲连接数
GHPROXY_SERVER_POOL_HTTP2_STREAM_WINDOW_SIZE 2097152 HTTP/2 stream window 大小
GHPROXY_SERVER_POOL_HTTP2_CONNECTION_WINDOW_SIZE 8388608 HTTP/2 connection window 大小
GHPROXY_AUTH_TOKEN (空) GitHub API 访问令牌
GHPROXY_REGISTRY registry-1.docker.io 默认 Docker Registry
GHPROXY_REGISTRY_ALLOWED_HOSTS registry-1.docker.io Registry 白名单 (逗号分隔)
GHPROXY_REGISTRY_READINESS_DEPENDS_ON_REGISTRY false 是否将 registry 可达性纳入 readyz 判定
GHPROXY_PROXY_ALLOWED_HOSTS github.com,*.github.com,githubusercontent.com,*.githubusercontent.com 代理域名白名单 (逗号分隔)
GHPROXY_CACHE_STRATEGY memory_with_cdn disabled / memory_only / memory_with_cdn
GHPROXY_CACHE_MAX_SIZE 536870912 缓存最大大小 (字节, 512MB)
GHPROXY_CACHE_DEFAULT_TTL 3600 默认 TTL (秒)
GHPROXY_CACHE_MAX_TTL 86400 最大 TTL (秒)
GHPROXY_CACHE_MIN_OBJECT_SIZE 1024 最小可缓存对象大小 (字节)
GHPROXY_CACHE_MAX_OBJECT_SIZE 104857600 最大可缓存对象大小 (字节)
GHPROXY_CACHE_CACHEABLE_PATTERNS /github/*,/v2/*/blobs/*,/v2/*/manifests/* 显式可缓存路径模式 (逗号分隔)
GHPROXY_CACHE_BYPASS_PATTERNS /api/*,/metrics,/healthz,/readyz 显式绕过缓存路径模式 (逗号分隔)
GHPROXY_RATE_LIMIT_WINDOW 60 限流窗口 (秒)
GHPROXY_RATE_LIMIT_MAX_REQUESTS 100 窗口内最大请求数/IP
GHPROXY_LOG_LEVEL info trace / debug / info / warn / error
GHPROXY_SHELL_EDITOR false 是否启用 shell 编辑器模式
GHPROXY_DEBUG_ENDPOINTS_ENABLED false 是否开放 /debug/* 调试接口
GHPROXY_DEBUG_METRICS_ENABLED false 是否允许非 loopback 远端访问 /metrics

关键配置项:

  • proxy.allowed_hosts: 允许代理访问的上游域名白名单,重定向也会按这个列表校验。
  • registry.default: 默认 Docker Registry 上游,支持主机名或完整 origin URL;启动时会规范化为 concrete origin,不支持 wildcard。
  • registry.readiness_depends_on_registry: 控制 /readyz 是否把 registry 可达性纳入 readiness 判定,默认 false
  • registry.allowed_hosts: Docker Registry 代理允许访问的 registry host 白名单;默认仅允许 registry.default
  • cache.*: 控制内存缓存策略、对象大小范围和缓存/绕过路径模式。
  • cache.builtin_cacheable_kinds: 即使显式 cacheable_patterns 未命中,GitHub 文件、Docker blob、Docker manifest 仍会按内建类型兜底缓存;该语义会在 /api/config 中显式暴露,便于运维判断真实缓存行为。
  • rate_limit.*: 控制单 IP 的窗口限流参数。
  • server.pool.*: 控制 Hyper 客户端连接池与 HTTP/2 窗口大小。
  • shell.editor: 控制是否对 shell/html 文本中的 GitHub 链接执行代理前缀重写;开启后会按当前请求的域名和协议自动推导代理前缀。
  • debug.endpoints_enabled: 控制内部调试接口(如 /debug/blob-info)是否对外暴露,默认关闭。
  • debug.metrics_enabled: 控制 /metrics 是否允许非 loopback 远端访问;默认关闭,仅保留本机抓取。

运行前提:

  • 服务按"运行在受控入口之后"设计。源站仅在 loopback 请求上信任 Forwarded / X-Forwarded-* 这类代理头;否则会退回使用 socket 对端地址做归因。
  • 源站默认不开放跨站浏览器 CORS;Vue 3 前端按同源模式访问 /api/*/readyz。如果第三方站点想把它当浏览器侧跨域代理直接调用,默认会被浏览器拦住。
  • 如果启用了 shell.editor = true,服务会按当前请求的 Host 和协议自动推导重写前缀。
  • /metrics 默认只接受 loopback 访问;如果确实需要让远端 Prometheus 经由内网或受控入口抓取,再显式打开 debug.metrics_enabled = true
  • /api/*/healthz/readyz/metrics/registry/healthz/debug/* 会显式返回 Cache-Control: no-store,避免浏览器或 CDN 误缓存动态状态与运维数据;同源 UI/API 响应也会补充基础安全头。

📡 API 端点

端点 描述
GET / Vue 3 Web UI
GET /healthz 轻量存活检查
GET /readyz 就绪检查(默认只反映本地接流能力,同时返回 registry 子状态)
GET /metrics Prometheus 指标,默认仅 loopback 可访问
GET /api/config 当前公开运行摘要(含缓存规则、pool 配置、debug 开关等非敏感配置)
GET /api/stats 服务、缓存、Registry 上游/Token 摘要、请求分布与错误统计
GET/HEAD /github/{*path} GitHub 仓库相对路径代理,例如 owner/repo/main/file.txt
GET /registry/healthz Docker Registry 专项健康检查
GET /debug/blob-info Registry 调试接口,仅在 debug.endpoints_enabled = true 时开放
GET/HEAD /v2/* Docker Registry V2 只读代理

完整 GitHub URL 走回退入口,例如:

  • /https://github.com/owner/repo/blob/main/file.txt
  • /https://github.com/owner/repo/main/file.txt
  • /https://github.com/owner/repo/releases/download/v1.0.0/app.tar.gz

GitHub 代理入口和 fallback 入口都是只读模式,仅支持 GETHEAD

Prometheus 指标

默认情况下,/metrics 只对本机开放;远端抓取需要显式设置 debug.metrics_enabled = true

ghproxy_requests_total              # 总请求数
ghproxy_requests_by_status{status}  # 按状态码 (2xx/4xx/5xx)
ghproxy_requests_by_type{type}      # 按类型 (github/registry/api)
ghproxy_requests_by_method{method}  # 按方法 (GET/POST/HEAD)
ghproxy_errors_total{error_type}    # 错误计数
ghproxy_info{version}               # 服务版本
ghproxy_uptime_seconds              # 运行时间
ghproxy_active_requests             # 活跃请求数
ghproxy_bytes_transferred_total     # 传输字节数

🔧 开发指南

# 运行后端测试
cargo test -p ghproxy

# 代码格式化
cargo fmt --all

# 静态检查
cargo clippy -p ghproxy --all-targets --all-features -- -D warnings

# 供应链与安全检查
cargo audit
cargo deny check bans licenses sources

# 构建发布版
cargo build --release -p ghproxy

📌 当前能力边界

  • 首页用于生成 GitHub 文件、raw 地址和 release 下载地址的代理链接,不支持仅输入 owner/repo 仓库首页。
  • /github/* 仅接受仓库相对路径;如果输入的是完整 GitHub URL,请使用回退入口格式。
  • GitHub/file 代理入口是只读模式,仅支持 GETHEAD,不接受 POSTPUTPATCH 等写方法。
  • Docker Registry 代理当前是只读模式,支持 pull,不支持 push、blob 上传和镜像发布。
  • 调试接口默认关闭;只有在明确启用 debug.endpoints_enabled = true 时才会开放 /debug/blob-info
  • GET /healthz 是轻量存活检查,适合容器 HEALTHCHECK 与 liveness probe。
  • GET /readyz 默认反映服务接流能力,并在响应体中返回 registry 子状态;如需把 registry 可达性也纳入 readiness 判定,可启用 registry.readiness_depends_on_registry = true

📝 许可证

MIT License - 详见 LICENSE

👥 贡献

欢迎提交 Issue 和 Pull Request!

About

No description, website, or topics provided.

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors