08 - 開発者向け DevSecOps: CI/CD パイプラインの SAST、DAST、セキュリティ
2024 年 2 月、あるセキュリティ研究者が、どのようにセキュリティが侵害されるかを実証しました。 tj-アクション/変更されたファイル、23,000 以上のリポジトリで使用されている GitHub アクション、 数千の組織の CI/CD パイプラインから機密情報を抜き出すことが可能でした。 問題はアプリケーション コードにではなく、依存関係にもなく、パイプラインにもありました ソフトウェアを保護するはずだったツール自体が攻撃ベクトルになっていました。
このシナリオは不都合な真実を反映しています: ほとんどのチームはセキュリティに投資しています アプリケーション コードのセキュリティは保護しますが、それを構築する CI/CD インフラストラクチャのセキュリティは無視します。 テストして配布します。 DevSecOps は、いくつかのスキャン ツールをパイプラインに統合するだけではなく、 しかしアプローチの根本的な変更: 安全性は各フェーズの不可欠な部分でなければなりません リリース前の最終チェックではなく、開発サイクルの全体的なチェックです。
DORA 2025 レポートによると、包括的な DevSecOps プラクティスを採用しているチームは、 重大な脆弱性の平均修復時間 (MTTR) が 4 分の 1 に短縮 ステージングまたは運用環境でのみセキュリティ テストを実行するチームと比較して。費用 本番環境でのセキュリティ バグの修正は、平均して 100 倍のコストがかかります。 開発中に修正してください。「シフトレフト」原則には経済的正当性があります。 堅実であり、技術的です。
何を学ぶか
- シフトレフト セキュリティ: 開発サイクルの最初からセキュリティを統合します。
- Semgrep および CodeQL を使用した SAST: ソース コードの静的分析
- OWASP ZAP を使用した DAST: 実行中のアプリケーションの動的テスト
- Snyk および Trivy による SCA: 依存関係のソフトウェア構成分析
- Gitleaks と TruffleHog を使用したシークレット スキャン: 資格情報漏洩の防止
- Checkov を使用した IaC セキュリティ: Terraform および Kubernetes マニフェストのスキャン
- セキュリティ ゲートを備えた完全な GitHub Actions パイプライン
- DevSecOps の成熟度を測定するための指標と KPI
シフトレフトセキュリティ: 基本原則
「シフトレフト」という用語は、開発サイクルを線で視覚的に表現したものに由来しています。 タイムラインは左 (計画、開発) から右 (テスト、本番) までです。を移動します。 左側のセキュリティとは、セキュリティチェックをできるだけセキュリティに近づけることを意味します。 コードが記述される瞬間: 開発者の IDE、コミット前フック、 ステージング環境だけでなく、プル リクエストも可能です。
最も事後的なものから最もプロアクティブなものまで、シフトレフトのセキュリティのレベルは次のとおりです。
- レベル 0 - 生産: 脆弱性スキャンは本番環境でのみ行われます。遅い、高い。
- レベル 1 - ステージング/プリプロダクション: テスト環境の DAST。良くなりましたが、まだ遅いです。
- レベル 2 - CI/CD パイプライン: SAST、SCA、プッシュごとのシークレット スキャン。 DevSecOps 標準。
- レベル 3 - プル リクエスト: 各 PR の自動セキュリティ レビュー。高速かつ状況に応じた対応。
- レベル 4 - 事前コミット: コミット前のローカルチェック。即時フィードバック。
- レベル 5 - FDI: エディターのセキュリティ プラグイン (Snyk IDE、CodeQL 拡張機能)。リアルタイム。
45%のパラドックス
Veracode と GitLab の調査によると、コードの 45% は AI ツールによって生成されています (GitHub Copilot、Cursor、Claude Code) にはセキュリティ上の脆弱性があり、失敗する可能性があります 基本的なセキュリティテスト。 AI が本質的に危険だからではなく、複製するからです トレーニング データセットに安全でないコード パターンが存在します。これにより、コントロールが作成されます CI/CD での自動化は、バイブコーディングと AI 支援の時代ではさらに重要になります 開発。シリーズを見る バイブコーディング このトピックをさらに深く掘り下げるために。
SAST: 静的アプリケーション セキュリティ テスト
SAST は、アプリケーションを実行せずにソース コード、バイトコード、またはバイナリを分析します。 脆弱なコード パターン、構成ミス、セキュリティのアンチパターンを探します。 これは最も速い制御 (数秒または数分で実行可能) であり、統合することができます。 IDE、コミット前フック、CI/CD パイプラインで直接実行できます。
他のアプローチに対する SAST の主な利点は次のとおりです。 ソース コード上で実行されます。 (実行中のアプリケーション インスタンスは必要ありません)、最初に脆弱性を特定します めったに実行されないコード パスを含む、コードの 100% を分析できます。 主な欠点は誤検知率が高く、トリアージ プロセスが必要となることです。 そしてルールの調整。
Semgrep: SAST オープンソースで高速
Semgrep は、おそらく 2025 年のオープンソース エコシステムで最も使用される SAST ツールです。
その強みは、ルールの構文がシンプルであること (コードとほぼ同じ構造) にあります。
分析)、実行速度、および TypeScript、JavaScript のネイティブ サポート、
Python、Go、Java、その他多くの言語。何千ものセキュリティ ルールを
公式登録簿 semgrep.dev.
# Installazione Semgrep
pip install semgrep
# oppure con Homebrew
brew install semgrep
# Scansione base con ruleset OWASP
semgrep --config p/owasp-top-ten .
# Scansione con regole specifiche per JavaScript/TypeScript
semgrep --config p/javascript .
semgrep --config p/typescript .
# Regole per Angular/Node.js
semgrep --config p/nodejs-express-security .
semgrep --config p/jwt .
# Output in formato SARIF per GitHub Security tab
semgrep --config p/owasp-top-ten --sarif --output semgrep.sarif .
# Output JSON per processing automatico
semgrep --config p/owasp-top-ten --json --output semgrep.json .
# Escludi cartelle non rilevanti
semgrep --config p/owasp-top-ten \
--exclude="node_modules,dist,coverage,*.min.js" .
# Regola custom Semgrep per trovare JWT senza verifica della firma
# .semgrep/jwt-insecure.yaml
# rules:
# - id: jwt-decode-without-verify
# patterns:
# - pattern: jwt.decode($TOKEN, ...)
# - pattern-not: jwt.verify($TOKEN, ...)
# message: "Uso di jwt.decode senza verifica: usa jwt.verify"
# severity: ERROR
# languages: [javascript, typescript]
CodeQL: 深いセマンティック分析
GitHub によって開発された CodeQL は、Semgrep よりも詳細な分析を実行します。 コード データベースを使用すると、SQL に似た言語クエリを記述して検索できるようになります。 複数レベルの関数呼び出し (汚染分析) を通じても脆弱性を検出します。 LinkedIn は 2026 年 2 月に、CodeQL と Semgrep の両方をある意味で使用すると発表しました。 最適なコードベース カバレッジを実現するために補完的です。 CodeQL はネイティブに統合されています GitHub Advanced Security は、パブリック リポジトリで無料で利用できます。
# .github/workflows/codeql.yml
name: CodeQL Security Analysis
on:
push:
branches: [main, develop]
pull_request:
branches: [main]
schedule:
# Analisi settimanale (domenica alle 2:00 UTC)
- cron: '0 2 * * 0'
permissions:
contents: read
security-events: write
actions: read
jobs:
codeql-analysis:
name: CodeQL Analysis
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
language: ['javascript-typescript']
steps:
- name: Checkout repository
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
- name: Initialize CodeQL
uses: github/codeql-action/init@dd746615b1a4b1e1c5d3b87432fe040f4c04082 # v3.28.0
with:
languages: {{ matrix.language }}
# Query suite: default, extended, security-extended
queries: security-extended
config: |
paths-ignore:
- node_modules
- dist
- '**/*.test.ts'
- '**/*.spec.ts'
- name: Autobuild
uses: github/codeql-action/autobuild@dd746615b1a4b1e1c5d3b87432fe040f4c04082 # v3.28.0
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@dd746615b1a4b1e1c5d3b87432fe040f4c04082 # v3.28.0
with:
category: "/language:{{ matrix.language }}"
upload: true
SAST: 誤検知とトリアージ
SAST の主な問題は、誤検知の数です。つまり、攻撃的なルールセットです。 コミットごとに何百ものレポートが生成される可能性があり、プロセスを持続不可能にする可能性があります。 推奨される戦略は、高重大度プロファイル (CRITICAL/HIGH のみ) から始めることです。 特定のコードベースのルールを調整し、徐々に増加させます。 チームがツールに慣れるにつれてカバー範囲が広がります。ビルドをブロックしないでください 確立されたトリアージプロセスのない低/中型の場合。
DAST: 動的アプリケーションセキュリティテスト
SAST はコードを実行せずに分析しますが、DAST はアプリケーションを実行中にテストします。 実行では、攻撃者が行うような外部からの実際の攻撃をシミュレートします。ダスト SAST が認識できない脆弱性を発見します: サーバー構成の問題、 実行時の動作、REST API の脆弱性、および認証の問題 これらは実際の HTTP リクエストでのみ出現します。
DAST は SAST を補完するものであり、代替品ではありません。SAST は脆弱性の 70 ~ 80% を検出します。 ソース コード内で、DAST は実行時にのみ現れる残りの 20 ~ 30% を見つけます。一つには 完全にカバーするには、両方が必要です。
OWASP ZAP: オープンソース エコシステムの DAST 標準
OWASP ZAP (Zed Attack Proxy) は、オープンソースの世界で最も使用されている DAST ツールです。 GitHub Actions でのネイティブ統合。 CI/CD には 3 つの主要なモードが提供されます。 ベースラインスキャン (受動的、非侵襲的、あらゆる PR に最適)、 フルスキャン (アクティブ、実際の攻撃ペイロードを使用、隔離された環境でのみ) e APIスキャン (OpenAPI/Swagger に特化しており、マイクロサービスに最適です)。
# .github/workflows/dast-zap.yml
name: DAST Security Scan (OWASP ZAP)
on:
push:
branches: [main]
workflow_dispatch:
inputs:
target_url:
description: 'URL target per la scansione DAST'
required: true
default: 'https://staging.myapp.com'
permissions:
contents: read
issues: write # ZAP crea issues GitHub per le vulnerabilità trovate
jobs:
zap-baseline-scan:
name: OWASP ZAP Baseline Scan
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
# Baseline scan: scansione PASSIVA (non invia payload di attacco)
# Ideale per ogni PR/push - veloce e non invasivo
- name: ZAP Baseline Scan
uses: zaproxy/action-baseline@v0.14.0
with:
target: 'https://staging.myapp.com'
rules_file_name: '.zap/rules.tsv'
fail_action: true
cmd_options: '-a -j -l WARN'
# Full scan: scansione ATTIVA (usa payload di attacco reali)
# Solo in ambienti di test isolati, mai in produzione!
# - name: ZAP Full Scan (staging only)
# uses: zaproxy/action-full-scan@v0.11.0
# with:
# target: 'https://staging-isolated.myapp.com'
# API Scan: specializzato per REST API con OpenAPI spec
# - name: ZAP API Scan
# uses: zaproxy/action-api-scan@v0.9.0
# with:
# target: 'https://api.staging.myapp.com/openapi.json'
- name: Upload ZAP Report
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.0
if: always()
with:
name: zap-report
path: report_html.html
# .zap/rules.tsv - personalizzazione regole ZAP
# ID ACTION PARAM
# 10015 WARN # Incomplete or No Cache-control Header Set
# 10038 IGNORE # CSP Header Not Set (gestito separatamente dal server)
# 10096 WARN # Timestamp Disclosure
# 40014 IGNORE # CSRF (se il token CSRF e implementato lato app)
SSR を使用した Angular プロジェクトの場合、DAST は到達可能なインスタンス上で実行する必要があります パイプラインから。一時的なステージング環境での効果的な戦略と展開 (Firebase Hosting Preview Channel などで) パイプラインの一部として実行します。 DAST に合格し、DAST が合格した場合にのみ実稼働環境へのデプロイメントを続行します。
# Esempio: Deploy staging effimero + DAST in pipeline Angular
# .github/workflows/angular-devsecops.yml (estratto)
jobs:
deploy-staging:
runs-on: ubuntu-latest
outputs:
staging_url: {{ steps.deploy.outputs.details_url }}
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
- run: npm ci --ignore-scripts
- run: npm run build --configuration=staging
- name: Deploy to Firebase Hosting preview channel
id: deploy
uses: FirebaseExtended/action-hosting-deploy@v0
with:
repoToken: {{ secrets.GITHUB_TOKEN }}
firebaseServiceAccount: {{ secrets.FIREBASE_SERVICE_ACCOUNT }}
channelId: staging-{{ github.run_id }}
expires: 1d
dast-scan:
needs: deploy-staging
runs-on: ubuntu-latest
permissions:
contents: read
issues: write
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
- name: ZAP Baseline Scan on ephemeral staging
uses: zaproxy/action-baseline@v0.14.0
with:
target: {{ needs.deploy-staging.outputs.staging_url }}
fail_action: true
rules_file_name: '.zap/rules.tsv'
SCA: ソフトウェア構成分析
SCA (ソフトウェア構成分析) は、アプリケーションのオープンソース依存関係を分析します。 既知の脆弱性 (CVE)、ライセンスの問題、古いパッケージを特定します。 このシリーズの前の記事 ( サプライ チェーン セキュリティ: npm 監査と SBOM) npm Audit、Snyk、Dependabot、SBOM の生成について詳しく説明します。この中で これに関連して、SCA と IaC の両方のスキャンを 1 つで提供する Trivy に焦点を当てます。 統合された DevSecOps パイプラインに最適なツールです。
# Trivy: SCA + container + IaC in un unico tool
# Installazione
curl -sfL https://raw.githubusercontent.com/aquasecurity/trivy/main/contrib/install.sh \
| sh -s -- -b /usr/local/bin
# Scansione dipendenze npm (SCA)
trivy fs --scanners vuln --pkg-types library .
# Solo vulnerabilità HIGH e CRITICAL (per security gate)
trivy fs --scanners vuln --severity HIGH,CRITICAL \
--pkg-types library --exit-code 1 .
# Output SARIF per GitHub Security tab
trivy fs --scanners vuln --format sarif \
--output trivy-results.sarif .
# Scansione con SBOM output (CycloneDX)
trivy fs --format cyclonedx --output sbom.json .
# File .trivyignore per CVE accettati (con motivazione obbligatoria!)
# .trivyignore
# CVE-2023-44270 # postcss: impatto solo in CLI, non nel build output - review 2026-06-01
# Scansione completa: vuln + segreti + misconfigurazioni
trivy fs --scanners vuln,secret,misconfig .
# GitHub Actions con Trivy Action ufficiale
# - name: Run Trivy vulnerability scanner
# uses: aquasecurity/trivy-action@d43c1f16c00cfd3978dde6c07f4bbcf9eb6993ca
# with:
# scan-type: 'fs'
# scan-ref: '.'
# scanners: 'vuln,secret'
# severity: 'HIGH,CRITICAL'
# exit-code: '1'
# format: 'sarif'
# output: 'trivy-results.sarif'
シークレットのスキャン: 資格情報漏洩の防止
毎週、何千もの秘密が公開 GitHub で誤って公開されています。 API キー、OAuth トークン、データベース パスワード、プライベート証明書。 GitGuardian、 公共リポジトリを監視し、2024 年に 1,200 万以上が検出されたと報告 公開リポジトリで公開された秘密の数、前年比 28% 増加 以前。シークレットがパブリック リポジトリに置かれると (たとえ数分間であっても) 削除する前に)、危険にさらされているとみなして、すぐにローテーションする必要があります。
Gitleaks と TruffleHog は、シークレット検出に最もよく使用される 2 つのツールです。 補足: Gitleaks は高速で CI/CD に最適で、TruffleHog は積極的にチェックします 見つかったシークレットがまだ有効であるかどうか (誤検知が大幅に減少します)。
Gitleaks: 構成と統合
# Installazione Gitleaks
brew install gitleaks
# oppure scarica il binario da GitHub Releases
# https://github.com/gitleaks/gitleaks/releases
# Scansione del repository corrente (tutti i commit)
gitleaks detect --source . --verbose
# Scansione solo dei file staged (per pre-commit hook)
gitleaks protect --staged --verbose
# Scansione di un range di commit specifico
gitleaks detect --source . --log-opts HEAD~1..HEAD
# Output in formato JSON
gitleaks detect --source . --report-format json \
--report-path gitleaks-report.json
# Configurazione pre-commit con pre-commit framework
# .pre-commit-config.yaml
# repos:
# - repo: https://github.com/gitleaks/gitleaks
# rev: v8.24.2
# hooks:
# - id: gitleaks
# Configurazione custom .gitleaks.toml
# [extend]
# useDefault = true
#
# [[rules]]
# id = "internal-api-token"
# description = "Token API interno MyCompany"
# regex = '''mycompany_token_[0-9a-zA-Z]{32}'''
# tags = ["token", "internal"]
#
# [allowlist]
# description = "Test fixtures e placeholder sicuri"
# regexTarget = "line"
# regexes = [
# '''EXAMPLE_TOKEN_PLACEHOLDER''',
# '''test_secret_[a-z0-9]{8}'''
# ]
# paths = [
# '''.*_test\.ts''',
# '''.*\.spec\.ts''',
# '''.*\.fixture\.ts'''
# ]
TruffleHog: アクティブ シークレットの検証
# Installazione TruffleHog
curl -sSfL https://raw.githubusercontent.com/trufflesecurity/trufflehog/main/scripts/install.sh \
| sh -s -- -b /usr/local/bin
# Scansione con verifica attiva (riduce falsi positivi)
trufflehog git file://. --only-verified
# Scansione di un repository remoto
trufflehog github --repo https://github.com/myorg/myrepo --only-verified
# Output JSON per processing
trufflehog git file://. --json --no-verification
# GitHub Actions: secrets scanning su ogni push/PR
# .github/workflows/secrets-scan.yml
# - name: TruffleHog secrets scan
# uses: trufflesecurity/trufflehog@main
# with:
# path: ./
# base: $GITHUB_BASE_REF
# head: HEAD
# extra_args: --only-verified
# Differenza chiave Gitleaks vs TruffleHog:
# - Gitleaks: veloce, pattern matching, ottimo per pre-commit e CI
# - TruffleHog: verifica attiva (testa il secret contro l'API reale)
# Risultato: meno falsi positivi, ma più lento e invasivo
# Raccomandazione: entrambi in pipeline (Gitleaks fast, TruffleHog verified)
git rm ではシークレットが削除されない
シークレットが誤ってコミットされた場合は、次のコマンドを使用してファイルを削除します。 git rm または
ファイルを追加します .gitignore それだけでは十分ではありません: 秘密はまだあります
git 履歴に表示されます。本当に削除するには、次を使用します git filter-repo
(GitHub によって公式に推奨されているツール)、すべてのブランチを強制プッシュします。
秘密が漏洩したとみなして、すぐにローテーションします。 GitHub では、
リポジトリ設定のネイティブ「シークレット スキャン」ツールを監視
200 以上の既知のトークン タイプの履歴を継続的にコミットします。
IaC セキュリティ: Terraform および Kubernetes 用の Checkov
Infrastructure as Code (IaC) はインフラストラクチャ管理を民主化しましたが、 また、Terraform、Kubernetes ファイルの構成ミスという新たなリスクベクトルも導入されました。 マニフェスト、Docker Compose、インフラストラクチャ全体を公開できる AWS CloudFormation です。 Checkov (Bridgecrew/Palo Alto Networks) は、1000 以上のファイルを静的にスキャンします。 CIS ベンチマーク、NIST、その他の標準にマッピングされた統合セキュリティ ポリシー。
注: Aqua Security のオリジナル IaC スキャン ツールである tfsec が統合されました トリビーで。新しいプロジェクトの場合は、IaC 用の Trivy またはより広範囲をカバーする Checkov をお勧めします。
# Installazione Checkov
pip install checkov
# oppure con Homebrew
brew install checkov
# Scansione directory Terraform
checkov -d ./terraform
# Scansione Kubernetes manifests
checkov -d ./k8s --framework kubernetes
# Scansione Dockerfile
checkov -f Dockerfile --framework dockerfile
# Output in formato SARIF per GitHub Security
checkov -d ./terraform --output sarif --output-file checkov.sarif
# Skippa check specifici (con commento di motivazione!)
checkov -d ./terraform --skip-check CKV_AWS_18,CKV_AWS_21
# Violazioni Terraform AWS comuni che Checkov rileva:
# CKV_AWS_18: S3 bucket - access logging disabilitato
# CKV_AWS_57: S3 bucket - ACL pubblica (mai in produzione!)
# CKV_AWS_87: Lambda - non in VPC
# CKV_AWS_135: EC2 - IMDSv1 abilitato (usa IMDSv2)
# Esempio Kubernetes manifest INSICURO (violazioni Checkov):
# apiVersion: v1
# kind: Pod
# spec:
# containers:
# - name: app
# image: myapp:latest # CKV_K8S_14: usa tag specifico, non :latest
# securityContext:
# runAsRoot: true # CKV_K8S_6: non eseguire come root
# privileged: true # CKV_K8S_16: non usare privileged mode
# resources: {} # CKV_K8S_11: definisci resource limits
# Esempio Kubernetes manifest SICURO (supera Checkov):
# spec:
# containers:
# - name: app
# image: myapp:1.2.3
# securityContext:
# runAsNonRoot: true
# runAsUser: 1000
# allowPrivilegeEscalation: false
# readOnlyRootFilesystem: true
# resources:
# limits:
# memory: "256Mi"
# cpu: "500m"
# requests:
# memory: "128Mi"
# cpu: "250m"
GitHub Actions パイプラインの完成: 究極のセキュリティ ゲート
これらすべてのツールを 1 つの一貫したパイプラインに統合するには、計画が必要です 注意してください: すべてのジョブがビルドをブロックする必要があるわけではありません。一部のスキャンの方が適切です。 PR 用、その他はメインでのプッシュ用、および非並列化は並列化が基本です 開発フローが過度に遅くなります。次のパイプラインは 1 つを示しています 6 つの並列および順次ジョブによる完全な構成。
# .github/workflows/devsecops-complete.yml
name: DevSecOps Security Pipeline
on:
push:
branches: [main, develop]
pull_request:
branches: [main]
schedule:
- cron: '0 3 * * 1' # Ogni lunedi alle 3:00 UTC (scan completo)
# Permissions minime a livello workflow (principio del minimo privilegio)
permissions:
contents: read
jobs:
# ===== JOB 1: SECRETS SCANNING (primo - fail fast) =====
secrets-scan:
name: Secrets Scanning
runs-on: ubuntu-latest
permissions:
contents: read
steps:
- name: Checkout
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
with:
fetch-depth: 0 # Storia completa per Gitleaks
- name: Gitleaks secrets detection
uses: gitleaks/gitleaks-action@v2
env:
GITHUB_TOKEN: {{ secrets.GITHUB_TOKEN }}
# ===== JOB 2: SCA - Dependency Vulnerabilities =====
sca-scan:
name: SCA Dependency Audit
runs-on: ubuntu-latest
permissions:
contents: read
security-events: write
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
- uses: actions/setup-node@39370e3970a6d050c480ffad4ff0ed4d3fdee5af # v4.1.0
with:
node-version: '22'
cache: 'npm'
- run: npm ci --ignore-scripts
- name: npm audit (solo production deps)
run: npm audit --audit-level=high --omit=dev
- name: Trivy SCA scan
uses: aquasecurity/trivy-action@d43c1f16c00cfd3978dde6c07f4bbcf9eb6993ca
with:
scan-type: 'fs'
scan-ref: '.'
scanners: 'vuln'
severity: 'HIGH,CRITICAL'
exit-code: '1'
format: 'sarif'
output: 'trivy-vuln.sarif'
- name: Upload Trivy results
uses: github/codeql-action/upload-sarif@dd746615b1a4b1e1c5d3b87432fe040f4c04082
if: always()
with:
sarif_file: 'trivy-vuln.sarif'
# ===== JOB 3: SAST - Static Code Analysis =====
sast-scan:
name: SAST Static Analysis
runs-on: ubuntu-latest
permissions:
contents: read
security-events: write
actions: read
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
- name: Initialize CodeQL
uses: github/codeql-action/init@dd746615b1a4b1e1c5d3b87432fe040f4c04082
with:
languages: 'javascript-typescript'
queries: security-extended
- name: Autobuild
uses: github/codeql-action/autobuild@dd746615b1a4b1e1c5d3b87432fe040f4c04082
- name: CodeQL Analysis
uses: github/codeql-action/analyze@dd746615b1a4b1e1c5d3b87432fe040f4c04082
with:
category: "/language:javascript-typescript"
- name: Semgrep SAST
uses: semgrep/semgrep-action@v1
with:
config: >-
p/owasp-top-ten
p/javascript
p/typescript
p/jwt
env:
SEMGREP_APP_TOKEN: {{ secrets.SEMGREP_APP_TOKEN }}
# ===== JOB 4: IaC Security =====
iac-scan:
name: IaC Security Scan
runs-on: ubuntu-latest
permissions:
contents: read
security-events: write
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
- name: Trivy config scan
uses: aquasecurity/trivy-action@d43c1f16c00cfd3978dde6c07f4bbcf9eb6993ca
with:
scan-type: 'config'
scan-ref: '.'
severity: 'HIGH,CRITICAL'
exit-code: '1'
- name: Checkov IaC scan
uses: bridgecrewio/checkov-action@v12
with:
directory: .
framework: all
soft_fail_on: MEDIUM
hard_fail_on: HIGH,CRITICAL
# ===== JOB 5: DAST (solo su push a main) =====
dast-scan:
name: DAST ZAP Baseline
runs-on: ubuntu-latest
if: github.event_name == 'push' && github.ref == 'refs/heads/main'
needs: [secrets-scan, sca-scan, sast-scan]
permissions:
contents: read
issues: write
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
- name: ZAP Baseline Scan
uses: zaproxy/action-baseline@v0.14.0
with:
target: {{ secrets.STAGING_URL }}
fail_action: true
- name: Upload ZAP Report
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
if: always()
with:
name: zap-report-{{ github.sha }}
path: report_html.html
retention-days: 30
# ===== JOB 6: SBOM (su push a main dopo tutti i check) =====
sbom-generate:
name: Generate SBOM
runs-on: ubuntu-latest
if: github.ref == 'refs/heads/main'
needs: [sca-scan, sast-scan, iac-scan]
permissions:
contents: write
id-token: write
attestations: write
steps:
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
- uses: actions/setup-node@39370e3970a6d050c480ffad4ff0ed4d3fdee5af
with:
node-version: '22'
- run: npm ci --ignore-scripts
- name: Generate SBOM (CycloneDX)
run: |
npm install -g @cyclonedx/cyclonedx-npm
cyclonedx-npm --omit dev \
--output-format json \
--output-file sbom-{{ github.sha }}.json
- name: Attest SBOM
uses: actions/attest-build-provenance@v1
with:
subject-path: sbom-{{ github.sha }}.json
- name: Upload SBOM
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
with:
name: sbom-{{ github.sha }}
path: sbom-{{ github.sha }}.json
retention-days: 365
セキュリティ ゲート: 構築されるブロックと構築されないブロック
効果的なセキュリティ ゲートは、すべての警告をブロックするのではなく、問題を区別します。 すぐに対応が必要な問題と、時間をかけて対処できる問題です。 基本的なルールは次のとおりです。 明らかに危険で実行可能なもののみをブロックします。 誤検知が多すぎる場合や脆弱性が低い場合にビルドをブロックすると、チームは無効化することになります。 完全に制御できなくなり、投資全体が台無しになります。
推奨されるセキュリティ ゲート マトリックス
- 常にブロック: コード内の秘密、修正が必要な重大な脆弱性 利用可能、SAST インジェクション/RCE 所見、IaC 構成ミス重大 (S3 パブリック バケット、入力 SSH のセキュリティ グループ 0.0.0.0/0)
- メインでブロックします (PR ではありません): 高い脆弱性があり、修正が利用可能、 DAST の検出結果が FAIL に設定され、依存関係に互換性のないライセンスが設定されます (GPL 市販品)
- 警告 (通知はしますが、ブロックはしません): 修正のない高い脆弱性 利用可能、SAST では MEDIUM、IaC HIGH、回避策は次のとおりです。 例外、DAST の検出結果が WARN に設定される
- 無視 (ドキュメントあり): LOW/INFO の脆弱性、誤検知 例外ファイル (.trivyignore、.gitleaks.toml ホワイトリスト) に文書化されています。 特定のアプリケーション コンテキストに実際の影響を与えない CVE
# Gestione delle eccezioni documentate nei file di configurazione
# .trivyignore - CVE accettati con motivazione obbligatoria
# Formato: CVE-ID # [data] Motivazione e piano di revisione
CVE-2023-44270 # [2026-02-01] postcss: impatto solo in CLI usage, non nel build output. Review 2026-06
# .gitleaks.toml - allowlist per pattern non pericolosi
# [allowlist]
# description = "Test fixtures, placeholder e valori di esempio"
# regexes = [
# '''EXAMPLE_API_KEY_[A-Z0-9]{16}''',
# '''test_secret_placeholder''',
# '''YOUR_TOKEN_HERE'''
# ]
# paths = [
# '''.*\.spec\.ts''',
# '''.*\.fixture\.ts''',
# '''README\.md'''
# ]
# Semgrep - eccezione inline nel codice sorgente
# Aggiungi commento sulla stessa riga per sopprimere un finding
# const regex = new RegExp(userPattern); // nosemgrep: javascript.lang.security.audit.unsafe-regex
# Checkov - soppressione inline nel file Terraform
# resource "aws_s3_bucket" "cdn_assets" {
# bucket = "my-public-cdn-assets"
# #checkov:skip=CKV_AWS_57: Bucket CDN per assets statici pubblici - progettato per essere pubblico
# }
Angular チェックリスト: DevSecOps パイプライン
Angular プロジェクトには、次のような DevSecOps に関する特別な考慮事項があります。 ツールチェーン (Angular CLI、esbuild、ng-packagr)、バインディング付きの HTML テンプレートの使用 動的、および Node.js サーバー Express を使用した SSR へ。
# Angular DevSecOps Checklist
# 1. SAST: regole Semgrep specifiche per Angular
# Patterns pericolosi da rilevare:
# - DomSanitizer.bypassSecurityTrustHtml(userInput) senza sanitizzazione
# - [innerHTML]="untrustedData" (binding HTML non sicuro)
# - eval() o new Function() in servizi Angular
# - HttpClient senza interceptor di autenticazione
# 2. SECRETS: environment files NON devono contenere valori reali
# SBAGLIATO - environment.ts committato con secret:
# export const environment = {
# apiKey: 'sk-prod-real-key-12345', # Bloccato da Gitleaks!
# googleMapsKey: 'AIza...' # Bloccato da Gitleaks!
# };
# CORRETTO - placeholder nei file committati, valori iniettati in CI:
# export const environment = {
# apiKey: '', // iniettato a build time dalla pipeline CI/CD
# };
# In pipeline: sed -i "s/apiKey: ''/apiKey: '{{ secrets.API_KEY }}'/" src/environments/environment.prod.ts
# 3. CSP HEADER nel server SSR Angular (Express)
# server.ts
# import { randomBytes } from 'crypto';
# const generateNonce = () => randomBytes(16).toString('base64');
#
# app.use((req, res, next) => {
# const nonce = generateNonce();
# res.locals['nonce'] = nonce;
# res.setHeader('Content-Security-Policy', [
# "default-src 'self'",
# `script-src 'self' 'nonce-${nonce}'`,
# "style-src 'self' 'unsafe-inline'",
# "img-src 'self' data: https:",
# "connect-src 'self' https://api.myapp.com",
# "frame-ancestors 'none'"
# ].join('; '));
# next();
# });
# 4. SAST Semgrep per Angular (regola custom bypassSecurityTrust)
# .semgrep/angular-security.yaml
# rules:
# - id: angular-bypass-security-trust
# patterns:
# - pattern: this.$SANITIZER.bypassSecurityTrust$TYPE(...)
# message: "Uso di bypassSecurityTrust$TYPE: verifica la sanitizzazione del valore"
# severity: WARNING
# languages: [typescript]
# 5. Verifica e aggiornamento Angular LTS
ng version
npm outdated @angular/core @angular/cli @angular/material
npm audit --omit=dev --audit-level=high
DevSecOps 成熟度の指標と KPI
改善には測定が欠かせません。 DevSecOps メトリクスのバランスをとる必要がある 安全性の有効性を備えた開発のスピード。目標は決してゼロではない 脆弱性(達成不可能)はあるが、リスクを許容レベルまで軽減する できるだけ短い時間で。
DevSecOps の重要な KPI
- MTTD (平均検出時間): 導入間の平均時間 脆弱性とその検出。 CI/CD を使用したターゲット: 24 時間以内。 フルシフト左 (プリコミット) の場合: 数秒で検出。
- MTTR (平均修復時間): 検出から修正まで 生産中です。 OWASP ターゲット: CRITICAL の場合は 7 日未満、HIGH の場合は 30 日未満。 成熟した DevSecOps プロセスの場合: MTTR は従来のチームの 4 分の 1 です。
- 左シフト検出率 (SLDR): 脆弱性の割合 開発時と運用時に検出されます。ターゲット: 80% 以上が展開前に検出されました。
- 担保債務: 重大度ごとの未解決の脆弱性の総数。 時間の経過に伴う傾向を監視します。傾向は減少するか、安定したままでなければなりません。
- 誤検知率: 誤検知の SAST/DAST アラートの割合。 目標: チームの疲労を避け、プロセスの信頼性を維持するために 20% 未満。
- パイプライン期間: DevSecOps パイプラインの合計時間。 ターゲット: 生産性への影響を避けるため、SAST + SCA + シークレットは 10 分以内です。
- セキュリティ範囲: SAST によってカバーされるコードベースの割合、 DAST でカバーされる API の割合。目標: SAST で 90% 以上。
# Script per generare un report KPI di sicurezza dal progetto
# Conta vulnerabilità aperte con npm audit
npm audit --json | jq '.metadata.vulnerabilities'
# Output: { "info": 2, "low": 5, "moderate": 3, "high": 1, "critical": 0, "total": 11 }
# Conta findings SAST da Semgrep (JSON output)
semgrep --config p/owasp-top-ten --json . 2>/dev/null \
| jq '.results | group_by(.extra.severity) | map({severity: .[0].extra.severity, count: length})'
# Verifica durata pipeline (GitHub Actions API)
curl -s -H "Authorization: token $GITHUB_TOKEN" \
"https://api.github.com/repos/$OWNER/$REPO/actions/runs?per_page=10" \
| jq '[.workflow_runs[] | select(.name == "DevSecOps Security Pipeline") | {
run_id: .id,
status: .status,
conclusion: .conclusion,
duration_seconds: ((.updated_at | fromdateiso8601) - (.run_started_at | fromdateiso8601))
}]'
# Badge GitHub Actions per status sicurezza nel README
# 
DevSecOps 文化: ヒューマンファクター
テクノロジーだけでは十分ではありません: DevSecOps には文化的な変化が必要です セキュリティを専門チームの責任から責任へと変える すべての開発者によって共有されます。これには、トレーニング、明確なプロセス、そして何よりも、 安全性を障害物ではなく障害物として認識させる摩擦を取り除くこと 品質のツール。
成熟した DevSecOps 文化の基本原則は次のとおりです。
- 「コードとしてのセキュリティ」: セキュリティ ポリシーはコードであり、バージョン管理されています git では、他のコードベースの変更と同様にレビューされます。ポリシーの例外 コード自体に、正当な理由と改訂日とともに文書化されています。
- 即時の状況に応じたフィードバック: 開発者はフィードバックを受け取ります 数週間後には理解できない PDF レポートが作成されることはありません。 「この関数には 42 行目に SQL インジェクションの問題があります」というコンテキストが重要です。 「バックエンド モジュールで検出された脆弱性タイプ A07」よりもはるかに便利です。
- 責めることはありません、はい、学習しています: CI/CD で見つかった脆弱性は次のとおりです。 罰ではなく学習の機会です。導入した開発者 将来的にそれらを防ぐ理由と方法を理解する必要があります。
- セキュリティチャンピオンプログラム: どのチームにもセキュリティ チャンピオンがいます。 開発チームとセキュリティ チームの間の橋渡し役として機能し、アラートの初期トリアージを実行し、 状況に応じたベスト プラクティス。
- 予防的脅威モデリング: 機能を実装する前に、 チームは潜在的な攻撃ベクトルについて話し合います。 STRIDE (なりすまし、改ざん、 否認、情報開示、DoS、特権昇格)およびフレームワーク このプロセスではシンプルで実用的です。
今すぐ DevSecOps を始めるとすぐに効果が得られます
ゼロから始める場合は、すべてを一度に実装しようとしないでください。ここ 20% の労力で 80% のリスクをカバーする 3 つのステップ:
-
Gitleaks をプリコミットに追加する: プリコミットフレームワークをインストールします。
Gitleaks 構成を追加
.pre-commit-config.yaml、 走るpre-commit install。機密情報の漏洩を事前に防止 リモートリポジトリ。推定所要時間: 30 分。 -
CI で GitHub dependabot と npm Audit を有効にする: での依存ボットのアクティブ化
リポジトリ設定と追加
npm audit --audit-level=high --omit=dev既存の CI パイプラインに追加します。脆弱な依存関係に関する自動アラートを受信します。 推定所要時間: 1 時間。 - GitHub で CodeQL を有効にする: パブリックリポジトリは無料、含まれています エンタープライズプライベートリポジトリ向けの GitHub Advanced Security にあります。すべての自動 SAST 追加の構成を必要とせずにプッシュおよびプル リクエストを実行できます。 推定所要時間: 15 分。
結論と次のステップ
DevSecOps は購入する製品やインストールするツールではありません。プロセスです。 セキュリティ、開発、運用を 1 つのサイクルで統合する継続的な改善 高潔な。この記事で紹介するパイプラインは、すべての主要なレイヤーをカバーしています。 資格情報の漏洩を防ぐためのシークレット スキャン、依存関係の SCA、SAST ソース コードの場合は DAST、ランタイムの場合は DAST、インフラストラクチャの場合は IaC セキュリティ、 トレーサビリティとコンプライアンスのための SBOM の生成。
指針となる原則は常に同じです。問題が発生した場合はできるだけ早く問題を発見することです。 修正にかかる費用は最小限で済みます。 AI が生成したコードの 45% が失敗する 基本的なセキュリティ テストと DevSecOps の自動化は、この時代においてさらに重要になっています 人工知能によって支援された開発。私たちはそれに頼ることはできません 高速開発のコンテキストでの手動レビューのみに基づいて行われます。
この記事でシリーズは終了です 開発者向けの Web セキュリティ: OWASP トップ 10 の脆弱性からセキュリティ スタック全体を調べました。 フロントエンドの防御、バックエンドのセキュリティから暗号化、DevSecOps まで 自動化された測定可能なプロセスですべてのベスト プラクティスを統合する接着剤。 セキュリティは最終製品ではなく、継続的な取り組みです。各リリースは ソフトウェアのセキュリティ体制を改善する機会です。
シリーズ全体: 開発者のための Web セキュリティ
- 01 - OWASP トップ 10 2025: 開発者ガイド
- 02 - XSS、CSRF、CSP: フロントエンドのセキュリティ
- 03 - SQL インジェクションと入力検証: バックエンドのセキュリティ
- 04 - 安全な認証: セッションと Cookie
- 05 - API セキュリティ: OAuth 2.1、JWT、レート制限
- 06 - サプライ チェーン セキュリティ: npm 監査と SBOM
- 07 - 暗号エラー: ハッシュ、暗号化、トークン
- 08 - 開発者向け DevSecOps: CI/CD の SAST、DAST (この記事)
シリーズの詳細もご覧ください DevOps フロントエンド (ID 250 ~ 255) セキュリティを Angular デプロイメント ワークフローおよびシリーズと統合するため バイブコーディング リスクを理解するために AI 生成コードに特有のセキュリティ問題と、DevSecOps でそれらを軽減する方法。







