{"id":17247132,"url":"https://github.com/kevingong2013/apkgo","last_synced_at":"2026-05-04T05:01:42.728Z","repository":{"id":66748770,"uuid":"603385700","full_name":"KevinGong2013/apkgo","owner":"KevinGong2013","description":"快速将apk更新至各个平台","archived":false,"fork":false,"pushed_at":"2024-06-21T02:42:07.000Z","size":1157,"stargazers_count":29,"open_issues_count":4,"forks_count":5,"subscribers_count":2,"default_branch":"main","last_synced_at":"2025-03-27T19:41:55.933Z","etag":null,"topics":["andoird","app","fastlane"],"latest_commit_sha":null,"homepage":"https://apkgo.com.cn","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/KevinGong2013.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-02-18T10:55:42.000Z","updated_at":"2025-01-13T03:24:11.000Z","dependencies_parsed_at":"2024-06-21T01:07:31.175Z","dependency_job_id":"df09777e-529c-4c13-bc8a-ed1d56357e0b","html_url":"https://github.com/KevinGong2013/apkgo","commit_stats":{"total_commits":115,"total_committers":2,"mean_commits":57.5,"dds":0.008695652173912993,"last_synced_commit":"19510352e5c02bc96c61ffca0537dac3f7c5ca40"},"previous_names":[],"tags_count":24,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/KevinGong2013%2Fapkgo","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/KevinGong2013%2Fapkgo/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/KevinGong2013%2Fapkgo/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/KevinGong2013%2Fapkgo/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/KevinGong2013","download_url":"https://codeload.github.com/KevinGong2013/apkgo/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248826586,"owners_count":21167716,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["andoird","app","fastlane"],"created_at":"2024-10-15T06:36:27.208Z","updated_at":"2026-04-29T09:09:08.779Z","avatar_url":"https://github.com/KevinGong2013.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"# apkgo\n\n![GitHub release](https://img.shields.io/github/v/release/KevinGong2013/apkgo) ![build](https://img.shields.io/github/actions/workflow/status/kevingong2013/apkgo/release.yml?style=flat-square) ![go](https://img.shields.io/github/go-mod/go-version/kevingong2013/apkgo?style=flat-square) ![license](https://img.shields.io/github/license/kevingong2013/apkgo?style=flat-square)\n\n一行命令，将 APK 发布到所有主流安卓应用商店。为 CI/CD 和 AI Agent 设计。\n\n## 支持的商店\n\n| 商店 | 认证方式 |\n|------|---------|\n| 华为 AppGallery | OAuth2 |\n| 小米开放平台 | RSA 签名 |\n| OPPO 开放平台 | HMAC-SHA256 |\n| vivo 开放平台 | HMAC-SHA256 |\n| 荣耀开发者平台 | OAuth2 |\n| 腾讯应用宝 | HMAC-SHA256 |\n| Google Play | Service Account JWT |\n| Samsung Galaxy Store | Service Account JWT |\n| 蒲公英 (Pgyer) | API Key |\n| fir.im | API Token |\n| 脚本 (Script) | 自定义脚本 |\n\n## 为什么不直接用「应用生态联盟」一键多发？\n\n[中国安卓应用生态联盟](https://www.appchinaalliance.org)（华为/小米/OPPO/vivo 等共同发起）提供过\"一次上传同步到多家商店\"的能力。听起来很方便，但一旦你严肃发版就会撞到下面这些限制 —— 这也是 apkgo 选择直接调用每家商店原生 API 的原因：\n\n| 痛点 | 联盟同步 | apkgo 直发 |\n|------|---------|------------|\n| **同步时间** | 不可控，少则数小时多则数天，等一家慢的拖累整体 | 各家并发，整体时间 ≈ 最慢那一家的 API 时间 |\n| **过程可观测** | 看不到每家具体进度，出问题靠\"等\" | 每家结构化 JSON 状态码 + 错误消息直出 |\n| **差异化包** | 强制同包，不支持给不同商店投不同 APK（渠道号、签名、白名单功能） | 每家可单独传，`--file` / `--file64` / 渠道包灵活组合 |\n| **撤回 / 下架** | 联盟统一控制，无法只撤回某一家 | 每家用自己后台/脚本独立处理，apkgo 只管发不管控 |\n| **凭证归属** | 凭证集中在联盟方 | 凭证留在自家 CI，每家商店只看到自己的 token |\n| **可审计** | 上传历史散落在联盟系统 | 你的 CI 日志就是发布日志 |\n\n简单总结：联盟方案是为\"图省事\"设计的，apkgo 是为\"自己说了算\"设计的。如果你只是偶尔丢个内部测试包，联盟够用；如果你要做正经发布、自动化、多渠道、版本回滚，原生 API + apkgo 才是可行路径。\n\n## 安装\n\n```bash\n# AI Agent Skill (支持 Claude Code、Cursor、Windsurf 等 40+ agent)\nnpx skills add KevinGong2013/apkgo\n\n# macOS (Apple Silicon)\ncurl -fsSL https://github.com/KevinGong2013/apkgo/releases/latest/download/apkgo_Darwin_arm64.tar.gz | tar xz -C /usr/local/bin apkgo\n\n# macOS (Intel)\ncurl -fsSL https://github.com/KevinGong2013/apkgo/releases/latest/download/apkgo_Darwin_x86_64.tar.gz | tar xz -C /usr/local/bin apkgo\n\n# Linux (x86_64)\ncurl -fsSL https://github.com/KevinGong2013/apkgo/releases/latest/download/apkgo_Linux_x86_64.tar.gz | tar xz -C /usr/local/bin apkgo\n\n# Linux (arm64)\ncurl -fsSL https://github.com/KevinGong2013/apkgo/releases/latest/download/apkgo_Linux_arm64.tar.gz | tar xz -C /usr/local/bin apkgo\n\n# Windows (PowerShell)\n# 从 https://github.com/KevinGong2013/apkgo/releases/latest 下载 apkgo_Windows_x86_64.zip\n# 解压后将 apkgo.exe 添加到 PATH\n\n# Go\ngo install github.com/KevinGong2013/apkgo@latest\n\n# Docker\ndocker pull ghcr.io/kevingong2013/apkgo:latest\n```\n\n## 快速开始\n\n```bash\n# 1. 生成配置文件\napkgo init\n\n# 2. 填写商店凭证\nvim apkgo.yaml\n\n# 3. 上传\napkgo upload -f app.apk\n```\n\n## 用法\n\n### 上传\n\n```bash\n# 上传到所有配置的商店\napkgo upload -f app.apk\n\n# 上传到指定商店\napkgo upload -f app.apk --store huawei,xiaomi\n\n# 带更新日志\napkgo upload -f app.apk --notes \"修复了登录问题\"\napkgo upload -f app.apk --notes-file CHANGELOG.md\n\n# 分架构包\napkgo upload -f app-arm32.apk --file64 app-arm64.apk\n\n# 只验证不上传\napkgo upload -f app.apk --dry-run\n```\n\n### 初始化配置\n\n```bash\n# 生成包含所有商店的配置\napkgo init\n\n# 只生成指定商店的配置\napkgo init --store huawei,xiaomi\n\n# 指定配置文件路径\napkgo init -c production.yaml\n```\n\n### 查看支持的商店\n\n```bash\napkgo stores\n```\n\n### 体检（验证商店配置）\n\n`doctor` 在不上传文件的前提下，校验已配置商店的凭证和权限是否到位，避免真实上传到一半才发现问题：\n\n```bash\n# 校验所有已配置商店的凭证\napkgo doctor\n\n# 只校验指定商店\napkgo doctor -s huawei\n\n# 提供包名后会跑更深入的检查（包名映射、发布权限等）\napkgo doctor -s huawei -p com.example.app\napkgo doctor -s huawei -f app.apk         # 从 APK 自动取包名\n```\n\n任一探针失败时，退出码为 1。目前 Huawei 已支持，其他商店标记为 `doctor not implemented`。\n\n## 配置文件\n\n`apkgo.yaml`:\n\n```yaml\n# hooks 为可选配置，不需要可以不写\nhooks:\n  before: \"./scripts/validate.sh\"          # 所有上传前执行\n  after: \"./scripts/notify.sh\"             # 所有上传后执行\n\nstores:\n  huawei:\n    # 推荐：服务账号（PS256 JWT）\n    service_account_file: \"/secure/path/huawei-sa.json\"\n    # 或者: service_account: \"\u003cbase64(JSON)\u003e\"\n    # app_id: \"\"  # 可选，不填则自动通过包名查询\n    before: \"./scripts/before-huawei.sh\"   # 可选，该商店上传前执行\n    after: \"./scripts/after-huawei.sh\"     # 可选，该商店上传后执行\n\n  xiaomi:\n    email: \"your@email.com\"\n    private_key: \"your-private-key\"             # 小米后台的「接口密钥」（被 SDK 当作 password 使用）\n    cert_file: \"/secure/path/xiaomi-pubkey.cer\" # 公钥证书（也支持 cert: \u003cPEM 内容\u003e 或 cert: \u003cbase64\u003e）\n\n  oppo:\n    client_id: \"your-client-id\"        # 19 位数字\n    client_secret: \"your-client-secret\"\n\n  vivo:\n    access_key: \"your-access-key\"\n    access_secret: \"your-access-secret\"\n\n  honor:\n    client_id: \"your-client-id\"\n    client_secret: \"your-client-secret\"\n    app_id: \"your-app-id\"\n\n  tencent:\n    user_id: \"your-user-id\"\n    access_secret: \"your-access-secret\"\n    app_id: \"your-app-id\"\n    # 多 app: app_id_map: '{\"com.foo\":\"111\",\"com.bar\":\"222\"}'\n\n  pgyer:\n    api_key: \"your-pgyer-api-key\"\n\n  fir:\n    api_token: \"your-fir-api-token\"\n\n  # 单个脚本\n  script:\n    command: \"./deploy.sh\"\n\n  # 多个脚本实例 (script.实例名)\n  script.cdn-upload:\n    command: \"./upload-cdn.sh\"\n  script.dingtalk:\n    command: \"./notify-dingtalk.sh\"\n```\n\n#### Hooks 说明\n\nHooks 是可选功能，不配置则不生效。Hook 脚本通过 stdin 接收 JSON 上下文，通过退出码控制流程：\n\n- `before` hook 失败（非零退出码）→ 中止上传\n- `after` hook 失败 → 仅记录警告，不影响结果\n- 自动注入环境变量：`APKGO_STORE`、`APKGO_PACKAGE`、`APKGO_VERSION`\n- stderr 输出作为错误信息\n\n**全局 before hook** (`hooks.before`) stdin：\n\n```json\n{\n  \"file_path\": \"/path/to/app.apk\",\n  \"apk\": {\"package\": \"com.example.app\", \"version_name\": \"1.0.0\", \"version_code\": 1, \"app_name\": \"MyApp\"},\n  \"stores\": [\"huawei\", \"xiaomi\"]\n}\n```\n\n**全局 after hook** (`hooks.after`) stdin：\n\n```json\n{\n  \"file_path\": \"/path/to/app.apk\",\n  \"apk\": {\"package\": \"com.example.app\", \"version_name\": \"1.0.0\", \"version_code\": 1, \"app_name\": \"MyApp\"},\n  \"results\": [\n    {\"store\": \"huawei\", \"success\": true, \"duration_ms\": 12300},\n    {\"store\": \"xiaomi\", \"success\": false, \"error\": \"auth failed\", \"duration_ms\": 400}\n  ]\n}\n```\n\n**商店 before hook** (`stores.\u003cname\u003e.before`) stdin：\n\n```json\n{\n  \"file_path\": \"/path/to/app.apk\",\n  \"apk\": {\"package\": \"com.example.app\", \"version_name\": \"1.0.0\", \"version_code\": 1, \"app_name\": \"MyApp\"},\n  \"store\": \"huawei\"\n}\n```\n\n**商店 after hook** (`stores.\u003cname\u003e.after`) stdin：\n\n```json\n{\n  \"file_path\": \"/path/to/app.apk\",\n  \"apk\": {\"package\": \"com.example.app\", \"version_name\": \"1.0.0\", \"version_code\": 1, \"app_name\": \"MyApp\"},\n  \"store\": \"huawei\",\n  \"result\": {\"store\": \"huawei\", \"success\": true, \"duration_ms\": 12300}\n}\n```\n\nHook 脚本示例（上传完成后发送钉钉通知）：\n\n```bash\n#!/bin/bash\ninput=$(cat)\nresults=$(echo \"$input\" | jq -r '.results[] | \"\\(.store): \\(if .success then \"✓\" else \"✗ \"+.error end)\"')\ncurl -s -X POST \"$DINGTALK_WEBHOOK\" \\\n  -H \"Content-Type: application/json\" \\\n  -d \"{\\\"msgtype\\\":\\\"text\\\",\\\"text\\\":{\\\"content\\\":\\\"APK 发布完成 v${APKGO_VERSION}\\n${results}\\\"}}\"\n```\n\n### 环境变量\n\nCI/CD 环境中可通过环境变量配置凭证，无需配置文件：\n\n```bash\n# 格式: APKGO_\u003c商店名\u003e_\u003c字段名\u003e=值\nexport APKGO_HUAWEI_SERVICE_ACCOUNT=\"$(base64 -w0 huawei-sa.json)\"  # 推荐\nexport APKGO_XIAOMI_EMAIL=\"your@email.com\"\nexport APKGO_XIAOMI_PRIVATE_KEY=\"your-接口密钥\"\nexport APKGO_XIAOMI_CERT=\"$(base64 -w0 xiaomi-pubkey.cer)\"\nexport APKGO_OPPO_CLIENT_ID=\"your-19-digit-id\"\nexport APKGO_OPPO_CLIENT_SECRET=\"your-secret\"\nexport APKGO_VIVO_ACCESS_KEY=\"your-key\"\nexport APKGO_VIVO_ACCESS_SECRET=\"your-secret\"\nexport APKGO_TENCENT_USER_ID=\"your-user-id\"\nexport APKGO_TENCENT_ACCESS_SECRET=\"your-secret\"\nexport APKGO_TENCENT_APP_ID=\"your-app-id\"\n# 多 app: APKGO_TENCENT_APP_ID_MAP='{\"com.foo\":\"111\",\"com.bar\":\"222\"}'\nexport APKGO_PGYER_API_KEY=\"your-pgyer-key\"\nexport APKGO_FIR_API_TOKEN=\"your-fir-token\"\n\n# 环境变量会覆盖配置文件中的同名字段\n# 如果没有配置文件，完全通过环境变量配置也可以\napkgo upload -f app.apk --store huawei\n```\n\n### 凭证获取指南\n\n| 商店 | 控制台地址 | 说明 |\n|------|-----------|------|\n| 华为 | [AppGallery Connect](https://developer.huawei.com/consumer/cn/console) | 用户与权限 \u003e 服务账号（[详细步骤](#华为-appgallery-connect)） |\n| 小米 | [小米开放平台](https://dev.mi.com) | 账号管理 \u003e 接口密钥（[详细步骤](#小米开放平台)） |\n| OPPO | [OPPO 开放平台](https://open.oppomobile.com) | 管理中心 \u003e API 密钥管理（[详细步骤](#oppo-开放平台)） |\n| vivo | [vivo 开放平台](https://dev.vivo.com.cn) | 账号管理 \u003e API 接入（[详细步骤](#vivo-开放平台)） |\n| 荣耀 | [荣耀开发者平台](https://developer.honor.com) | API 管理（[详细步骤](#荣耀开发者平台)） |\n| 腾讯 | [腾讯开放平台](https://app.open.qq.com) | 应用 \u003e 账户管理 \u003e API 发布接口 \u003e 申请开通（[详细步骤](#腾讯应用宝)） |\n| 蒲公英 | [pgyer.com](https://www.pgyer.com/account/api) | 账户设置 \u003e API 密钥（[详细步骤](#蒲公英-pgyer)） |\n| fir.im | [betaqr.com.cn](https://www.betaqr.com.cn) | 账户 \u003e API Token（[详细步骤](#firim)） |\n\n每家的凭证申请流程都以官方文档为准（链接见下文），README 这边只描述 **apkgo 特有的事**：要哪几个字段、`doctor` 怎么验、需要注意的非显然行为。\n\n#### 华为 AppGallery Connect\n\n📖 官方文档：[Service Account 接入介绍](https://developer.huawei.com/consumer/cn/doc/AppGallery-connect-Guides/agcapi-getstarted-0000001111845114#section1785535363715)\n\n推荐用**开发者级**服务账号（PS256 JWT 鉴权），不要选项目级——访问发布 API 会被拒。下载到的 JSON 凭证文件直接交给 apkgo：\n\n```yaml\nstores:\n  huawei:\n    service_account_file: \"/secure/path/huawei-sa.json\"\n    # 或 base64(JSON) 内联：service_account: \"ewogICJrZXlfaWQiOiAi...\"\n```\n\n旧版 `client_id` + `client_secret` 仍兼容，但华为已不推荐。\n\n```bash\napkgo doctor -s huawei -p com.example.app\n```\n\n3 项探针：`token` / `appid-list`（包名 → appId）/ `release-permission`（应用发布权限）。\n\n#### 小米开放平台\n\n📖 官方文档：[API 上传应用](https://dev.mi.com/xiaomihyperos/documentation/detail?pId=1134)\n\n要在小米后台「接口密钥」页面拿两样东西：**接口密钥**（SDK 里叫 password）和**公钥证书**（`.cer` 文件）。两个都是开发者账号绑定的。\n\n```yaml\nstores:\n  xiaomi:\n    email: \"\u003c开发者账号邮箱\u003e\"\n    private_key: \"\u003c接口密钥\u003e\"\n    cert_file: \"/secure/path/xiaomi-pubkey.cer\"\n    # 也支持: cert: \"-----BEGIN CERTIFICATE-----...\" 或 base64(.cer)\n```\n\n```bash\napkgo doctor -s xiaomi -p com.example.app\n```\n\n\u003e ⚠️ apkgo v3.0 之前内置了一份公钥证书，但那份 **2023-05 已过期**（且来源不明），从 v3.0 起必须自己提供。\n\n#### OPPO 开放平台\n\n📖 官方文档：[发布接口接入指引](https://open.oppomobile.com/new/developmentDoc/info?id=10998)\n\n```yaml\nstores:\n  oppo:\n    client_id: \"\u003c19 位数字\u003e\"\n    client_secret: \"\u003c密钥\u003e\"\n```\n\n```bash\napkgo doctor -s oppo -p com.example.app\n```\n\nOPPO 的发布是异步任务，apkgo 会自动处理两个非显然的状态：撞 `911216 任务处理中` 时跳过 publish 直接等任务结束；撞 `911215 应用审核中` 视为成功（已进入审核队列）。\n\n#### vivo 开放平台\n\n📖 官方文档：[开放接口指引](https://dev.vivo.com.cn/documentCenter/doc/326)\n\n```yaml\nstores:\n  vivo:\n    access_key: \"\u003c...\u003e\"\n    access_secret: \"\u003c...\u003e\"\n```\n\n```bash\napkgo doctor -s vivo -p com.example.app\n```\n\nvivo 的错误码分两层：网关 `code` + 业务 `subCode`。apkgo 同时识别两层，错误信息直接打印中文消息（比如 `[15042] 请上传与历史签名一致的APK包...`）。\n\n#### 荣耀开发者平台\n\n📖 官方文档：[发布接口指南](https://developer.honor.com/cn/doc/guides/101159)\n\n```yaml\nstores:\n  honor:\n    client_id: \"\u003c...\u003e\"\n    client_secret: \"\u003c...\u003e\"\n    # app_id: \"\"  # 可选，不填则按 APK 包名自动查\n```\n\n```bash\napkgo doctor -s honor -p com.example.app\n```\n\ndoctor `app-detail` 探针会预检 *应用简介*（intro）—— 这个字段在荣耀后台必须填，否则 `update-language-info` 会以 `[20076] app introduction is empty` 拒绝。先在控制台填好再发版。\n\n#### 腾讯应用宝\n\n📖 官方文档：[API 接口传包-接入介绍](https://wikinew.open.qq.com/index.html#/iwiki/4015262492)\n\n腾讯没有 list 或 pkg→id 反查接口，所以 `app_id` 必须手填。一份 yaml 服务多个应用用 `app_id_map`：\n\n```yaml\nstores:\n  tencent:\n    user_id: \"\u003c开发者 ID\u003e\"\n    access_secret: \"\u003c接口密钥\u003e\"\n    # 单 app:\n    app_id: \"\u003c应用 ID\u003e\"\n    # 多 app: 按 APK 包名命中\n    # app_id_map: '{\"com.example.foo\":\"111\",\"com.example.bar\":\"222\"}'\n```\n\n```bash\napkgo doctor -s tencent -p com.example.app\n```\n\n发布是异步任务，apkgo 会轮询 `query_app_update_status` 直到 `audit_status` 终态（最长 5 分钟）；超时视为成功（任务已交给腾讯）。\n\n#### 蒲公英 (Pgyer)\n\n📖 官方文档：[API 上传应用](https://www.pgyer.com/doc/view/app_upload)\n\n```yaml\nstores:\n  pgyer:\n    api_key: \"\u003c...\u003e\"\n```\n\n```bash\napkgo doctor -s pgyer -p com.example.app\n```\n\n#### fir.im\n\n📖 官方文档：[betaqr.com.cn/docs](https://www.betaqr.com.cn/docs)\n\n```yaml\nstores:\n  fir:\n    api_token: \"\u003c...\u003e\"\n```\n\n```bash\napkgo doctor -s fir\n```\n\n\u003e ⚠️ **fir 上传要求账号已完成实名认证**，否则 `/apps` 接口会以 `没有实名认证不能上传app` 拒绝。先去后台做实名再用。\n\n## AI Agent 集成\n\napkgo 的输出格式专为 AI Agent 和自动化场景设计：\n\n**结构化 JSON 输出** (stdout):\n```json\n{\n  \"apk\": {\"package\": \"com.example.app\", \"version_name\": \"1.0.0\", \"version_code\": 1},\n  \"results\": [\n    {\"store\": \"huawei\", \"success\": true, \"duration_ms\": 12300},\n    {\"store\": \"xiaomi\", \"success\": false, \"error\": \"invalid private key\", \"duration_ms\": 400}\n  ]\n}\n```\n\n**语义化退出码**:\n| Code | 含义 |\n|------|------|\n| 0 | 全部成功 |\n| 1 | 部分失败 |\n| 2 | 全部失败 |\n| 3 | 输入错误 |\n\n**可发现的配置 schema**:\n```bash\napkgo stores  # 返回每个商店需要的配置字段\n```\n\n**非交互**: 无 prompt、无确认，适合无人值守环境。\n\n## CI/CD 示例\n\n### GitHub Actions\n\n```yaml\n- name: Upload to app stores\n  env:\n    APKGO_HUAWEI_SERVICE_ACCOUNT: ${{ secrets.HUAWEI_SERVICE_ACCOUNT }}  # base64(JSON 凭证)\n    APKGO_XIAOMI_EMAIL: ${{ secrets.XIAOMI_EMAIL }}\n    APKGO_XIAOMI_PRIVATE_KEY: ${{ secrets.XIAOMI_PRIVATE_KEY }}\n    APKGO_XIAOMI_CERT: ${{ secrets.XIAOMI_CERT }}             # base64(.cer 文件)\n    APKGO_OPPO_CLIENT_ID: ${{ secrets.OPPO_CLIENT_ID }}\n    APKGO_OPPO_CLIENT_SECRET: ${{ secrets.OPPO_CLIENT_SECRET }}\n    APKGO_VIVO_ACCESS_KEY: ${{ secrets.VIVO_ACCESS_KEY }}\n    APKGO_VIVO_ACCESS_SECRET: ${{ secrets.VIVO_ACCESS_SECRET }}\n    APKGO_TENCENT_USER_ID: ${{ secrets.TENCENT_USER_ID }}\n    APKGO_TENCENT_ACCESS_SECRET: ${{ secrets.TENCENT_ACCESS_SECRET }}\n    APKGO_TENCENT_APP_ID_MAP: ${{ secrets.TENCENT_APP_ID_MAP }}     # 多 app: '{\"com.foo\":\"111\",...}'\n  run: |\n    apkgo upload \\\n      -f app/build/outputs/apk/release/app-release.apk \\\n      --notes-file CHANGELOG.md \\\n      --store huawei,xiaomi,oppo,vivo,tencent \\\n      --timeout 15m\n```\n\n### Docker\n\n```bash\ndocker run --rm \\\n  -v $(pwd)/apkgo.yaml:/apkgo.yaml \\\n  -v $(pwd)/app.apk:/app.apk \\\n  ghcr.io/kevingong2013/apkgo:latest \\\n  upload -f /app.apk --notes \"Bug fixes\"\n```\n\n## Web GUI\n\n不想用命令行？`apkgo serve` 启动本地 Web 界面：\n\n```bash\napkgo serve                    # http://localhost:8080\napkgo serve -p 9090            # 自定义端口\napkgo serve -c production.yaml # 指定配置文件\n```\n\n打开浏览器，拖拽 APK、勾选商店、填写更新日志、点击上传。适合运营人员使用。\n\n## 跨机器同步配置\n\n通过加密导出/导入，安全地在多台机器或 CI 间共享商店凭证：\n\n```bash\n# 机器 A：加密导出\napkgo config export --out config.enc\n# 输入密码（或设置 APKGO_CONFIG_KEY 环境变量）\n\n# 提交到私有仓库\ngit add config.enc \u0026\u0026 git commit -m \"sync config\" \u0026\u0026 git push\n\n# 机器 B：解密导入\ngit pull\napkgo config import config.enc\n```\n\nCI 中使用环境变量免交互：\n\n```yaml\n- name: Import apkgo config\n  env:\n    APKGO_CONFIG_KEY: ${{ secrets.APKGO_CONFIG_KEY }}\n  run: apkgo config import config.enc\n```\n\n加密方式：AES-256-GCM + scrypt 密钥派生，密码错误会明确提示。\n\n## 全部命令\n\n```\napkgo init          [-s store1,store2] [-c config.yaml]\napkgo upload        -f \u003capk\u003e [--file64 \u003capk\u003e] [-s stores] [-n notes] [--notes-file path] [--dry-run] [-t timeout]\napkgo doctor        [-s stores] [-f \u003capk\u003e | -p \u003cpackage\u003e]\napkgo serve         [-p port] [-c config.yaml]\napkgo config export --out \u003cfile\u003e\napkgo config import \u003cfile\u003e\napkgo stores        [-o json|text]\napkgo history       [-n limit]\napkgo upgrade\napkgo version       [-o json|text]\n```\n\n## 全局参数\n\n```\n-c, --config        配置文件路径 (默认: apkgo.yaml)\n-o, --output        输出格式: json 或 text (默认: json)\n-t, --timeout       全局超时 (默认: 10m)\n-v, --verbose       详细日志输出到 stderr\n    --no-telemetry  禁用匿名使用统计\n```\n\n## 隐私\n\napkgo 收集匿名使用统计以改进产品，**不收集任何敏感信息**：\n\n| 收集 | 不收集 |\n|------|--------|\n| 匿名安装 ID (随机 UUID) | 账号、凭证 |\n| 使用的商店名称 | 包名、应用名 |\n| 上传成功/失败 | APK 文件内容 |\n| CLI/GUI 使用方式 | 更新日志内容 |\n| apkgo 版本、OS/架构 | IP 地址 |\n\n关闭方式：`--no-telemetry` 或 `APKGO_TELEMETRY=off`\n\n## License\n\n[Apache License 2.0](./LICENSE)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fkevingong2013%2Fapkgo","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fkevingong2013%2Fapkgo","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fkevingong2013%2Fapkgo/lists"}