{"id":31197953,"url":"https://github.com/larch-c/fork-repo","last_synced_at":"2025-09-20T06:57:03.783Z","repository":{"id":307921720,"uuid":"1019600313","full_name":"Larch-C/fork-repo","owner":"Larch-C","description":"Fork multiple repositories in batch","archived":false,"fork":false,"pushed_at":"2025-08-26T09:11:23.000Z","size":172,"stargazers_count":1,"open_issues_count":0,"forks_count":1,"subscribers_count":0,"default_branch":"main","last_synced_at":"2025-08-26T10:34:26.478Z","etag":null,"topics":["action","actions"],"latest_commit_sha":null,"homepage":"","language":null,"has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Larch-C.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,"zenodo":null}},"created_at":"2025-07-14T15:21:08.000Z","updated_at":"2025-08-26T09:11:27.000Z","dependencies_parsed_at":null,"dependency_job_id":"bca8e73b-618b-443c-b18b-d51615825ade","html_url":"https://github.com/Larch-C/fork-repo","commit_stats":null,"previous_names":["larch-c/fork-repo"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/Larch-C/fork-repo","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Larch-C%2Ffork-repo","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Larch-C%2Ffork-repo/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Larch-C%2Ffork-repo/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Larch-C%2Ffork-repo/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Larch-C","download_url":"https://codeload.github.com/Larch-C/fork-repo/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Larch-C%2Ffork-repo/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":276058102,"owners_count":25577867,"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","status":"online","status_checked_at":"2025-09-20T02:00:10.207Z","response_time":63,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"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":["action","actions"],"created_at":"2025-09-20T06:57:02.467Z","updated_at":"2025-09-20T06:57:03.766Z","avatar_url":"https://github.com/Larch-C.png","language":null,"funding_links":[],"categories":[],"sub_categories":[],"readme":"# AstrBot 插件 Fork/Sync 工作流\n\n一个可批量 Fork 与同步 GitHub 仓库的工作流，支持批次处理、重试与超时保护、速率限制防护、冲突自动重命名，以及试运行模式与结果汇总报告。脚本已按 Job 分类拆分，便于维护与复用。\n\n## 特性\n\n- 批量处理仓库（默认每批 100 个），并行度可控（`max-parallel`）\n- 支持手动触发与定时任务，支持强制同步与试运行模式\n- 冲突自动处理：`rename`（自动重命名）、`skip`、`interactive`\n- 对关键操作增加重试与超时，增强稳定性\n- 自动生成结果表（Artifacts + Step Summary），包含统计与重命名明细\n- 脚本分层：`prepare`、`create-batches`、`fork-sync`、`collect-results`、`summary`\n\n## 快速开始\n\n1) 准备一个 Personal Access Token，命名为仓库 Secret：`GH_PAT`\n- 必须包含至少 `repo` 与 `workflow` 权限\n\n2) 配置触发方式与输入参数\n- 在 `.github/workflows/fork.yml` 中已默认开启 `workflow_dispatch` 与 `schedule`\n\n3) 运行\n- 在 Actions 页面选择该工作流，按需填写输入项并触发\n\n## 触发与输入\n\n工作流触发：\n- 手动：`workflow_dispatch`\n- 定时：`schedule`（默认每小时）\n\n可用输入（`workflow_dispatch.inputs`）：\n- `dry_run`（boolean，默认 `false`）：试运行，不执行实际 fork/sync，仅预览动作\n- `force_sync`（boolean，默认 `false`）：对已 fork 的仓库强制执行同步\n- `conflict_resolution`（choice，默认 `rename`）：重名冲突策略，可选 `skip` | `rename` | `interactive`\n\n环境变量：\n- `PLUGIN_JSON_URL`：包含插件列表的 JSON 地址（默认为 AstrBot 的 `plugins.json`）\n\nSecrets：\n- `GH_PAT`：GitHub Personal Access Token（需要 `repo`、`workflow` 权限）\n\n依赖：\n- 运行环境：`ubuntu-latest`\n- 预装工具（Actions Runner 已内置或可用）：`gh`、`jq`、`curl`\n\n## 目录结构（脚本分组）\n\n```text\n.github/\n  scripts/\n    prepare/\n      fetch_plugins.sh\n      parse_repo_list.sh\n    create-batches/\n      create_batches.sh\n    fork-sync/\n      setup_env.sh\n      setup_gh_cli.sh\n      verify_auth.sh\n      batch_delay.sh\n      process_batch_repos.sh\n    collect-results/\n      generate_results_table.sh\n      display_results_summary.sh\n    summary/\n      final_summary.sh\n```\n\n## 工作原理（Jobs）\n\n1) `prepare`\n- 下载 `plugins.json` 并解析仓库列表，产出：\n  - `steps.list.outputs.repos`：去重后的仓库数组（JSON 字符串）\n  - `steps.list.outputs.total_count`：仓库总数\n\n2) `create-batches`\n- 将仓库均分为批次（默认每批 100），产出：\n  - `steps.batch.outputs.batches`：批次数组（含 `batch_id` 与 `repos`）\n  - `steps.batch.outputs.batch_count`：批次数量\n\n3) `fork-sync`（矩阵并行执行）\n- 对每个批次：\n  - 登录 `gh`（使用 `GH_PAT`）\n  - 防抖延迟（随批次递增）以降低 Rate Limit 风险\n  - 遍历批次内仓库：\n    - 检查原仓库存在性\n    - 检查是否已有有效 fork\n    - 根据输入策略执行 fork 或同步\n    - 失败/超时场景做重试与错误归类\n  - 生成每个仓库的 JSON 结果文件并上传为 Artifact（分批）\n\n4) `collect-results`\n- 下载所有批次的结果 JSON，生成 `results_summary.md` 并上传 Artifact，同时输出到 Step Summary\n\n5) `summary`\n- 汇总整次运行的关键指标与说明到 Step Summary\n\n## 使用示例（手动触发）\n\n```yaml\nname: Fork/Sync Plugins\n\non:\n  workflow_dispatch:\n    inputs:\n      dry_run:\n        type: boolean\n        default: false\n      force_sync:\n        type: boolean\n        default: false\n      conflict_resolution:\n        type: choice\n        default: rename\n        options: [skip, rename, interactive]\n\njobs:\n  call:\n    uses: your-org/your-repo/.github/workflows/fork.yml@main\n    secrets: inherit\n```\n\n\u003e 如果想作为“可复用工作流”在其他仓库调用，建议在本工作流的 `on:` 中添加 `workflow_call:` 并为各输入定义 schema，然后如上通过 `uses:` 语法引用。\n\n## 结果与报告\n\n- 每个仓库生成一份 JSON 结果（包含状态、信息、时间戳、是否重命名等）\n- 汇总报告 `results_summary.md` 会：\n  - 以 Artifact 形式上传（名称：`fork-sync-results`）\n  - 同时追加到 Step Summary，便于直接在页面查看\n\n## 速率限制与稳定性\n\n- 每个批次在开始前按批次编号增加延迟（`batch_id * 15s`）\n- 关键 API 操作均设置超时（`timeout`）与最多 3 次重试\n- 批次和仓库间穿插固定 sleep，进一步降低被限速概率\n- 并发控制通过 `strategy.max-parallel` 实现\n\n## 常见问题\n\n1) 能否只用 `GITHUB_TOKEN` 而不用 `GH_PAT`？\n- 不建议。`GITHUB_TOKEN` 是当前仓库作用域，无法在你的用户命名空间创建 fork；故使用具备 `repo` 与 `workflow` 权限的 `GH_PAT` 更可靠。\n\n2) `plugins.json` 中的仓库地址支持哪些形式？\n- 支持 `https://github.com/owner/repo[.git]`，会自动去掉 `/tree/...`、`/blob/...` 与 `.git` 后缀并做唯一化。\n\n3) 为什么要分批？\n- 降低并发、控制速率、提升成功率；同时便于在失败时部分重试与问题定位。\n\n## 许可\n\n本仓库遵循仓库内 `LICENSE` 文件所述协议。\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flarch-c%2Ffork-repo","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Flarch-c%2Ffork-repo","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flarch-c%2Ffork-repo/lists"}