GitLab

GitDevOpsCI/CDセキュリティプラットフォームマージリクエストセルフホストオールインワン

バージョン管理ツール

GitLab

概要

GitLabは、AI駆動の包括的DevSecOpsプラットフォームで、ソフトウェア開発ライフサイクル全体を単一のアプリケーションで統合する革新的なアプローチを採用しています。2011年に設立され、Git管理、CI/CD、プロジェクト管理、課題追跡、セキュリティスキャンを統合提供し、8%のマーケットシェアでDevOps統合プラットフォームとして地位を確立。セルフホスト可能な点で企業での採用が増加し、コードコミットから本番環境まで一貫したワークフローを実現しています。

詳細

GitLab 2025年版は、包括的DevSecOpsプラットフォームとして成熟度を増し続けています。AI機能GitLab Duoによるコード提案から脆弱性説明、マージリクエスト生成まで開発ライフサイクル全体でAI支援を提供。ネイティブCI/CD、セキュリティスキャン、プロジェクト管理を単一プラットフォームで統合し、外部ツール依存を最小化。セルフホスト型とクラウド型の両方をサポートし、企業要件に応じた柔軟な導入が可能です。特に大規模チームでのコスト削減効果が高く、完全制御を求める企業に最適なソリューションを提供しています。

主な特徴

  • オールインワンDevOpsプラットフォーム: バージョン管理からデプロイまで単一統合
  • AI統合: GitLab Duoによる開発ライフサイクル全体でのAI支援
  • ネイティブCI/CD: プラットフォーム内蔵の高度な自動化パイプライン
  • 包括的セキュリティ: SAST、DAST、依存関係スキャン等のDevSecOps統合
  • セルフホスト対応: 無料プランでもオンプレミス展開可能
  • 企業向け機能: SAML/SCIM、監査ログ、コンプライアンス対応

メリット・デメリット

メリット

  • 単一プラットフォームでの包括的DevOpsライフサイクル統合
  • セルフホスト型での完全制御とデータ主権の確保
  • 大規模チームでの大幅なコスト削減効果(年間$10,000+節約可能)
  • ネイティブCI/CDによる外部ツール統合不要の効率性
  • AI駆動セキュリティによる脆弱性の自動検出・修正提案
  • 無料プランでもセルフホスト可能な柔軟性

デメリット

  • セルフホスト運用でのメンテナンス責任(月約6時間)
  • GitHubと比較した開発者コミュニティの小ささ
  • 学習コストが高く、初期設定の複雑さ
  • UI/UXがGitHubより複雑で直感性に欠ける面
  • サードパーティ統合の選択肢がGitHubより限定的
  • マーケットプレイスのエコシステムが小規模

参考ページ

書き方の例

インストールとセットアップ

# GitLab CLI (glab) のインストール
# macOS
brew install glab

# Ubuntu/Debian
curl -s https://api.github.com/repos/profclems/glab/releases/latest | grep "browser_download_url.*linux_amd64.deb" | cut -d '"' -f 4 | wget -qi -
sudo dpkg -i glab_*_linux_amd64.deb

# 認証設定
glab auth login

# Git設定(GitLab用)
git config --global user.name "Your Name"
git config --global user.email "[email protected]"

# SSH鍵の設定
ssh-keygen -t ed25519 -C "[email protected]"
cat ~/.ssh/id_ed25519.pub  # GitLabに登録

プロジェクト作成とクローン

# 新しいプロジェクトを作成
glab repo create my-project --public
glab repo create my-private-project --private

# 既存プロジェクトをクローン
git clone [email protected]:username/project.git
glab repo clone username/project

# GitLab.comのプロジェクトを検索
glab repo search "react components"

# プロジェクト情報表示
glab repo view username/project

マージリクエスト(MR)ワークフロー

# 1. 最新のmainブランチを取得
git checkout main
git pull origin main

# 2. 新しいブランチで作業
git checkout -b feature/user-authentication

# 3. 開発・コミット
echo "新機能のコード" > auth.js
git add auth.js
git commit -m "feat: ユーザー認証機能を追加"

