{{< details >}}

  • Tier: 基础版, 专业版, 旗舰版
  • Offering: JihuLab.com, 私有化部署

{{< /details >}}

极狐GitLab 支持并自动化管理 Git 仓库中的维护任务,以确保它们能够尽可能高效地提供服务。维护任务包括:

  • 压缩 Git 对象和修订版本。
  • 删除不可达对象。
  • 删除过期数据,如锁文件。
  • 维护数据结构以提升性能。
  • 更新对象池以改善跨分叉的对象去重。

{{< alert type=”warning” >}}

不要手动执行 Git 命令来在极狐GitLab 控制的 Git 仓库中进行维护。这样做可能会导致仓库损坏和数据丢失。

{{< /alert >}}

维护策略

Gitaly 可以通过两种方式在 Git 仓库中执行维护任务:

  1. 积极维护 独立于仓库状态执行特定的维护任务。
  2. 启发式维护 基于一组启发式方法执行维护任务,这些方法根据仓库状态确定需要执行哪些维护任务。

积极维护

“积极”维护策略独立于仓库状态在仓库中执行维护任务。这是由手动触发器和基于推送的触发器使用的默认策略。

积极维护策略由极狐GitLab 应用控制。根据导致维护作业运行的触发器,极狐GitLab 会要求 Gitaly 执行特定的维护任务。即使仓库处于优化状态,Gitaly 仍会执行这些任务。因此,在需要较慢执行维护任务的大型仓库中,这种策略可能效率不高。

启发式维护

{{< history >}}

  • 在极狐GitLab 14.9 中引入,用于手动触发器和基于推送的触发器,带有一个名为 optimized_housekeeping标志。默认启用。
  • 在极狐GitLab.com 中,在极狐GitLab 14.10 中启用。
  • 在极狐GitLab 15.8 中正式可用。功能标志 optimized_housekeeping 被移除。

{{< /history >}}

启发式(或“机会主义”)维护策略分析仓库的状态,仅在发现一个或多个数据结构优化不足时才执行维护任务。这是计划维护使用的策略。

启发式维护使用以下信息来决定需要运行的任务:

  • 松散和过期对象的数量。
  • 包含已压缩对象的包文件的数量。
  • 松散引用的数量。
  • 提交图的存在。

是否需要优化任何分析过的数据结构的决定基于仓库的大小:

  • 对象总大小越大,打包的频率越高。
  • 引用总数越多,打包的频率越低。

Gitaly 这样做是为了抵消优化这些数据结构所需的时间随其增大而增加的事实。在大型单一库(接收大量流量)中,避免过于频繁地优化它们尤为重要。

您可以更改 Gitaly 被要求优化仓库的频率。

  1. 在左侧边栏的底部,选择 管理员
  2. 选择 设置 > 仓库
  3. 展开 仓库维护
  4. 维护 部分,配置维护选项。
  5. 选择 保存更改
  • 启用自动仓库维护:定期请求 Gitaly 运行仓库优化。如果长时间禁用此设置,您极狐GitLab 服务器上的 Git 仓库访问速度会变慢,您的仓库会占用更多的磁盘空间。
  • 优化仓库周期:在多少次 Git 推送后请求 Gitaly 优化仓库。

运行维护任务

极狐GitLab 运行维护任务的方式有多种:

  1. 项目的管理员可以手动触发仓库维护任务。
  2. 极狐GitLab 可以在多次 Git 推送后自动安排维护任务。
  3. 极狐GitLab 可以计划一个作业在可配置的时间框架内为所有仓库运行维护任务。

手动触发

仓库的管理员可以手动触发仓库中的维护任务。通常不需要这样做,因为极狐GitLab 知道如何自动运行维护任务。手动触发在以下情况下可能有用:

  1. 已知某个仓库需要维护。
  2. 已禁用基于推送的维护任务自动安排。

要手动触发维护任务:

  1. 在左侧边栏,选择 搜索或转到 并找到您的项目。
  2. 选择 设置 > 常规
  3. 展开 高级
  4. 选择 运行维护

这将为项目的仓库启动一个异步后台工作者。后台工作者要求 Gitaly 执行若干优化。

200 次推送时,维护还会从您的项目中删除未引用的 LFS 文件,从而释放项目的存储空间。

修剪不可达对象

不可达对象作为计划维护的一部分被修剪。但是,您也可以手动触发修剪。例如:删除包含敏感信息的提交。触发维护会以两周的宽限期修剪不可达对象。当您手动触发不可达对象的修剪时,宽限期缩短为 30 分钟。

{{< alert type=”warning” >}}

如果并发进程(如 git push)创建了一个对象,但尚未为该对象创建引用,则如果在对象删除后添加了对该对象的引用,您的仓库可能会损坏。宽限期的存在是为了减少此类竞争条件的可能性。例如,如果频繁通过有时非常慢的连接推送许多大对象,那么修剪不可达对象带来的风险比在公司内部通过高效连接访问项目的企业环境要高得多。在使用此选项时,请考虑项目使用情况并选择一个安静的时期。

