ジョブのアーティファクト管理

  • GitLab 8.2とGitLab Runner 0.7.0で導入されました。
  • GitLab 8.4とGitLab Runner 1.0から、アーティファクトアーカイブのフォーマットがZIPに変わりました。
  • GitLab 8.17から、ビルドはジョブという名前に変わりました。
  • ユーザーガイドはpipelines/job_artifactsを参照してください。

アーティファクトとは、ジョブが終了した後に添付されるファイルやディレクトリのリストのことです。 この機能は、すべてのGitLabインストールでデフォルトで有効になっています。 無効にする方法を知りたい場合は、このまま読み進めてください。

ジョブアーティファクトの無効化

サイト全体でアーティファクトを無効にするには、以下の手順に従ってください。

オムニバスのインストールで:

  1. /etc/gitlab/gitlab.rb を編集し、以下の行を追加します:

    gitlab_rails['artifacts_enabled'] = false
    
  2. ファイルを保存し、変更を有効にするために GitLab を再設定します。

ソースからのインストールで:

  1. /home/git/gitlab/config/gitlab.yml を編集し、以下の行を追加または修正してください:

    artifacts:
      enabled: false
    
  2. ファイルを保存し、GitLabを再起動して変更を有効にします。

アーティファクトの保存

GitLab Runnerはジョブのアーティファクトを含むアーカイブをGitLabにアップロードすることができます。 デフォルトでは、これはジョブが成功したときに行われますが、失敗したときや、artifacts:when パラメータを使って常に行うこともできます。

ほとんどのアーティファクトは GitLab Runner で圧縮されてからコーディネータに送信されます。レポートのアーティファクトは例外で、アップロード後に圧縮されます。

ローカルストレージの使用

アーティファクトをローカルに保存する場所を変更するには、以下の手順に従います。

オムニバスのインストールで:

アーティファクトはデフォルトで/var/opt/gitlab/gitlab-rails/shared/artifactsに保存されます。

  1. 例えばストレージパスを/mnt/storage/artifactsに変更するには、/etc/gitlab/gitlab.rb を編集し、以下の行を追加します:

    gitlab_rails['artifacts_path'] = "/mnt/storage/artifacts"
    
  2. ファイルを保存し、変更を有効にするために GitLab を再設定します。

ソースからのインストールで:

アーティファクトはデフォルトで/home/git/gitlab/shared/artifactsに保存されます。

  1. 保存パスを例えば/mnt/storage/artifactsに変更するには、/home/git/gitlab/config/gitlab.yml を編集し、以下の行を追加または修正します:

    artifacts:
      enabled: true
      path: /mnt/storage/artifacts
    
  2. ファイルを保存し、GitLabを再起動して変更を有効にします。

オブジェクトストレージの使用

GitLabがインストールされているローカルディスクをアーティファクトの保存に使いたくない場合は、代わりにAWS S3のようなオブジェクトストレージを使うことができます。 この設定は、有効なAWS認証情報がすでに設定されていることに依存します。 ジョブのアーティファクトを保存するには、AWS S3のようなオブジェクトストレージオプションを使います。

危険:CIログとアーティファクトをオブジェクトストレージに保存するようにGitLabを設定する場合、インクリメンタルロギングも有効にする必要があります。 そうしないと、ジョブログが消えたり保存されなかったりします。

GitLabでのオブジェクトストレージの使用についてはこちらをご覧ください。

オブジェクトストレージの設定

ソースのインストールでは、以下の設定はartifacts: の下にネストされ、次にobject_store:となります。Omnibus GitLab のインストールでは、これらの設定の前にartifacts_object_store_が付きます。