# 4. ブランチをプッシュ
git push -u origin feature/user-authentication

# 5. マージリクエストを作成
glab mr create --title "ユーザー認証機能を追加" \
               --description "・ログイン/ログアウト機能\n・JWT認証\n・パスワードハッシュ化" \
               --assignee @username \
               --label "feature,authentication"

# 6. マージリクエスト一覧確認
glab mr list
glab mr view 123

# 7. レビュー対応
git checkout feature/user-authentication
# 修正作業
git add .
git commit -m "fix: レビューコメントに対応"
git push origin feature/user-authentication

# 8. マージリクエスト承認・マージ
glab mr merge 123 --squash

CI/CDパイプライン設定

# .gitlab-ci.yml - 基本的なパイプライン
stages:
  - build
  - test
  - security
  - deploy

variables:
  NODE_VERSION: "20"
  DOCKER_DRIVER: overlay2

# テンプレートの使用
include:
  - template: Jobs/Dependency-Scanning.gitlab-ci.yml
  - template: Jobs/SAST.gitlab-ci.yml
  - template: Jobs/Secret-Detection.gitlab-ci.yml

# Node.js アプリケーションのビルド
build:
  stage: build
  image: node:${NODE_VERSION}
  cache:
    key: ${CI_COMMIT_REF_SLUG}
    paths:
      - node_modules/
  script:
    - npm ci
    - npm run build
  artifacts:
    paths:
      - dist/
    expire_in: 1 hour

# テスト実行
test:unit:
  stage: test
  image: node:${NODE_VERSION}
  cache:
    key: ${CI_COMMIT_REF_SLUG}
    paths:
      - node_modules/
    policy: pull
  script:
    - npm ci
    - npm run test:unit
  coverage: '/Statements\s*:\s*([^%]+)/'
  artifacts:
    reports:
      coverage_report:
        coverage_format: cobertura
        path: coverage/cobertura-coverage.xml

test:integration:
  stage: test
  image: node:${NODE_VERSION}
  services:
    - postgres:13
  variables:
    POSTGRES_DB: test_db
    POSTGRES_USER: test
    POSTGRES_PASSWORD: test
    DATABASE_URL: "postgresql://test:test@postgres:5432/test_db"
  script:
    - npm ci
    - npm run test:integration

# セキュリティテスト
security:audit:
  stage: security
  image: node:${NODE_VERSION}
  script:
    - npm audit --audit-level high
  allow_failure: true

# デプロイ(本番環境)
deploy:production:
  stage: deploy
  image: alpine:latest
  before_script:
    - apk add --no-cache curl
  script:
    - echo "Deploying to production..."
    - curl -X POST "$DEPLOY_WEBHOOK_URL" 
      -H "Content-Type: application/json"
      -d '{"ref":"'$CI_COMMIT_SHA'","environment":"production"}'
  environment:
    name: production
    url: https://myapp.example.com
  only:
    - main
  when: manual  # 手動承認が必要

# レビュー環境(マージリクエスト用)
deploy:review:
  stage: deploy
  image: alpine:latest
  script:
    - echo "Deploying review app for MR $CI_MERGE_REQUEST_IID"
    - echo "Review URL: https://mr-$CI_MERGE_REQUEST_IID.review.example.com"
  environment:
    name: review/$CI_MERGE_REQUEST_IID
    url: https://mr-$CI_MERGE_REQUEST_IID.review.example.com
    on_stop: stop:review
  only:
    - merge_requests

stop:review:
  stage: deploy
  image: alpine:latest
  script:
    - echo "Stopping review app for MR $CI_MERGE_REQUEST_IID"
  environment:
    name: review/$CI_MERGE_REQUEST_IID
    action: stop
  when: manual
  only:
    - merge_requests

Auto DevOps設定

# .gitlab-ci.yml - Auto DevOps カスタマイズ
include:
  - template: Auto-DevOps.gitlab-ci.yml

