从Legacy到Hashed:GitLab 13.12.12升级前的存储迁移全流程实操手册
从Legacy到HashedGitLab 13.12.12升级前的存储迁移全流程实操手册当GitLab从13.x版本升级到14.x时存储架构发生了重大变革。传统存储Legacy Storage被废弃全面转向哈希存储Hashed Storage。这一变化不仅影响数据组织方式更直接关系到升级能否成功。本文将深入解析迁移全过程提供从准备到验证的完整解决方案。1. 理解存储架构变革哈希存储并非简单的格式转换而是GitLab为提升性能、增强安全性而设计的全新存储架构。与传统存储相比它具有以下核心优势目录结构优化项目不再按命名空间平铺而是通过SHA256哈希算法分散存储避免单个目录文件过多导致的性能问题权限管理简化每个项目拥有独立存储路径不再依赖上层目录的权限设置备份一致性消除硬链接带来的备份困扰确保数据完整性关键差异对比特性传统存储哈希存储项目路径/var/opt/gitlab/git-data/repositories/namespace/project/var/opt/gitlab/git-data/repositories/hashed/aa/bb/aabbcc...附件存储与项目同目录独立hashed路径跨项目移动需要重命名目录仅需更新数据库记录性能表现大命名空间下较差均衡分布稳定高效迁移前务必确认当前存储类型# 查看传统存储项目数量 sudo gitlab-rake gitlab:storage:legacy_projects # 列出所有传统存储项目 sudo gitlab-rake gitlab:storage:list_legacy_projects2. 预迁移环境准备成功的迁移始于周密的准备。建议按以下步骤搭建沙盒环境完整备份# 创建全量备份包含数据库和仓库 sudo gitlab-backup create STRATEGYcopy # 单独备份关键配置文件 cp /etc/gitlab/gitlab-secrets.json /backup/ cp /etc/gitlab/gitlab.rb /backup/资源检查确保磁盘空间至少为现有仓库大小的2倍内存建议4GB以上大型实例需8GB准备维护窗口每1万项目约需1小时服务状态确认# 检查后台任务队列 sudo gitlab-rake gitlab:background_migrations:status # 验证组件健康状态 sudo gitlab-ctl status | grep -v run: normal注意避免在CI/CD流水线运行高峰期执行迁移可能引发不可预知的冲突。3. 核心迁移操作流程3.1 基础迁移命令标准迁移流程看似简单sudo gitlab-rake gitlab:storage:migrate_to_hashed但实际场景中常遇到三类典型问题问题1假性成功Enqueuing migration of 41 projects in batches of 200. Done!多次执行仍显示相同输出但实际未完成迁移。解决方案# 进入数据库终端 sudo gitlab-rails dbconsole # 重置runner令牌GitLab 13.12已知问题 UPDATE projects SET runners_token null, runners_token_encrypted null; # 退出并重试迁移 \q sudo gitlab-rake gitlab:storage:migrate_to_hashed问题2只读项目阻塞后台迁移队列卡住通常因项目处于只读状态。诊断与修复# 进入Rails控制台 sudo gitlab-rails console # 查找并修改只读项目 Project.where(repository_read_only: true).each do |p| p.update!(repository_read_only: false) puts Unlocked project #{p.full_path} end问题3附件迁移失败传统存储的wiki附件、issue上传等需要单独处理# 强制重新迁移附件 sudo gitlab-rake gitlab:storage:migrate_to_hashed ATTACHMENTS_ONLYtrue3.2 分批迁移策略对于大型实例超过5000项目建议采用分批次迁移# 在Rails控制台中执行分批迁移 projects Project.with_unmigrated_storage batch_size 200 projects.each_slice(batch_size) do |batch| puts Migrating batch of #{batch_size} projects... batch.each { |p| p.storage_migrate_to_hashed } sleep 60 # 批次间隔 end4. 迁移后验证体系完整的验证应包含四个维度数量校验# 哈希存储项目数应与控制面板统计一致 sudo gitlab-rake gitlab:storage:hashed_projects # 传统存储项目数应为0 sudo gitlab-rake gitlab:storage:legacy_projects完整性检查# 随机抽样验证仓库完整性 sudo gitlab-rake gitlab:git:fsck权限测试使用不同权限用户执行git clone/push操作验证CI/CD流水线能否正常访问仓库性能基准# 迁移前后性能对比示例测试命令 ab -n 1000 -c 10 https://gitlab.example.com/group/project常见异常处理现象可能原因解决方案404错误NFS缓存未更新执行sudo gitlab-ctl restart nginxPush被拒hook未更新重新安装hookssudo gitlab-rake gitlab:shell:setupCI无法克隆runner令牌失效在项目设置中重置runner令牌5. 升级前最终检查清单执行正式升级前请逐项确认[ ] 所有传统存储项目已迁移legacy_projects返回0[ ] 后台迁移队列为空Admin Monitoring Background Jobs[ ] 数据库无挂起迁移sudo gitlab-rake db:migrate:status[ ] 备份验证通过测试备份恢复流程[ ] 性能监控基线已建立Prometheus/Grafana指标记录最后的安全确认命令# 综合检查GitLab 13.12 sudo gitlab-rake gitlab:storage:verify存储迁移是版本升级的关键前置步骤但并非终点。完成迁移后建议观察24小时再执行版本升级确保系统稳定运行。对于超大型实例10万项目可考虑联系GitLab专业服务团队获取定制化迁移方案。