Skip to content

Latest commit

 

History

History
188 lines (134 loc) · 4.84 KB

File metadata and controls

188 lines (134 loc) · 4.84 KB

Git Bundle 增量同步完整解决方案

问题背景

你遇到的场景:

  1. 分支 inner 基于 master 的 A0 节点,开发了 A1, A2, A3, A4
  2. 已经将 A1-A3 打包成 bundle_A123 给同事C
  3. 同事B开发了B1并合并到master
  4. 你将A4 rebase到B1后变成:A0 → B1 → A1' → A2' → A3' → A4'
  5. 现在需要给同事C发送A4',但要避免重新传输A1', A2', A3'

解决方案概述

核心思路:创建增量bundle,只包含A4'这个新提交,充分利用同事C已有的bundle_A123。

具体操作步骤

第一步:你的操作(创建增量bundle)

# 1. 确保你在inner分支上
git checkout inner

# 2. 找到A3'的commit hash
git log --oneline -5
# 假设A3'的hash是 abc123

# 3. 使用脚本创建增量bundle
./create_incremental_bundle.sh -b abc123 -t inner -c

# 或者手动创建
git bundle create bundle_A4_only.bundle abc123..inner

第二步:发送给同事C

将生成的 bundle_A4_only.bundle(或压缩后的 .gz 文件)发送给同事C。

第三步:同事C的操作(应用增量bundle)

# 方法1:使用提供的脚本(推荐)
./apply_incremental_bundle.sh bundle_A4_only.bundle

# 方法2:手动操作
# 2.1 首先确保已经应用了之前的bundle_A123
git fetch bundle_A123.bundle refs/heads/inner:inner_base

# 2.2 应用新的增量bundle
git fetch bundle_A4_only.bundle refs/heads/inner:inner_updated

# 2.3 切换到更新后的分支
git checkout inner_updated

提供的工具脚本

1. create_incremental_bundle.sh - 创建增量bundle

功能特点

  • 自动验证提交点存在性
  • 显示将要打包的提交列表
  • 支持压缩输出
  • 提供详细的操作指导

使用示例

# 基本用法
./create_incremental_bundle.sh -b HEAD~1

# 指定目标分支和输出文件
./create_incremental_bundle.sh -b abc123 -t inner -o my_bundle.bundle

# 创建压缩的bundle
./create_incremental_bundle.sh -b abc123 -c

2. apply_incremental_bundle.sh - 应用增量bundle

功能特点

  • 自动验证bundle完整性
  • 支持预览模式查看内容
  • 可创建新分支或更新现有分支
  • 自动处理压缩文件

使用示例

# 基本用法
./apply_incremental_bundle.sh bundle_A4_only.bundle

# 预览bundle内容
./apply_incremental_bundle.sh --preview bundle_A4_only.bundle

# 创建新分支而不是更新现有分支
./apply_incremental_bundle.sh -n bundle_A4_only.bundle

高级技巧

1. 使用Git标签标记关键点

# 在创建bundle_A123时打标签
git tag -a sync_point_A123 A3_commit_hash -m "Sync point for bundle_A123"

# 基于标签创建增量bundle
./create_incremental_bundle.sh -b sync_point_A123

2. 验证bundle大小对比

# 创建完整bundle(对比用)
git bundle create bundle_full.bundle master..inner

# 创建增量bundle
./create_incremental_bundle.sh -b A3_hash

# 对比大小
ls -lh *.bundle

3. 处理复杂的rebase情况

如果rebase后的A1', A2', A3'与原来的A1, A2, A3差异很大:

# 方案1:基于共同祖先创建bundle
COMMON_ANCESTOR=$(git merge-base A3_original_hash A3_new_hash)
git bundle create bundle_from_common.bundle $COMMON_ANCESTOR..inner

# 方案2:使用cherry-pick方式
# 让同事C基于bundle_A123创建分支,然后应用A4'
git bundle create bundle_A4_cherry.bundle A4_hash^..A4_hash

故障排除

问题1:同事C应用bundle后出现冲突

# 检查当前状态
git status

# 查看冲突的文件
git diff

# 解决冲突后继续
git add .
git commit -m "Resolve conflicts from incremental bundle"

问题2:bundle验证失败

# 重新创建bundle
git bundle create new_bundle.bundle base_commit..target_branch

# 验证bundle
git bundle verify new_bundle.bundle

问题3:找不到基础提交点

# 查看详细的提交历史
git log --oneline --graph -20

# 或者使用reflog查找
git reflog show inner

最佳实践建议

  1. 记录同步点:每次创建bundle时记录base commit hash
  2. 使用描述性文件名:包含日期、分支名和版本信息
  3. 验证操作:在本地模拟同事的操作流程
  4. 备份重要分支:在应用bundle前创建备份分支
  5. 压缩传输:对于大文件使用压缩选项
  6. 文档化流程:团队内部建立标准的bundle同步流程

总结

这个解决方案通过创建增量bundle,有效解决了rebase后避免重复传输的问题。关键优势:

  • 大幅减少传输大小:只传输新的提交A4'
  • 保持完整历史:同事C可以完整重建分支历史
  • 操作简单:提供自动化脚本,减少人为错误
  • 灵活性高:支持多种应用方式和验证选项

通过这种方式,你可以高效地与内网同事同步代码,避免重复传输大量已同步的内容。