variables:
  # Auto DevOps 設定
  AUTO_DEVOPS_DOMAIN: auto-devops.example.com
  POSTGRES_ENABLED: "true"
  POSTGRES_VERSION: "13"
  
  # セキュリティスキャン設定
  SAST_DISABLE: "false"
  DEPENDENCY_SCANNING_DISABLE: "false"
  SECRET_DETECTION_DISABLE: "false"
  
  # Kubernetes 設定
  KUBE_NAMESPACE: my-app-production
  PRODUCTION_REPLICAS: 3
  
  # Docker設定
  DOCKER_TLS_CERTDIR: "/certs"

# カスタムビルドステップ
build:
  extends: .auto-devops-build
  before_script:
    - echo "Custom build preparation"
    - npm install -g @angular/cli

# カスタムテスト
test:custom:
  stage: test
  image: node:20
  script:
    - npm ci
    - npm run lint
    - npm run test:e2e
  only:
    - merge_requests
    - main

セキュリティ機能

# セキュリティ専用パイプライン
stages:
  - security-scan
  - vulnerability-management

# SAST(静的アプリケーションセキュリティテスト)
sast:
  stage: security-scan
  include:
    - template: Jobs/SAST.gitlab-ci.yml

# DAST(動的アプリケーションセキュリティテスト)
dast:
  stage: security-scan
  include:
    - template: Jobs/DAST-On-Demand-Scan.gitlab-ci.yml
  variables:
    DAST_WEBSITE: https://your-app.example.com

# 依存関係スキャン
dependency_scanning:
  stage: security-scan
  include:
    - template: Jobs/Dependency-Scanning.gitlab-ci.yml

# シークレット検出
secret_detection:
  stage: security-scan
  include:
    - template: Jobs/Secret-Detection.gitlab-ci.yml

# コンテナスキャン
container_scanning:
  stage: security-scan
  include:
    - template: Jobs/Container-Scanning.gitlab-ci.yml
  variables:
    CS_IMAGE: $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA

# Infrastructure as Code スキャン
iac_scanning:
  stage: security-scan
  include:
    - template: Jobs/SAST-IaC.gitlab-ci.yml

# セキュリティレポート統合
security:report:
  stage: vulnerability-management
  image: alpine:latest
  script:
    - echo "Generating security report..."
  artifacts:
    reports:
      sast: gl-sast-report.json
      dependency_scanning: gl-dependency-scanning-report.json
      secret_detection: gl-secret-detection-report.json

Issues(課題管理)とエピック

# Issue操作
glab issue list
glab issue create --title "バグ: ログイン機能が動作しない" \
                  --description "詳細説明..." \
                  --assignee @username \
                  --label "bug,priority-high"

glab issue view 123
glab issue close 123

# エピック操作(Premium以上)
glab epic list
glab epic create --title "ユーザー管理機能" \
                 --description "ユーザー管理に関する機能群"

# Issue をエピックに関連付け
glab issue update 123 --add-epic 456

GitLab Pages設定