設定 説明 デフォルト
enabled オブジェクトストレージの有効化/無効化 false
remote_directory アーティファクトが保存されるバケット名  
direct_upload trueに設定すると、ローカル共有ストレージを使用せずにアーティファクトを直接アップロードできるようになります。 オプションは、すべてのファイルに対して単一ストレージのみをサポートすることに決定した時点で削除される可能性があります。 false
background_upload 自動アップロードを無効にするにはfalseに設定します。 S3へのアップロードが完了すると、このオプションは削除されます。 true
proxy_download 送信されたすべてのファイルのプロキシを有効にするには、true を設定します。 このオプションは、すべてのデータをプロキシする代わりに、クライアントがリモートストレージから直接ダウンロードできるようにするため、イグレストラフィックを減らすことができます。 false
connection 以下の様々な接続オプション  
S3互換接続設定

接続設定はフォグが提供するものと同じで、以下の通りです:

設定 説明 デフォルト
provider 常に互換性のあるホストに対してAWS エーダブリュエス
aws_access_key_id AWSクレデンシャル、または互換性のあるもの  
aws_secret_access_key AWSクレデンシャル、または互換性のあるもの  
aws_signature_version AWS署名のバージョンは2または4が有効です。 4
enable_signature_v4_streaming AWS v4 シグネチャでHTTP チャンク転送を有効にするには true に設定します。 Oracle Cloud S3 では false に設定する必要があります。 真の
region AWSリージョン 米東1
host AWSを使用しない場合のS3互換ホスト、例えばlocalhost またはstorage.example.com s3.amazonaws.com
endpoint MinIOなどのS3互換サービスを設定する際に、以下のようなURLを入力することで使用できます。http://127.0.0.1:9000 (オプション)
path_style bucket_name.host/objectの代わりにhost/bucket_name/object 形式のパスを使用する場合は true に設定します。 AWS S3 の場合は false のままにします。 false
use_iam_profile アクセスキーの代わりに IAM プロファイルを使用するには true を設定します。 false

オムニバスのインストールで:

アーティファクトはデフォルトで/var/opt/gitlab/gitlab-rails/shared/artifactsに保存されます。

  1. /etc/gitlab/gitlab.rb を編集し、必要な値を代入して以下の行を追加します:

    gitlab_rails['artifacts_enabled'] = true
    gitlab_rails['artifacts_object_store_enabled'] = true
    gitlab_rails['artifacts_object_store_remote_directory'] = "artifacts"
    gitlab_rails['artifacts_object_store_connection'] = {
      'provider' => 'AWS',
      'region' => 'eu-central-1',
      'aws_access_key_id' => 'AWS_ACCESS_KEY_ID',
      'aws_secret_access_key' => 'AWS_SECRET_ACCESS_KEY'
    }
    
    GitLab 9.4+ では、AWS IAM プロファイルを使っている場合は、AWS アクセスキーとシークレットアクセスキー/値のペアを必ず省略してください。 例えば、以下のようになります:
    gitlab_rails['artifacts_object_store_connection'] = {
      'provider' => 'AWS',
      'region' => 'eu-central-1',
      'use_iam_profile' => true
    }
    
  2. ファイルを保存し、変更を有効にするために GitLab を再設定します。
  3. 既存のローカル・アーティファクトをオブジェクト・ストレージに移行します:

    gitlab-rake gitlab:artifacts:migrate
    
注意:JUnit テストレポート アーティファクト (junit.xml.gz) の移行は、gitlab:artifacts:migrate スクリプトではサポートされていません。

ソースからのインストールで:

アーティファクトはデフォルトで/home/git/gitlab/shared/artifactsに保存されます。

  1. /home/git/gitlab/config/gitlab.yml を編集し、以下の行を追加または修正してください:

    artifacts:
      enabled: true
      object_store:
        enabled: true
        remote_directory: "artifacts" # The bucket name
        connection:
          provider: AWS # Only AWS supported at the moment
          aws_access_key_id: AWS_ACCESS_KEY_ID
          aws_secret_access_key: AWS_SECRET_ACCESS_KEY
          region: eu-central-1
    
  2. ファイルを保存し、GitLabを再起動して変更を有効にします。
  3. 既存のローカル・アーティファクトをオブジェクト・ストレージに移行します:

    sudo -u git -H bundle exec rake gitlab:artifacts:migrate RAILS_ENV=production
    
