极狐GitLab Git 大文件存储 (LFS) 管理

关于如何使用 Git LFS 的文档位于使用 Git LFS 文档管理大型二进制文件下。

默认情况下,在极狐GitLab 私有化部署实例中启用 LFS。

要求

配置

Git LFS 对象可以很大。默认情况下,它们存储在安装极狐GitLab 的服务器上。

有多种配置选项可以帮助极狐GitLab 服务器管理员:

  • 启用/禁用 Git LFS 支持。
  • 更改 LFS 对象存储的位置。
  • 设置 Fog 支持的对象存储。

Omnibus 安装实例的配置

/etc/gitlab/gitlab.rb 中:

# Change to true to enable lfs - enabled by default if not defined
gitlab_rails['lfs_enabled'] = false

# Optionally, change the storage path location. Defaults to
# `#{gitlab_rails['shared_path']}/lfs-objects`. Which evaluates to
# `/var/opt/gitlab/gitlab-rails/shared/lfs-objects` by default.
gitlab_rails['lfs_storage_path'] = "/mnt/storage/lfs-objects"

更新 /etc/gitlab/gitlab.rb 中的设置后,运行 Omnibus GitLab reconfigure

源安装实例的配置

config/gitlab.yml 中:

# Change to true to enable lfs
  lfs:
    enabled: false
    storage_path: /mnt/storage/lfs-objects

在远程对象存储中存储 LFS 对象

您可以将 LFS 对象存储在远程对象存储中。这使您可以减少对本地磁盘的读取和写入,并释放磁盘空间。 极狐GitLab 与 Fog 紧密集成,因此您可以参考其文档查看哪些存储服务可以与极狐GitLab 集成。 您还可以在专用本地网络中使用外部对象存储。例如,MinIO 是一个独立的对象存储服务,可与极狐GitLab 实例一起使用。

极狐GitLab 为上传机制提供了两种不同的选项:“直接上传”和“后台上传”。

阅读有关在极狐GitLab 中使用对象存储的更多信息

note在 13.2 及更高版本,我们建议使用整合对象存储设置。本节介绍早期的配置格式。

选项 1:直接上传

  1. 用户将 lfs 文件推送到极狐GitLab 实例。
  2. 极狐GitLab-workhorse 将文件直接上传到外部对象存储。
  3. 极狐GitLab-workhorse 通知极狐GitLab-rails 上传过程完成。

选项 2:后台上传

  1. 用户将 lfs 文件推送到极狐GitLab 实例。
  2. 极狐GitLab-rails 将文件存储在本地文件存储中。
  3. 极狐GitLab-rails 然后将文件异步上传到外部对象存储。

支持以下常规设置。

设置 描述 默认值
enabled 启用/禁用对象存储。 false
remote_directory 存储 LFS 对象的存储桶名称。  
proxy_download 设置为 true 以启用代理所有提供的文件。选项允许减少出口流量,因为这允许客户端直接从远程存储下载而不是代理所有数据。 false
connection 下面描述的各种连接选项。  

请参阅不同提供商的可用连接设置

以下是 S3 的配置示例。

S3 - Omnibus 安装实例

在 Omnibus 安装实例中,设置以 lfs_object_store_ 为前缀:

  1. 编辑/etc/gitlab/gitlab.rb并添加以下行,根据您的需要替换值:

    gitlab_rails['lfs_object_store_enabled'] = true
    gitlab_rails['lfs_object_store_remote_directory'] = "lfs-objects"
    gitlab_rails['lfs_object_store_connection'] = {
      'provider' => 'AWS',
      'region' => 'eu-central-1',
      'aws_access_key_id' => '1ABCD2EFGHI34JKLM567N',
      'aws_secret_access_key' => 'abcdefhijklmnopQRSTUVwxyz0123456789ABCDE',
      # The below options configure an S3 compatible host instead of AWS
      'host' => 'localhost',
      'endpoint' => 'http://127.0.0.1:9000',
      'path_style' => true
    }
    
  2. 保存文件,然后重新配置极狐GitLab,使更改生效。
  3. 将任何现有的本地 LFS 对象迁移到对象存储。除非 gitlab_rails['lfs_object_store_background_upload']gitlab_rails['lfs_object_store_direct_upload'] 设置为 false,否则新的 LFS 对象将被转发到对象存储。

S3 - 源安装实例

对于源安装,设置嵌套在 lfs: 下,然后是 object_store:

  1. 编辑 /home/git/gitlab/config/gitlab.yml 并添加或修改以下行:

    lfs:
    enabled: true
    object_store:
      enabled: false
      remote_directory: lfs-objects # Bucket name
      connection:
        provider: AWS
        aws_access_key_id: 1ABCD2EFGHI34JKLM567N
        aws_secret_access_key: abcdefhijklmnopQRSTUVwxyz0123456789ABCDE
        region: eu-central-1
        # Use the following options to configure an AWS compatible host such as Minio
        host: 'localhost'
        endpoint: 'http://127.0.0.1:9000'
        path_style: true
    
  2. 保存文件,然后重启极狐GitLab,使更改生效。
  3. 将任何现有的本地 LFS 对象迁移到对象存储。除非 background_uploaddirect_upload 设置为 false,否则新的 LFS 对象将被转发到对象存储。

迁移到对象存储

选项 1:Rake 任务

配置对象存储后,使用以下任务将现有 LFS 对象从本地存储迁移到远端存储。该处理是在后台 worker 中完成的,并且要求没有停机时间

Omnibus 安装实例:

sudo gitlab-rake "gitlab:lfs:migrate"

