# git-code-sync **Repository Path**: rxbook/git-code-sync ## Basic Information - **Project Name**: git-code-sync - **Description**: 一个自托管的轻量 Web 工具:在两个本地 Git 仓库之间,以提交(commit)为粒度、人工可控地把「来源仓库」的提交逐个同步到「目标仓库」。 - **Primary Language**: Unknown - **License**: MIT - **Default Branch**: main - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 1 - **Forks**: 0 - **Created**: 2026-10-26 - **Last Updated**: 2026-10-27 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # Git提交同步工具箱 一个自托管的轻量 Web 工具:在**两个本地 Git 仓库**之间,以**提交(commit)为粒度**、人工可控地把「来源仓库」的提交逐个同步到「目标仓库」。 - 后端:Go 标准库,**零第三方依赖**,编译为单个可执行文件,前端通过 `embed` 内嵌。 - 前端:Vue 3 + Bootstrap 5,库文件随程序内置,**离线可用、不依赖 CDN**。 - 界面:手机 / 桌面自适应,随时随地用浏览器操作。 --- ## 一、背景与用途 现实开发中,代码的**实际完成时间**与希望呈现的**提交节奏**并不总是一致。例如: > 一个需求原计划 5 天完成,但后 4 天需要外出、无法随时使用电脑。于是可以在第 1 天集中把 5 天的工作全部做完,先放在一个「草稿仓库」里;之后在外出的几天里,用手机抽空打开本工具,每天把其中一部分提交同步到「正式仓库」。 这样,正式仓库的提交记录会呈现出**每天均匀、持续推进**的节奏,而不是某一天的集中爆发。 本工具要解决的正是「**Git 提交无法按计划、按节奏分批落地**」的问题。它不改变你写代码的方式,只把「草稿仓库 → 正式仓库」这一搬运过程变得可视化、可拆分、可在手机上随时进行。 --- ## 二、核心概念 | 概念 | 含义 | | --- | --- | | **来源仓库** | 数据来源(如提前写完的草稿仓库)。工具对它**只读**。 | | **目标仓库** | 写入对象(如对外展示的正式仓库)。同步的结果提交到这里。 | | **同步点(起始提交)** | 视为「已经同步到这里」的基准提交;工具从它**之后**的第一个提交开始。 | | **排除项** | 不参与同步的文件 / 文件夹(如临时文件、本地配置),在同步界面划线标注「已排除」。 | | **同步配置** | 一组「来源仓库 + 分支 + 同步点」对应「目标仓库 + 分支」的规则,可保存多条,进度各自独立保留。 | **同步方式是文件级搬运,而不是 `git cherry-pick`**:工具读取来源仓库某提交中的文件内容(blob),覆盖写入目标仓库工作区,再在目标仓库生成一条**全新的提交**。因此它可以: - 在**互不相关**的两个仓库之间工作(不要求共同祖先); - 对每个提交内的文件**逐个勾选**,决定本次同步哪些; - 跳过中间某些提交(其改动若未被后续覆盖,会随后续提交一起进入); - 自动沿用来源提交的备注,也可在提交前手动修改。 --- ## 三、三个功能页面 1. **本地仓库**:扫描本地仓库根路径,列出每个一级目录(即一个仓库)及其当前分支;并提供 SSH 密钥与接入引导。 2. **同步配置**:新建 / 编辑 / 删除同步规则——选择来源仓库、分支、起始提交(支持 commit ID 或备注关键词检索),选择目标仓库与分支(默认与来源相同),设置排除项。 3. **开始同步**:选择一条同步配置,查看「当前同步阶段」「下一步待同步」与本次文件清单、文件级改动明细;按需勾选后执行:**复制代码 → 提交 → 推送**,每一步都可撤销 / 回退。 > 若已存在同步配置,打开工具会默认进入「开始同步」并载入上次的配置与进度;切换配置后,下次继续使用新配置,各配置进度互不影响。 --- ## 四、快速开始 ### 1. 准备本地仓库(一次性) 工具不内置 clone 与密钥管理。根路径下的**每个一级目录就是一个仓库**,由你自行重命名标记;可直接 clone 或复制现有目录: ```bash ROOT=/root/code/rx/git-code-sync-remote-path cd $ROOT # 方式一:直接 clone(生成一级目录 demo) git clone git@gitee.com:alice/demo.git # 方式二:clone 后自定义仓库名 git clone git@gitee.com:alice/demo.git my-source # 方式三:复制已有项目目录 cp -r /path/to/project ./my-source ``` 多账号请在 `~/.ssh/config` 中用不同 Host 别名 + 不同密钥,详见工具内「本地仓库」页的接入引导。 ### 2. 构建 ```bash ./build.sh # 产物为 ./git-code-sync ``` ### 3. 配置(可选) 首次启动会自动生成 `data/config.json`;也可手动复制示例: ```bash cp deploy/config.example.json data/config.json ``` 关键配置项:`reposRoot`(本地仓库根路径)、`port`(默认 8770)、`password`(访问口令)、`basePath`(反代前缀,见下)。 ### 4. 以 systemd 常驻运行 ```bash # 先创建运行数据目录(systemd 命名空间要求该目录在启动前已存在) mkdir -p data sudo cp deploy/git-code-sync.service /etc/systemd/system/ sudo systemctl daemon-reload sudo systemctl enable --now git-code-sync systemctl status git-code-sync ``` > 若你修改了 `reposRoot`,请同步在 systemd 单元的 `ReadWritePaths` 中追加新路径。 ### 5. 用 Nginx 反代(推荐) 把 `deploy/nginx-git-code-sync.conf` 中的两个 `location` 块加入站点 `server{}`,然后: ```bash sudo nginx -t && sudo systemctl reload nginx ``` `proxy_pass` 结尾带 `/`(剥离前缀),因此 `data/config.json` 的 `basePath` 保持为空 `""`。 完成后访问:`http://<服务器IP>/git-code-sync/` > 健康检查:`./deploy/healthcheck.sh` --- ## 五、目录结构 ``` git-code-sync/ ├── main.go # 入口:路由、鉴权、启动、HTTP handler ├── config.go # 配置与运行期数据读写、排除规则 ├── git.go # 底层 Git 命令封装 ├── diff.go # 统一 diff 解析(含行内高亮) ├── repo.go # 本地仓库扫描 ├── sync.go # 同步配置与迁移清单 ├── sync_ops.go # 复制 / 提交 / 推送 / 撤销等操作 ├── build.sh # 构建脚本 ├── web/ │ ├── index.html # 单页应用(三个功能页) │ └── assets/ # 本地内置的 Bootstrap / Vue ├── deploy/ # 部署示例:systemd、nginx、健康检查、配置示例 ├── docs/ │ └── architecture.md # 架构设计文档 └── data/ # 运行期数据(不入库,自动生成) ├── config.json ├── syncConfigs.json ├── plan_.json ├── state_.json └── ops.log ``` --- ## 六、配置卫生(哪些内容不进入版本库) `data/` 整个目录与编译产物被 `.gitignore` 忽略,包含:访问口令、仓库清单、各配置的同步进度、操作日志。 - 配置示例见 `deploy/config.example.json`,运行数据结构示例见 `deploy/syncConfigs.example.json`。 - 代码与文档中**不写死任何具体仓库地址、账号或个人信息**;所有仓库均在页面上选择,根路径仅在配置中设置。 --- ## 七、安全说明 - 默认仅监听 `127.0.0.1:8770`,建议通过 Nginx 反代访问,不直接暴露。 - 若改为对外监听(`0.0.0.0`),**必须设置口令**,否则程序拒绝启动。 - 来源仓库始终只读;目标仓库工作区若有未提交改动,会阻止复制,避免覆盖你的在制内容。 - 已提交但未推送的提交可回退;一旦推送(对外公开),工具拒绝改写该历史。 - systemd 单元通过 `NoNewPrivileges`、`ReadWritePaths` 等限制可写范围,缩小被利用后的破坏面。 --- ## 八、工作原理(简述) 1. 依据同步配置,从「来源仓库 `origin/<分支>`」上、同步点之后列出待同步提交队列。 2. 对下一步提交,计算其相对同步点的文件增删改(`git diff --name-status`),标注排除项。 3. 【复制】把勾选中的文件:新增 / 修改则读取来源 blob 覆盖写入目标,删除则在目标移除。 4. 【提交】在目标仓库 `git add -A` 后,以来源提交备注(可改)生成一条全新提交。 5. 【推送】把目标分支推送到 `origin`,成功后推进同步点、更新进度。 完整设计见 [`docs/architecture.md`](docs/architecture.md)。