Azure DevOps Services |Azure DevOps Server |Azure DevOps Server 2022
Git 是一种常用的分布式源代码存储库(存储库),允许用户在处于断开连接状态时使用完整的存储库。 Git 的优点是有记录的,但如果需要在主存储库上“回滚时钟”,会发生什么情况? 这样做并不直观,需要提升的权限。 预计此要求将适用于影响所有存储库用户的事项。
如何安全地回滚中央存储库?
问题方案
假设将大型文件(如视频)提交到 Git 服务器。 在传统的源代码系统中,将一切存储在一个位置,然后拉取所需的内容是方便的。 使用 Git,整个存储库将克隆到每个用户的本地计算机。 使用大型文件时,项目中的每个用户还必须下载大型文件。
每提交一个大型文件到服务器,问题只会加剧。 存储库变得太大,以至于无法高效地服务其用户。 即使从本地存储库中删除大型文件并重新提交,该文件仍存在于存储库的历史记录中。 因此,该文件仍作为历史记录的一部分下载到每个人的本地计算机。
将大型文件添加到本地存储库。
从本地存储库提交之后,服务器上也有这个大型文件。
冻结存储库
若要修复大型存储库的问题,必须从源开始。 在此方案中,源是服务器存储库。 请团队停止向代码库推送。 如果在此过程中发生更多推送,则必须对这些推送进行处理,以免丢失任何数据。
重要
以下步骤从分支历史记录中删除视频,但从 Azure Repos 克隆存储库时,该文件将保留在存储库历史记录中。 从分支历史记录中删除文件会阻止更新文件,从而在存储库中创建另一个版本的大型文件。
详细了解如何在 Git 中管理大型文件。 有关使用 Azure Repos Git 存储库时此行为的说明和解决方法,请参阅 为什么从 Visual Studio Team Services 克隆会返回旧的未引用对象?。
变基和强制推送
如果团队中没有其他人对存储库进行任何更改(通常通过推送进行),则可以采用简单的路线。 你基本上使本地存储库看起来就像你想要它一样(也就是说,没有大型文件)。 然后,将更改强制推送到服务器。
在开始这项工作之前,可能需要克隆或修复本地存储库。 此过程可能会导致工作数据或更改丢失,因此请谨慎操作。
默认情况下,可以修改本地项目文件并将更改推送到服务器,但不能执行服务器级操作,例如删除或重新分组。 若要继续,需要对存储库具有强制推送(首选)或管理员权限。 请与项目管理员联系,请求这些权限,或请求已拥有这些权限的人员提供帮助。 有关详细信息,请参阅设置 Git 存储库权限。
接下来,需要重新设置存储库的基。
使用
git log查找最新提交的安全哈希算法 (SHA) 哈希值。 你很快会需要此信息,因为你需要知道最新的有效提交。 可以通过打开 Git 命令提示符并输入以下信息来获取此信息:git log或者,可以从在 Visual Studio 团队资源管理器中查看分支历史记录来获取 SHA 哈希。
打开 Git 命令提示符。
查找感兴趣的 SHA 哈希号。
需要以
25b4开头的 SHA。请记住,Git 使用指针来确定存储库中头或当前分支所在的位置。 你感兴趣的存储库状态位于过去某个时刻。
若要及时返回并将以前的状态设置为新的当前状态,请使用
git rebase以下命令:git rebase -i <SHA hash of desired new current branch>
该
-i开关提供额外的安全性,因为它在编辑器中显示历史记录。 (本文使用 Git 的实现,该实现在 Windows 中的命令行上显示经典 vi 编辑器。如果使用的是基于 Unix 的系统,可能会记住它。对于此示例,请输入:
git rebase -i 25b4编辑器启动后,将所有
pick行删除,只保留您想作为新主干的分支。 如果一切看起来正确,请在 vi 中输入:w\<enter\>以保存,或输入!q\<enter\>退出而不保存。
删除不再需要的行。
将
pick更改为drop,如下所示。 然后输入:w(在 vi 中)进行保存,然后输入:q!以启动 rebase。现在再次输入
git log。 日志中应不存在引发问题的分支。 如果是,则可以完成最后一步,这需要项目管理员权限:git log
大型视频的提交现在已从本地存储库中消失。
输入以下命令:
git push --force
这个命令会强制让你的存储库覆盖服务器上的存储库。
请谨慎使用此命令,因为可以轻松丢失服务器上的数据。
必须向服务器进行身份验证才能执行此操作。
如果使用 Azure Repos,可能需要设置不使用特殊字符的备用凭据。 例如电子邮件地址中的 at 符号(@)。 若要执行此任务,请按照 Azure Repos 身份验证中的说明进行操作。
现在分支已永久地从服务器中消失。 项目团队成员的后续克隆和同步不会下载尝试删除的大型文件。 用户需要从服务器下拉,以确保它们与新的服务器存储库状态同步。
如果用户有较新的提交
如果其他用户将提交推送到服务器存储库,则还有另一个注意事项。 你想要删除包含大型文件的分支,但不想丢失团队所做的更改。 若要解决这种情况,在变基过程中打开编辑器时,请仔细查看提交。 请确保您想要保留的提交列在 pick 所示的行上。 删除你想要移除的内容,例如添加了大型文件的地方。
团队中的其他用户在变基后也需要进行变基,以确保每个人都拥有服务器代码库的一致副本。 这项工作对于每个人来说都是乏味的,你想避免它。 如果需要删除推送,则需要与团队协调。 欲了解关于变基的更多信息,请参阅 Git 分支 - 变基。
关键是确保知道所需的提交和不需要的提交。 研究git log或历史记录,或集成开发环境(如 Visual Studio)中的历史记录。 仔细记下要保留的 SHA 哈希和要删除的哈希。
在大型文件已旧且存在后续分支和合并操作的情况下,您可以使用 git filter-branch 命令选项删除该文件。 有关详细信息,请参阅 从存储库中删除敏感数据。
最佳做法注意事项
确保大型文件远离主存储库,以节省团队成员的额外工作。 下面是团队要记住的一些常见最佳做法。
待办事项
- 经常提交更改。 以后总是可以使用压缩或变基来解决问题。
- 使用分支来隔离更改。 分行便宜,私人化,合并很简单。 可以通过将分支上的更改推送到服务器来备份。
- 发布主题分支时,请使用命名约定。 将分支
users/<alias>/<branchname>命名为 。 此名称有助于对分支进行分组,并便于其他人识别所有者。 - 请记住推送您的更改。 使用
Commit != Checkin和(Commit + Push) == Checkin。 - 请考虑对大型二进制文件使用
.gitignore,以便不会将其添加到存储库中。 有关详细信息,请参阅 “忽略文件”。 - 请考虑使用 NuGet 或 Team Foundation Server 版本控制来存储大型二进制文件。
要避免的事项
- 不要在推送后进行变基。 在 Git 中变基已推送的提交可能会很糟糕,因为它会迫使存储库中的其他人重新变基他们的本地更改。 如果团队成员需要执行此任务,则他们可能并不高兴。 除非其他人正在拉取这些提交,否则在你自己的个人分支上重新提交推送提交(即使已推送)并不是问题。
- 不要将二进制文件提交到存储库。 Git 不会按照 Team Foundation 版本控制的方式压缩二进制文件。 由于所有存储库都保留完整历史,从而提交二进制文件会导致永久冗余。
概要
有时,不需要的元素(如大型文件)会添加到存储库中,必须将其删除,以使存储库保持干净且轻量级。 可以通过按顺序获取本地存储库来执行此任务。 使用命令 git rebase ,然后使用命令 git push --force 将本地存储库覆盖到服务器存储库。