{{< /alert >}}

要触发手动修剪不可达对象:

  1. 在左侧边栏,选择 搜索或转到 并找到您的项目。
  2. 选择 设置 > 常规
  3. 展开 高级
  4. 选择 运行维护
  5. 等待 30 分钟以完成操作。
  6. 返回到您选择 运行维护 的页面,然后选择 修剪不可达对象

计划维护

{{< details >}}

  • Offering: 极狐GitLab 私有化部署

{{< /details >}}

虽然极狐GitLab 根据推送次数自动执行维护任务,但它不维护完全没有接收任何推送的仓库。因此,不活跃的仓库或仅接收读取请求的仓库可能无法从仓库维护策略的改进中受益。

管理员可以启用一个后台作业,该作业在可自定义的间隔内执行所有仓库的维护,以解决这种情况。这个后台作业以随机顺序处理所有由 Gitaly 节点托管的仓库,并积极地对它们执行维护任务。如果所需时间超过配置的间隔,Gitaly 节点将停止处理仓库。

配置计划维护

Git 仓库的后台维护在 Gitaly 中配置。默认情况下,Gitaly 每天中午 12:00 进行后台仓库维护,持续 10 分钟。

您可以在 Gitaly 配置中更改此默认设置。

对于具有 Gitaly 集群的环境,计划维护的开始时间可以在 Gitaly 节点之间错开,以便计划维护不会在多个节点上同时运行。

如果计划维护运行达到指定的 duration,则正在运行的任务将被优雅地取消。在后续的计划维护运行中,Gitaly 随机打乱要处理的仓库列表。

以下代码片段启用 default 存储的每日后台仓库维护,开始于 23:00,持续 1 小时:

{{< tabs >}}

{{< tab title=”自编译(源代码)” >}}

[daily_maintenance]
start_hour = 23
start_minute = 00
duration = 1h
storages = ["default"]

使用以下代码片段可完全禁用后台仓库维护:

[daily_maintenance]
disabled = true

{{< /tab >}}

{{< tab title=”Linux 软件包(Omnibus)” >}}

gitaly['configuration'] = {
  daily_maintenance: {
    disabled: false,
    start_hour: 23,
    start_minute: 00,
    duration: '1h',
    storages: ['default'],
  },
}

使用以下代码片段可完全禁用后台仓库维护:

gitaly['configuration'] = {
  daily_maintenance: {
    disabled: true,
  },
}

{{< /tab >}}

{{< /tabs >}}

执行计划维护时,您可以在 Gitaly 日志中看到以下条目:

# 当计划维护开始时
{"level":"info","msg":"maintenance: daily scheduled","pid":197260,"scheduled":"2023-09-27T13:10:00+13:00","time":"2023-09-27T00:08:31.624Z"}

# 当计划维护完成时
{"actual_duration":321181874818,"error":null,"level":"info","max_duration":"1h0m0s","msg":"maintenance: daily completed","pid":197260,"time":"2023-09-27T00:15:21.182Z"}

actual_duration(以纳秒为单位)表示计划维护执行所花费的时间。在上面的例子中,计划维护在 5 分钟多一点的时间内完成。

对象池仓库

{{< details >}}

  • Offering: 极狐GitLab 私有化部署

{{< /details >}}

对象池仓库由极狐GitLab 用于跨仓库分叉去重对象。当创建第一个分叉时,我们:

  1. 创建一个对象池仓库,其中包含即将被分叉的仓库的所有对象。
  2. 使用 Git 的替代机制将仓库链接到这个新对象池。
  3. 重新打包仓库,使其使用对象池中的对象,从而可以丢弃其自己的对象副本。

现在,这个仓库的任何分叉都可以链接到对象池,因此只需保留与主仓库不同的对象。

极狐GitLab 需要在对象池中执行特殊的维护操作:

  • Gitaly 绝不能从对象池中删除不可达对象,因为它们可能被任何连接到它的分叉使用。
  • Gitaly 必须保持所有对象都是可达的,原因相同。因此,对象池会维护对不可达“悬空”对象的引用,以防止它们被删除。
  • 极狐GitLab 必须定期更新对象池,以拉入在主仓库中添加的新对象。否则,对象池在去重对象方面会越来越低效。

这些维护操作由专门的 FetchIntoObjectPool RPC 执行,该 RPC 处理所有这些特殊任务,同时执行我们为标准 Git 仓库执行的常规维护任务。

每当主成员进行垃圾收集时,对象池会自动优化。因此,节奏可以使用该项目中的相同 Git GC 周期进行配置。

如果需要从 Rails 控制台手动调用 RPC,可以调用 project.pool_repository.object_pool.fetch。这是一个可能需要很长时间的任务,不过 Gitaly 会在大约 8 小时后超时。