如何在本地缩小远程.git文件夹后更新它

Posted

技术标签:

【中文标题】如何在本地缩小远程.git文件夹后更新它【英文标题】:How to update remote .git folder after shrinking it locally 【发布时间】:2022-01-14 15:51:47 【问题描述】:

我正在清理一个 gitlab 存储库,其中显然有一些 非常 大文件在某一时刻提交,导致 .git 文件夹高达 7.5gb。我按照this guide 了解如何缩小文件夹并重写提交历史记录,并在我的本地计算机上成功地将文件夹减小到 1.1gb。我意识到这仍然很大,但此时我只想更新远程存储库,然后再继续尝试查看它是否可以进一步缩小。

我的问题是,推送后,远程.git文件夹没有改变。事实上,存储库的整体大小已经增长了数百兆字节。

如何正确推送这些更改?

【问题讨论】:

但是本地的.git文件夹缩水了?你是如何推动这些变化的?与git push -f?如果没有,请尝试一下! (-f 用于强制 push-command) 如果有任何 PR 指向您重写的某些分支,您可能会发现减小大小非常困难,甚至不可能。我不确定 GitLab 如何处理已关闭的 PR,但我知道在 GitHub 上 PR 持有指向提交的指针,并且即使您重写或删除它所在的分支,该提交也无法被垃圾收集。我希望在 GitLab 上会有类似的行为。 @SwissCodeMen 是的,我的本地仓库克隆上的 .git 文件夹已经缩小。我用git push origin --force --all 推送,但是远程仓库上的.git 文件夹没有缩小。 【参考方案1】:

默认情况下,当您克隆存储库时,您不会在本地拥有所有远程 refs。即使您清理了本地 git 存储库(使得本地大小实际上更小),您也可能不会在 GitLab 中看到这一点。这是因为(1)默认情况下您没有所有远程参考,并且(2)GitLab 在许多情况下保留了您在本地删除的那些参考。例如,如果您的管道引用了占用空间的不再存在的本地引用,或者合并请求中存在引用等情况。

要解决这个问题,您还需要在遥控器上另外清理这些引用:

refs/merge-requests/* 用于合并请求。 refs/pipelines/* 用于管道。 refs/environments/* 用于环境。 refs/keep-around/* 被创建为隐藏引用,以防止删除数据库中引用的提交

如果您将这些引用添加到本地 git 存储库并获取它们,您将看到更接近地反映 GitLab 中报告的大小。

例如,如果您查看您的 git 配置,默认情况下您会看到如下内容:

[remote "origin"]
  url = https://gitlab.com/gitlab-org/gitlab-foss.git
  fetch = +refs/heads/*:refs/remotes/origin/*

你想编辑你的 git 配置(使用git config -e)并添加上面的引用。例如,添加 merge_requests 引用后,您的 git 配置应如下所示:

[remote "origin"]
  url = https://gitlab.com/gitlab-org/gitlab-foss.git
  fetch = +refs/heads/*:refs/remotes/origin/*
  fetch = +refs/merge-requests/*/head:refs/remotes/origin/merge-requests/*

对每个尚未清理的遥控器执行此操作,获取它们 (git fetch origin),在本地清理它们,然后强制推回遥控器。

但是,有些 refs 没有公布,只能通过导出 GitLab 项目并从导出 tarball(tarball 中的 project.bundle)恢复本地 repo 来检索

git clone --bare --mirror ./project.bundle myrepo
cd myrepo
git filter-repo ... # modify this for your cleanup
git remote remove origin
git remote add origin <project clone URL>
git push origin --force 'refs/heads/*'
git push origin --force 'refs/tags/*'
# push hidden refs
git push origin --force 'refs/replace/*'

完成此操作后,git filter-repo./filter-repo/commit-map 创建一个commit-map 文件。获取此文件并将其上传到“设置 -> 存储库 -> 清理”下的存储库清理。

请记住,删除这些也会破坏依赖它们的功能(例如,您将无法查看以前的 MR 中的代码/引用,这些代码/引用在删除引用后发生了更改)。

还知道,在您推送已清理的 refs 并启动 repo 清理后,根据 repo 大小,在 GitLab 中更新大小可能需要 30 分钟或更长时间。

其他参考:GitLab - Reduce repository size

或者,您可以创建一个新的 GitLab 项目并将干净的本地状态推送到新的 GitLab 项目,然后删除旧的。使用这种方法,您当然会丢失 GitLab 存储的大部分历史记录,例如合并请求、设置、CI/CD 管道等。 可以移动新项目以代替旧项目以保留正确的克隆 URL。这是核选项。

【讨论】:

以上是关于如何在本地缩小远程.git文件夹后更新它的主要内容,如果未能解决你的问题,请参考以下文章

如何查看git远程仓库中的文件

使用git更新代码

如何把git仓库移动到本地

修改git远程仓库地址

git如何强制用远程分支更新本地

如何将本地代码上传至git仓库