源安装实例:

RAILS_ENV=production sudo -u git -H bundle exec rake gitlab:lfs:migrate

您可以选择跟踪进度并使用 PostgreSQL 控制台验证所有包是否已成功迁移:

  • sudo gitlab-rails dbconsole 用于 14.1 及更早版本的 Omnibus 安装实例。
  • sudo gitlab-rails dbconsole --database main 用于 14.2 及更高版本的 Omnibus 安装实例。
  • sudo -u git -H psql -d gitlabhq_production 用于源安装实例。

验证下面的 objectstg(其中 store=2)有所有 LFS 对象的计数:

gitlabhq_production=# SELECT count(*) AS total, sum(case when file_store = '1' then 1 else 0 end) AS filesystem, sum(case when file_store = '2' then 1 else 0 end) AS objectstg FROM lfs_objects;

示例输出

total | filesystem | objectstg
------+------------+-----------
 2409 |          0 |      2409

验证 objects 文件夹中的磁盘上没有文件:

sudo find /var/opt/gitlab/gitlab-rails/shared/lfs-objects -type f | grep -v tmp | wc -l

选项 2:Rails 控制台

登录到 Rails 控制台:

sudo gitlab-rails console

手动上传 LFS 文件

LfsObject.where(file_store: [nil, 1]).find_each do |lfs_object|
  lfs_object.file.migrate!(ObjectStorage::Store::REMOTE) if lfs_object.file.file.exists?
end

迁移回本地存储

要迁移回本地存储:

  1. 在控制台上运行 rake gitlab:lfs:migrate_to_local
  2. gitlab.rb 中禁用 LFS 对象的 object_storage。记得之后重启极狐GitLab。

存储统计

您可以看到用于群组和项目上的 LFS 对象的总存储空间:

故障排除

缺少 LFS 对象

在以下任何一种情况下,都可能会出现有关丢失 LFS 对象的错误:

  • 将 LFS 对象从磁盘迁移到对象存储时,出现以下错误消息:

    ERROR -- : Failed to transfer LFS object
    006622269c61b41bf14a22bbe0e43be3acf86a4a446afb4250c3794ea47541a7
    with error: No such file or directory @ rb_sysopen -
    /var/opt/gitlab/gitlab-rails/shared/lfs-objects/00/66/22269c61b41bf14a22bbe0e43be3acf86a4a446afb4250c3794ea47541a7
    

    (为了便于阅读,添加了换行符。)

  • 使用 VERBOSE=1 参数运行 LFS 对象的完整性检查

数据库可以有不在磁盘上的 LFS 对象的记录。数据库条目可能会阻止推送对象的新副本。要删除这些引用:

  1. 启动 Rails 控制台
  2. 查询 rails 控制台报错的对象,返回文件路径:

    lfs_object = LfsObject.find_by(oid: '006622269c61b41bf14a22bbe0e43be3acf86a4a446afb4250c3794ea47541a7')
    lfs_object.file.path
    
  3. 检查磁盘或对象存储是否存在:

    ls -al /var/opt/gitlab/gitlab-rails/shared/lfs-objects/00/66/22269c61b41bf14a22bbe0e43be3acf86a4a446afb4250c3794ea47541a7
    
  4. 如果文件不存在,通过 rails 控制台删除数据库记录:

    lfs_object.destroy
    

Google::Apis::TransmissionError: execution expired

如果 LFS 集成配置了 Google Cloud Storage 和后台上传(background_upload: truedirect_upload: false),Sidekiq worker 可能会遇到此错误。这是因为文件非常大时上传超时。 无需任何额外步骤即可上传最大 6 GB 的 LFS 文件,否则您需要使用以下解决方法。

登录 Rails 控制台:

sudo gitlab-rails console

设置超时:

  • 这些设置仅对同一会话有效。例如,它们对 Sidekiq worker 无效。
  • 20 分钟(1200 秒)足以上传 30GB LFS 文件:
::Google::Apis::ClientOptions.default.open_timeout_sec = 1200
::Google::Apis::ClientOptions.default.read_timeout_sec = 1200
::Google::Apis::ClientOptions.default.send_timeout_sec = 1200

手动上传 LFS 文件(这个过程根本不使用 Sidekiq):

LfsObject.where(file_store: [nil, 1]).find_each do |lfs_object|
  lfs_object.file.migrate!(ObjectStorage::Store::REMOTE) if lfs_object.file.file.exists?
end

LFS 命令在 TLS v1.3 服务器上失败

如果您将极狐GitLab 配置为禁用 TLS v1.2,并且仅启用 TLS v1.3 连接,则 LFS 操作需要 Git LFS 客户端 2.11.0 或更高版本。如果您使用低于 2.11.0 版本的 Git LFS 客户端,极狐GitLab 会显示错误:

batch response: Post https://username:***@gitlab.example.com/tool/releases.git/info/lfs/objects/batch: remote error: tls: protocol version not supported
error: failed to fetch some objects from 'https://username:[MASKED]@gitlab.example.com/tool/releases.git/info/lfs'

在 TLS v1.3 配置的极狐GitLab 服务器上使用 CI 时,您必须升级到极狐GitLab Runner 13.2.0 或更高版本才能接收更新 Git LFS 客户端版本通过包含的 Runner Helper 镜像

要检查已安装的 Git LFS 客户端的版本,请运行以下命令:

git lfs version

已知限制

  • 仅与 Git LFS 客户端版本 1.1.0 及更高版本或 1.0.2 兼容。
  • 存储统计为每个链接到它的项目计算每个 LFS 对象。