ストレージ管理を自動化する
- プラン: Free、Premium、Ultimate
- 提供形態: GitLab.com、GitLab Self-Managed、GitLab Dedicated
このページでは、GitLab REST APIを使用してストレージの使用状況を管理するための、ストレージ分析とクリーンアップを自動化する方法について説明します。
パイプライン効率性を向上させることによって、ストレージの使用状況を管理することもできます。
API自動化に関する詳細については、GitLabコミュニティフォーラムとDiscordも使用できます。
このページのスクリプト例はデモンストレーションのみを目的としており、本番環境では使用しないでください。例を使用して、ストレージ自動化用の独自のスクリプトを設計およびテストできます。
API要件
ストレージ管理を自動化するには、GitLab.comまたはGitLab Self-ManagedのインスタンスがGitLab REST APIにアクセスできる必要があります。
API認証スコープ
APIで認証するには、次のスコープを使用します:
- ストレージ分析:
read_apiスコープを使用した読み取りAPIアクセス。- すべてのプロジェクトにおけるデベロッパー、メンテナー、またはオーナーのロール。
- ストレージクリーンアップ:
apiスコープを使用したフルAPIアクセス。- すべてのプロジェクトにおけるメンテナーまたはオーナーのロール。
コマンドラインツールまたはプログラミング言語を使用して、REST APIを操作できます。
コマンドラインツール
APIリクエストを送信するには、次のいずれかをインストールします:
- お好みのパッケージマネージャーでcURL。
- GitLab CLIを使用し、
glab apiサブコマンドを使用します。
JSONレスポンスをフォーマットするには、jqをインストールします。詳細については、生産的なDevOpsワークフローのヒント: を参照してください: jqとCI/CDのLint自動化によるJSONフォーマット。
これらのツールをREST APIで使用するには:
export GITLAB_TOKEN=xxx
curl --silent --header "Authorization: Bearer $GITLAB_TOKEN" "https://gitlab.com/api/v4/user" | jqglab auth login
glab api groups/YOURGROUPNAME/projectsGitLab CLIの使用
一部のAPIエンドポイントでは、すべての結果を取得するためにページネーションと後続のページのフェッチが必要です。GitLab CLIはフラグ--paginateを提供します。
JSONデータとしてフォーマットされたPOSTボディを必要とするリクエストは、key=valueのペアとして--raw-fieldパラメータに渡すことができます。
詳細については、GitLab CLIエンドポイントのドキュメントを参照してください。
APIクライアントライブラリ
このページで説明されているストレージ管理とクリーンアップの自動化メソッドでは、以下を使用します:
- 豊富な機能を持つプログラミングインターフェースを提供する
python-gitlabライブラリ。 - GitLab APIとPythonプロジェクトにある
get_all_projects_top_level_namespace_storage_analysis_cleanup_example.pyスクリプト。
python-gitlabライブラリのユースケースの詳細については、効率的なDevSecOpsワークフロー: を参照してください: 実践的なpython-gitlab API自動化。
他のAPIクライアントライブラリの詳細については、サードパーティクライアントを参照してください。
GitLab Duoコード提案を使用して、コードをより効率的に記述します。
ストレージ分析
ストレージタイプを特定する
プロジェクトAPIエンドポイントは、GitLabインスタンス内のプロジェクトの統計情報を提供します。プロジェクトAPIエンドポイントを使用するには、statisticsキーをブール値trueに設定します。このデータは、次のストレージタイプごとのプロジェクトのストレージ消費量に関するインサイトを提供します:
storage_size: 全体的なストレージlfs_objects_size: LFSオブジェクトストレージjob_artifacts_size: ジョブアーティファクトストレージpackages_size: パッケージストレージrepository_size: Gitリポジトリストレージsnippets_size: スニペットストレージuploads_size: アップロードストレージwiki_size: Wikiストレージ
ストレージタイプを特定するには:
curl --silent --header "Authorization: Bearer $GITLAB_TOKEN" "https://gitlab.com/api/v4/projects/$GL_PROJECT_ID?statistics=true" | jq --compact-output '.id,.statistics' | jq
48349590
{
"commit_count": 2,
"storage_size": 90241770,
"repository_size": 3521,
"wiki_size": 0,
"lfs_objects_size": 0,
"job_artifacts_size": 90238249,
"pipeline_artifacts_size": 0,
"packages_size": 0,
"snippets_size": 0,
"uploads_size": 0
}export GL_PROJECT_ID=48349590
glab api --method GET projects/$GL_PROJECT_ID --field 'statistics=true' | jq --compact-output '.id,.statistics' | jq
48349590
{
"commit_count": 2,
"storage_size": 90241770,
"repository_size": 3521,
"wiki_size": 0,
"lfs_objects_size": 0,
"job_artifacts_size": 90238249,
"pipeline_artifacts_size": 0,
"packages_size": 0,
"snippets_size": 0,
"uploads_size": 0
}project_obj = gl.projects.get(project.id, statistics=True)
print("Project {n} statistics: {s}".format(n=project_obj.name_with_namespace, s=json.dump(project_obj.statistics, indent=4)))プロジェクトの統計情報をターミナルに出力するには、GL_GROUP_ID環境変数をエクスポートしてスクリプトを実行します:
export GL_TOKEN=xxx
export GL_GROUP_ID=56595735
pip3 install python-gitlab
python3 get_all_projects_top_level_namespace_storage_analysis_cleanup_example.py
Project Developer Evangelism and Technical Marketing at GitLab / playground / Artifact generator group / Gen Job Artifacts 4 statistics: {
"commit_count": 2,
"storage_size": 90241770,
"repository_size": 3521,
"wiki_size": 0,
"lfs_objects_size": 0,
"job_artifacts_size": 90238249,
"pipeline_artifacts_size": 0,
"packages_size": 0,
"snippets_size": 0,
"uploads_size": 0
}プロジェクトとグループのストレージを分析する
複数のプロジェクトとグループの分析を自動化できます。たとえば、最上位のネームスペースレベルから開始し、すべてのサブグループとプロジェクトを再帰的に分析できます。異なるストレージタイプを分析することもできます。
複数のサブグループとプロジェクトを分析するアルゴリズムの例を次に示します:
- 最上位ネームスペースのIDをフェッチします。ネームスペース/グループの概要からID値をコピーできます。
- トップレベルグループからすべてのサブグループをフェッチし、IDをリストに保存します。
- すべてのグループをループして、各グループからすべてのプロジェクトをフェッチし、IDをリストに保存します。
- 分析するストレージタイプを特定し、プロジェクト統計やジョブアーティファクトなどのプロジェクト属性から情報を収集します。
- すべてのプロジェクトをグループごとにグループ化し、そのストレージ情報の概要を出力します。
glabを使用したShellアプローチは、小規模な分析により適している場合があります。大規模な分析の場合は、APIクライアントライブラリを使用するスクリプトを使用する必要があります。この種類のスクリプトは、可読性、データストレージ、フロー制御、テスト、再利用性を向上させることができます。
スクリプトがAPIレート制限に達しないようにするため、以下のサンプルコードは並列APIリクエスト用に最適化されていません。
このアルゴリズムを実装するには:
export GROUP_NAME="gitlab-da"
# Return subgroup IDs
glab api groups/$GROUP_NAME/subgroups | jq --compact-output '.[]' | jq --compact-output '.id'
12034712
67218622
67162711
67640130
16058698
12034604
# Loop over all subgroups to get subgroups, until the result set is empty. Example group: 12034712
glab api groups/12034712/subgroups | jq --compact-output '.[]' | jq --compact-output '.id'
56595735
70677315
67218606
70812167
# Lowest group level
glab api groups/56595735/subgroups | jq --compact-output '.[]' | jq --compact-output '.id'
# empty result, return and continue with analysis
# Fetch projects from all collected groups. Example group: 56595735
glab api groups/56595735/projects | jq --compact-output '.[]' | jq --compact-output '.id'
48349590
48349263
38520467
38520405
# Fetch storage types from a project (ID 48349590): Job artifacts in the `artifacts` key
glab api projects/48349590/jobs | jq --compact-output '.[]' | jq --compact-output '.id, .artifacts'
4828297946
[{"file_type":"archive","size":52444993,"filename":"artifacts.zip","file_format":"zip"},{"file_type":"metadata","size":156,"filename":"metadata.gz","file_format":"gzip"},{"file_type":"trace","size":3140,"filename":"job.log","file_format":null}]
4828297945
[{"file_type":"archive","size":20978113,"filename":"artifacts.zip","file_format":"zip"},{"file_type":"metadata","size":157,"filename":"metadata.gz","file_format":"gzip"},{"file_type":"trace","size":3147,"filename":"job.log","file_format":null}]
4828297944
[{"file_type":"archive","size":10489153,"filename":"artifacts.zip","file_format":"zip"},{"file_type":"metadata","size":158,"filename":"metadata.gz","file_format":"gzip"},{"file_type":"trace","size":3146,"filename":"job.log","file_format":null}]
4828297943
[{"file_type":"archive","size":5244673,"filename":"artifacts.zip","file_format":"zip"},{"file_type":"metadata","size":157,"filename":"metadata.gz","file_format":"gzip"},{"file_type":"trace","size":3145,"filename":"job.log","file_format":null}]
4828297940
[{"file_type":"archive","size":1049089,"filename":"artifacts.zip","file_format":"zip"},{"file_type":"metadata","size":157,"filename":"metadata.gz","file_format":"gzip"},{"file_type":"trace","size":3140,"filename":"job.log","file_format":null}]#!/usr/bin/env python
import datetime
import gitlab
import os
import sys
GITLAB_SERVER = os.environ.get('GL_SERVER', 'https://gitlab.com')
GITLAB_TOKEN = os.environ.get('GL_TOKEN') # token requires developer permissions
PROJECT_ID = os.environ.get('GL_PROJECT_ID') #optional
GROUP_ID = os.environ.get('GL_GROUP_ID') #optional
if __name__ == "__main__":
if not GITLAB_TOKEN:
print("🤔 Please set the GL_TOKEN env variable.")
sys.exit(1)
gl = gitlab.Gitlab(GITLAB_SERVER, private_token=GITLAB_TOKEN, pagination="keyset", order_by="id", per_page=100)
# Collect all projects, or prefer projects from a group id, or a project id
projects = []
# Direct project ID
if PROJECT_ID:
projects.append(gl.projects.get(PROJECT_ID))
# Groups and projects inside
elif GROUP_ID:
group = gl.groups.get(GROUP_ID)
for project in group.projects.list(include_subgroups=True, get_all=True):
manageable_project = gl.projects.get(project.id , lazy=True)
projects.append(manageable_project)
for project in projects:
jobs = project.jobs.list(pagination="keyset", order_by="id", per_page=100, iterator=True)
for job in