注意:JUnit テストレポート アーティファクト (junit.xml.gz) の移行は、gitlab:artifacts:migrate スクリプトではサポートされていません。

OpenStack互換の接続設定

接続設定はフォグが提供するものと同じで、以下の通りです:

設定 説明 デフォルト
provider 常に互換性のあるホストに対してOpenStack オープンスタック
openstack_username OpenStackユーザー名  
openstack_api_key OpenStack API キー  
openstack_temp_url_key 一時的な URL を生成するための OpenStack キー  
openstack_auth_url OpenStack 認証エンドポイント  
openstack_region OpenStackリージョン  
openstack_tenant_id OpenStackテナントID  

オムニバスのインストールで:

アップロードはデフォルトで/var/opt/gitlab/gitlab-rails/shared/artifactsに保存されます。

  1. /etc/gitlab/gitlab.rb を編集し、必要な値を代入して以下の行を追加します:

    gitlab_rails['artifacts_enabled'] = true
    gitlab_rails['artifacts_object_store_enabled'] = true
    gitlab_rails['artifacts_object_store_remote_directory'] = "artifacts"
    gitlab_rails['artifacts_object_store_connection'] = {
     'provider' => 'OpenStack',
     'openstack_username' => 'OS_USERNAME',
     'openstack_api_key' => 'OS_PASSWORD',
     'openstack_temp_url_key' => 'OS_TEMP_URL_KEY',
     'openstack_auth_url' => 'https://auth.cloud.ovh.net',
     'openstack_region' => 'GRA',
     'openstack_tenant_id' => 'OS_TENANT_ID',
    }
    
  2. ファイルを保存し、変更を有効にするために GitLab を再設定します。
  3. 既存のローカル・アーティファクトをオブジェクト・ストレージに移行します:

    gitlab-rake gitlab:artifacts:migrate
    

ソースからのインストールで:

アップロードはデフォルトで/home/git/gitlab/shared/artifactsに保存されます。

  1. /home/git/gitlab/config/gitlab.yml を編集し、以下の行を追加または修正してください:

    uploads:
      object_store:
        enabled: true
        direct_upload: false
        background_upload: true
        proxy_download: false
        remote_directory: "artifacts"
        connection:
          provider: OpenStack
          openstack_username: OS_USERNAME
          openstack_api_key: OS_PASSWORD
          openstack_temp_url_key: OS_TEMP_URL_KEY
          openstack_auth_url: 'https://auth.cloud.ovh.net'
          openstack_region: GRA
          openstack_tenant_id: OS_TENANT_ID
    
  2. ファイルを保存し、GitLabを再起動して変更を有効にします。
  3. 既存のローカル・アーティファクトをオブジェクト・ストレージに移行します:

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

オブジェクトストレージからローカルストレージへの移行

オムニバスのインストールで:

ローカルストレージに戻すには

  1. gitlab.rbのアーティファクト・オブジェクト・ストレージ設定で、direct_uploadbackground_upload の両方を false に設定します。
  2. GitLabを再設定します。
  3. gitlab-rake gitlab:artifacts:migrate_to_localを実行します。
  4. gitlab.rbでアーティファクトの object_storage を無効にします:
    • gitlab_rails['artifacts_object_store_enabled'] = falseを設定します。
    • artifacts_object_store_connection セクション全体を含む、他のすべてのartifacts_object_store 設定をコメントアウトしてください(終了}を含む)。
  5. GitLabを再設定します。

期限切れアーティファクト

artifacts:expire_in を使ってアーティファクトの有効期限を設定した場合、その日付が過ぎるとすぐに削除されます。そうでない場合は、デフォルトのアーティファクトの有効期限設定に従って期限切れになります。

アーティファクトは、Sidekiqが毎時50分に実行するexpire_build_artifacts_worker cronジョブによってクリーンアップされます(50 * * * *)。

アーティファクトの有効期限が切れるデフォルトのスケジュールを変更するには、以下の手順に従います。