# .gitlab-ci.yml - GitLab Pages
pages:
  stage: deploy
  image: node:20
  script:
    - npm ci
    - npm run build
    - mkdir public
    - cp -r dist/* public/
  artifacts:
    paths:
      - public
  only:
    - main

# カスタムドメイン設定例
pages:custom-domain:
  extends: pages
  environment:
    name: production
    url: https://www.example.com
  only:
    - main

Docker Registry活用

# GitLab Container Registry ログイン
docker login registry.gitlab.com

# イメージビルド・プッシュ
docker build -t registry.gitlab.com/username/project:latest .
docker push registry.gitlab.com/username/project:latest

# CI/CDでのDocker使用例
# .gitlab-ci.yml
docker:build:
  stage: build
  image: docker:latest
  services:
    - docker:dind
  before_script:
    - docker login -u $CI_REGISTRY_USER -p $CI_REGISTRY_PASSWORD $CI_REGISTRY
  script:
    - docker build -t $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA .
    - docker push $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA
    - docker tag $CI_REGISTRY_IMAGE:$CI_COMMIT_SHA $CI_REGISTRY_IMAGE:latest
    - docker push $CI_REGISTRY_IMAGE:latest

GitLab API活用

// GitLab API v4 使用例
const axios = require('axios');

const gitlabApi = axios.create({
  baseURL: 'https://gitlab.com/api/v4',
  headers: {
    'Private-Token': process.env.GITLAB_TOKEN
  }
});

// プロジェクト情報取得
async function getProject(projectId) {
  try {
    const response = await gitlabApi.get(`/projects/${projectId}`);
    console.log('Project:', response.data.name);
    console.log('Stars:', response.data.star_count);
    console.log('Language:', response.data.default_branch);
  } catch (error) {
    console.error('Error:', error.response.data);
  }
}

// マージリクエスト作成
async function createMergeRequest(projectId, data) {
  try {
    const response = await gitlabApi.post(`/projects/${projectId}/merge_requests`, {
      source_branch: data.sourceBranch,
      target_branch: data.targetBranch,
      title: data.title,
      description: data.description,
      assignee_id: data.assigneeId
    });
    
    console.log('MR created:', response.data.web_url);
  } catch (error) {
    console.error('Error:', error.response.data);
  }
}

// パイプライン状態確認
async function getPipelineStatus(projectId, pipelineId) {
  try {
    const response = await gitlabApi.get(`/projects/${projectId}/pipelines/${pipelineId}`);
    console.log('Pipeline status:', response.data.status);
    console.log('Duration:', response.data.duration);
  } catch (error) {
    console.error('Error:', error.response.data);
  }
}

// 使用例
getProject('12345678');
createMergeRequest('12345678', {
  sourceBranch: 'feature/new-function',
  targetBranch: 'main',
  title: '新機能追加',
  description: '詳細説明...',
  assigneeId: 987654
});

セルフホスト型GitLab設定

# Docker Composeを使用したGitLab セルフホスト
# docker-compose.yml
version: '3.6'

services:
  gitlab:
    image: gitlab/gitlab-ce:latest
    hostname: 'gitlab.example.com'
    ports:
      - '80:80'
      - '443:443'
      - '22:22'
    volumes:
      - './data/gitlab/config:/etc/gitlab'
      - './data/gitlab/logs:/var/log/gitlab'
      - './data/gitlab/data:/var/opt/gitlab'
    environment:
      GITLAB_OMNIBUS_CONFIG: |
        external_url 'https://gitlab.example.com'
        gitlab_rails['gitlab_shell_ssh_port'] = 22
        nginx['enable'] = true
        nginx['redirect_http_to_https'] = true

# 起動
docker-compose up -d

# 初期設定確認
docker exec -it gitlab_gitlab_1 gitlab-rake gitlab:check

# バックアップ
docker exec -t gitlab_gitlab_1 gitlab-backup create

# 復元
docker exec -t gitlab_gitlab_1 gitlab-backup restore BACKUP=1640123456_2024_12_15_15.6.2

高度なワークフロー

# マルチプロジェクト パイプライン
trigger:downstream:
  stage: deploy
  trigger:
    project: team/infrastructure
    branch: main
    strategy: depend
  variables:
    APP_VERSION: $CI_COMMIT_SHA
    ENVIRONMENT: production

# 並列実行とマトリックス
test:matrix:
  stage: test
  image: node:$NODE_VERSION
  parallel:
    matrix:
      - NODE_VERSION: ["18", "20", "22"]
        TEST_SUITE: ["unit", "integration"]
  script:
    - npm ci
    - npm run test:$TEST_SUITE

# 条件付き実行
deploy:staging:
  stage: deploy
  script:
    - deploy-to-staging.sh
  rules:
    - if: $CI_COMMIT_BRANCH == "develop"
    - if: $CI_PIPELINE_SOURCE == "merge_request_event"
      changes:
        - "src/**/*"

# 手動承認ワークフロー
deploy:production:
  stage: deploy
  script:
    - deploy-to-production.sh
  environment:
    name: production
    url: https://app.example.com
  when: manual
  only:
    - main
  before_script:
    - echo "本番環境へのデプロイを実行します"