代码库迁移 – Gitea 到 Gitee
下载地址
https://www.zhengdianxue.com/wp-content/uploads/skills/xzsmtech--gitea-to-gitee.zip将提示词发送给你的 AI 安装该 skills
请根据 https://skillhub.cn/install/skillhub.md,安装 @xzsmtech/gitea-to-gitee。- 将 Gitea 自部署平台上的代码仓库迁移到 Gitee。通过 `git clone –mirror` 镜像克隆 Gitea 源仓库,再用 `git push –mirror` 推送到 Gitee 目标仓库,保留所有分支与标签。传入 `https://` 形式的 URL 时,会自动转换为 `git@<
- host>
- :<
- path>
- ` 的 SSH 形式(丢弃嵌入 URL 的用户名/密码),并自动补全缺失的 `.git` 后缀
- 其余协议原样透传。迁移成功后,若 `transfer-tag/.env` 存在且合规,会调用 `transfer-tag/run.sh` 同步版本发布(release/tag 元数据)。假定本机已配置 git 鉴权(如 `~/.ssh/id_rsa`)。
阅读全文 (展开查看完整说明)
概述
gitea-to-gitee
将 Gitea 自部署平台上的代码仓库迁移到 Gitee,保留所有分支与标签。
使用方式
/gitea-to-gitee git@gitea.example.com:user/source-repo.git git@gitee.com:user/target-repo.git也支持 https:// 形式的 URL,skill 会自动将其转换为 git@<host>:<path> 的 SSH 形式(丢弃嵌入 URL 的用户名/密码),并自动补全缺失的 .git 后缀:
/gitea-to-gitee https://gitea.example.com/user/source-repo.git https://gitee.com/user/target-repo.git规范化后等价于:
git@gitea.example.com:user/source-repo.git → git@gitee.com:user/target-repo.git参数
$1— gitea-repo-url(必填):Gitea 源仓库克隆 URL,默认按 git 协议处理(如git@gitea.example.com:user/repo.git)。若传入https://形式,会自动转换为git@<host>:<path>的 SSH 形式(丢弃嵌入 URL 的用户名/密码);末尾缺失的.git会被自动补全。$2— gitee-repo-url(必填):Gitee 目标仓库克隆 URL(如git@gitee.com:user/repo.git)。URL 规范化规则与$1一致。
步骤
- 解析参数:从
$ARGUMENTS中取出源 URL($1)与目标 URL($2)。缺失任一参数时,打印用法并报错退出(非零退出码),不创建任何临时文件。 - URL 规范化:对
$1与$2分别执行以下规范化,结果赋给$GITEA_URL与$GITEE_URL,后续步骤一律使用这两个变量:- 协议转换:仅当 URL 以
https://开头时执行;其余协议(git@、ssh://、git://等)跳过本步。- 从
https://之后剥离掉嵌入的userinfo@(即https://user:token@host/...中的user:token@),避免把明文 token 带进 SSH URL。 - 取出
<host>与<path>,重组为git@<host>:<path>。
- 从
- 后缀补全:无论是否经过协议转换,若 URL 末尾不含
.git,自动追加.git。
- 协议转换:仅当 URL 以
- 镜像克隆 Gitea 源仓库:执行
git clone --mirror "$GITEA_URL" repo.git。克隆 Gitea 源仓库的完整镜像,包含所有分支、标签以及 Gitea 特有的refs/pull/<N>/head等 PR 引用。- 若克隆失败(退出码非 0),立即停止后续推送环节;保留
repo.git(若有部分产物)以便排查,并以非零退出码退出。
- 若克隆失败(退出码非 0),立即停止后续推送环节;保留
- 设置推送目标:进入
repo.git目录,执行git remote set-url --push origin "$GITEE_URL",将镜像仓库origin的 push URL 指向 Gitee 目标仓库。 - 镜像推送到 Gitee:执行
git push --mirror。- 用
|| true容忍非零退出码,让脚本继续往下走,不在这里直接判定迁移失败。 - 把该命令的 stdout/stderr 完整捕获下来,供下一步逐行分析。
- 用
- 判断推送结果:对
git push --mirror的输出按行扫描,做如下分类:- 凡是匹配
refs/pull/的行(典型形式:! [remote rejected] refs/pull/N/head (pre-receive hook declined)),归类为「PR refs 被拒,属预期内、可忽略」。 - 凡是
! [remote rejected]或error: failed to push some refs但不涉及refs/pull/*的行,归类为「真正失败」。 - 判定口径:
- 若所有失败/拒绝行均来自
refs/pull/*→ 视为迁移成功(分支、标签等已推送到位;PR refs 在 Gitee 上本就不应由外部推送)。 - 若存在任何非
refs/pull/*的拒绝/失败行 → 视为真正失败。
- 若所有失败/拒绝行均来自
- 凡是匹配
- 清理与现场保留:
- 成功路径(迁移成功 / 仅 PR refs 被忽略):执行
rm -rf repo.git删除临时镜像。 - 真正失败路径:不清理,保留
repo.git临时目录并输出其绝对路径,提示用户进入排查。
- 成功路径(迁移成功 / 仅 PR refs 被忽略):执行
- 报告结果:向用户输出汇总信息:
- 迁移成功时:打印源 URL → 目标 URL,并附上被忽略的
refs/pull/*列表(若有)供核对。 - 真正失败时:打印源 URL → 目标 URL、需排查的非 PR 类拒绝/失败行,以及保留的
repo.git绝对路径。
- 迁移成功时:打印源 URL → 目标 URL,并附上被忽略的
- release/tag 同步前置校验:仅当第 6 步判定为「迁移成功」时进入本环节。检查 skill 目录下
transfer-tag/.env:- 文件不存在,或
GITEA_URL、GITEA_TOKEN、GITEE_TOKEN三项中任一缺失/为空 → 视为不合规:报告「迁移成功,但 release/tag 同步已跳过(transfer-tag/.env 缺失或不合规)」,正常退出(退出码 0),迁移结果不受影响。 - 校验通过后,从
.env读取GITEA_TOKEN供后续步骤使用(不得在任何输出中回显其值)。
- 文件不存在,或
- 推导同步参数:从规范化后的
$GITEA_URL/$GITEE_URL中剥离末尾.git后缀,取路径的最后两段,分别得到 Gitea 与 Gitee 的owner/repo(如git@gitea.example.com:user/repo.git→user/repo)。 - 运行 transfer-tag 同步版本发布:执行
cd <skill目录>/transfer-tag && ./run.sh --gitea <gitea-owner/repo> --gitee <gitee-owner/repo>,将版本发布(release/tag 元数据)从 Gitea 同步到 Gitee。 - 判断同步结果:
run.sh退出码非零时:- 迁移本身仍照常报告为成功;
- 但须明确报告「release/tag 同步失败」,附上
run.sh的错误输出; - skill 最终以非零退出码退出,让调用方感知到部分失败。
- 退出码为 0 时,报告「迁移成功,release/tag 同步完成」及其结果摘要。
注意事项
- 假定本机已配置好 git 鉴权(SSH 私钥
~/.ssh/id_rsa,或对应平台的凭据)。 - 目标 Gitee 仓库需事先创建为空仓库:
git push --mirror会覆盖目标仓库的同名引用,目标仓库若有已有历史,相关 refs 会被拒或被覆盖。 - 默认不做 dry-run;如需预演可手动执行
git push --mirror --dry-run。 - release/tag 同步环节依赖 skill 目录下
transfer-tag/.env(含GITEA_URL、GITEA_TOKEN、GITEE_TOKEN真实凭据);.env缺失或不合规时跳过该环节并正常退出。.env中的 token 不得在任何输出中回显。 - 本 skill 会将
https://形式的源/目标 URL 自动转换为git@<host>:<path>的 SSH 形式(丢弃嵌入 URL 的用户名/密码),并自动补全缺失的.git后缀;其余协议(git@、ssh://、git://等)原样透传。
失败处理
- 克隆失败:立即退出,不进入推送环节;保留
repo.git(若有部分产物)以便排查。 - 推送失败(存在非
refs/pull/*的拒绝/失败行):保留repo.git临时目录并输出其绝对路径,提示用户检查 Gitee 仓库是否为空、鉴权是否正确、是否有非 PR 类 refs 被拒。 - 推送"失败"但全部源于
refs/pull/*被拒:视为成功,正常清理并报告(PR refs 在 Gitee 上本就不应由外部推送,分支、标签等已迁移完成)。