オムニバスのインストールで:

  1. /etc/gitlab/gitlab.rb を編集し、以下の行を追加してください(すでに存在し、コメントアウトされている場合はコメントアウトを解除してください):

    gitlab_rails['expire_build_artifacts_worker_cron'] = "50 * * * *"
    
  2. ファイルを保存し、変更を有効にするために GitLab を再設定します。

ソースからのインストールで:

  1. /home/git/gitlab/config/gitlab.yml を編集し、以下の行を追加または修正してください:

    expire_build_artifacts_worker:
      cron: "50 * * * *"
    
  2. ファイルを保存し、GitLabを再起動して変更を有効にします。

パイプラインでexpire ディレクティブが明示的に設定されていない場合、アーティファクトはCI/CD Admin 設定にあるデフォルトのアーティファクトの有効期限設定に従って期限切れになります。

依存関係の検証

GitLab 10.3から導入されました。

依存関係の検証を無効にするには、Railsコンソールからci_disable_validates_dependencies featureフラグを有効にします。

オムニバスのインストールで:

  1. Railsコンソールに入ります:

    sudo gitlab-rails console
    
  2. 検証を無効にするには、機能フラグを有効にします:

    Feature.enable(:ci_disable_validates_dependencies)
    

ソースからのインストールで:

  1. Railsコンソールに入ります:

    cd /home/git/gitlab
    sudo -u git -H bundle exec rails console -e production
    
  2. 検証を無効にするには、機能フラグを有効にします:

    Feature.enable(:ci_disable_validates_dependencies)
    

アーティファクトの最大ファイルサイズの設定

アーティファクトが有効になっている場合、管理エリアの設定でアーティファクトの最大ファイルサイズを変更できます。

ストレージ統計

グループやプロジェクトのアーティファクトに使用されるストレージの合計は、管理エリアやグループプロジェクトのAPIで確認できます。

実施内容

GitLabがアーティファクトアーカイブを受け取ると、GitLab Workhorseによってアーカイブメタデータファイルも生成されます。 このメタデータファイルには、アーティファクトアーカイブ自体にあるすべてのエントリが記述されています。 メタデータファイルはバイナリ形式で、さらにGzip圧縮が加えられています。

GitLabは容量、メモリ、ディスクI/Oを節約するためにアーティファクトアーカイブを抽出しません。 代わりに、関連するすべての情報を含むメタデータファイルを検査します。 これは、アーティファクトが多い場合やアーカイブが非常に大きなファイルの場合に特に重要です。

特定のファイルをクリックすると、GitLab Workhorseはアーカイブからそのファイルを抽出し、ダウンロードを開始します。 この実装はスペース、メモリ、ディスクI/Oを節約します。

トラブルシューティング

アーティファクトによるディスク容量の過剰使用

ジョブのアーティファクトが予想以上に早くディスク容量をいっぱいにしてしまうことがあります。 考えられる原因としては、以下のようなものがあります:

  • ジョブアーティファクトの有効期限が必要以上に長く設定されています。
  • ジョブの実行数、つまり生成されるアーティファクトの数が予想以上に多い。
  • ジョブ・ログは予想以上に大きく、時間の経過とともに蓄積されています。

このようなケースやその他のケースでは、ディスク使用量の最も大きな原因となっているプロジェクトを特定し、最も多くのスペースを使用しているアーティファクトの種類を把握し、場合によってはジョブのアーティファクトを手動で削除してディスクスペースを取り戻す必要があります。

最初のステップとしては、孤児となったアーティファクト・ファイルをクリーンアップすることが考えられます。

保存されているアーティファクトの合計サイズ別にプロジェクトを一覧表示します。

Railsコンソール(sudo gitlab-rails console)で以下のコードを実行して、保存されているジョブアーティファクトの合計サイズ順に上位20プロジェクトをリストアップします:

include ActionView::Helpers::NumberHelper
ProjectStatistics.order(build_artifacts_size: :desc).limit(20).each do |s|
  puts "#{number_to_human_size(s.build_artifacts_size)} \t #{s.project.full_path}"
end

.limit(20) 、表示されるプロジェクトの数を変更することができます。

単一プロジェクトにおける最大のアーティファクトのリスト

Railsコンソール(sudo gitlab-rails console)で以下のコードを実行することで、1つのプロジェクトで最も大きい50のジョブアーティファクトをリストアップします:

include ActionView::Helpers::NumberHelper
project = Project.find_by_full_path('path/to/project')
Ci::JobArtifact.where(project: project).order(size: :desc).limit(50).map { |a| puts "ID: #{a.id} - #{a.file_type}: #{number_to_human_size(a.size)}" }

.limit(50) を変更することで、表示されるジョブのアーティファクトの数を変更することができます。

特定の日付以前に完了したジョブのアーティファクトを削除します。

注意:これらのコマンドは、データベースとディスクからデータを永久に削除します。 サポート・エンジニアの指導の下でのみ実行するか、念のためインスタンスのバックアップをリストアできる状態にしてテスト環境で実行することを強くお勧めします。

複数のジョブのログを保持したまま、そのジョブに関連するアーティファクトを手動で削除する必要がある場合、Rails コンソール (sudo gitlab-rails console) から行うことができます:

  1. 削除するジョブを選択します:

    1つのプロジェクトのアーティファクトを含むすべてのジョブを選択します:

    project = Project.find_by_full_path('path/to/project')
    builds_with_artifacts =  project.builds.with_downloadable_artifacts
    

    GitLabインスタンス全体のアーティファクトを持つすべてのジョブを選択するには:

    builds_with_artifacts = Ci::Build.with_downloadable_artifacts
    
  2. 特定の日付より古いジョブのアーティファクトを削除します:

    注:このステップでは、ユーザーが「保持」を選択したアーティファクトも消去されます。
    builds_to_clear = builds_with_artifacts.where("finished_at < ?", 1.week.ago)
    builds_to_clear.find_each do |build|
      build.artifacts_expire_at = Time.now
      build.erase_erasable_artifacts!
    end
    

    1.week.ago はRailsのActiveSupport::Duration メソッドで、過去の新しい日付や時刻を計算します。 その他の有効な例としては、次のようなものがあります:

    • 7.days.ago
    • 3.months.ago
    • 1.year.ago

特定の日付以前に完了したジョブのアーティファクトとログを削除します。

注意:これらのコマンドは、データベースとディスクからデータを永久に削除します。 サポート・エンジニアの指導の下でのみ実行するか、念のためインスタンスのバックアップをリストアできる状態にしてテスト環境で実行することを強くお勧めします。

ジョブログを含め、複数のジョブに関連するすべてのジョブアーティファクトを手動で削除する必要がある場合、Rails コンソール (sudo gitlab-rails console) から行うことができます:

  1. 削除するジョブを選択します:

    1つのプロジェクトのアーティファクトを含むジョブを選択します:

    project = Project.find_by_full_path('path/to/project')
    builds_with_artifacts =  project.builds.with_existing_job_artifacts(Ci::JobArtifact.trace)
    

    GitLabインスタンス全体でアーティファクトを持つジョブを選択するには:

    builds_with_artifacts = Ci::Build.with_existing_job_artifacts(Ci::JobArtifact.trace)
    
  2. ジョブを消去するユーザーを選択します:

    admin_user = User.find_by(username: 'username')
    
  3. 特定の日付より古いジョブのアーティファクトとログを消去します:

    builds_to_clear = builds_with_artifacts.where("finished_at < ?", 1.week.ago)
    builds_to_clear.find_each do |build|
      print "Ci::Build ID #{build.id}... "
    
      if build.erasable?
        build.erase(erased_by: admin_user)
        puts "Erased"
      else
        puts "Skipped (Nothing to erase or not erasable)"
      end
    end
    

    1.week.ago はRailsのActiveSupport::Duration メソッドで、過去の新しい日付や時刻を計算します。 その他の有効な例としては、次のようなものがあります:

    • 7.days.ago
    • 3.months.ago
    • 1.year.ago