Checkov
Checkov = open-source IaC scanner โดย Bridgecrew (Prisma Cloud) — เป็นที่นิยมที่สุดสำหรับ Terraform
ทำไม Checkov?
- 🔍 750+ pre-built policies สำหรับ Terraform, K8s, CloudFormation, ARM, Bicep, Helm, Dockerfile
- 🆓 Open-source + free
- 🐍 Custom policies ผ่าน Python (และ YAML/JSON)
- 📊 Detailed remediation guidance
- ✅ CIS, HIPAA, PCI, SOC2 compliance built-in
Install
# Python
pip install checkov
# Brew
brew install checkov
# Docker
docker pull bridgecrew/checkov
# Verify
checkov --version
Basic Scan
# Scan current directory
checkov -d .
# Specific path
checkov -d ./terraform
# Scan plan file (more accurate)
terraform plan -out=tfplan
terraform show -json tfplan > plan.json
checkov -f plan.json
ตัวอย่าง Output
_ _
___| |__ ___ ___| | _______ __
/ __| '_ \ / _ \/ __| |/ / _ \ \ / /
| (__| | | | __/ (__| < (_) \ V /
\___|_| |_|\___|\___|_|\_\___/ \_/
By bridgecrew.io | version: 3.2.0
terraform scan results:
Passed checks: 145, Failed checks: 5, Skipped checks: 0
Check: CKV_AWS_18: "Ensure the S3 bucket has access logging enabled"
FAILED for resource: aws_s3_bucket.data
File: /main.tf:5-10
5 | resource "aws_s3_bucket" "data" {
6 | bucket = "my-data"
7 | }
Guide: https://docs.bridgecrew.io/docs/s3_13-enable-logging
Check: CKV_AWS_19: "Ensure all data stored in the S3 bucket is securely encrypted at rest"
FAILED for resource: aws_s3_bucket.data
...
Output Formats
# Default
checkov -d .
# JSON
checkov -d . -o json
# JUnit XML (CI)
checkov -d . -o junitxml
# SARIF (GitHub)
checkov -d . -o sarif
# CSV
checkov -d . -o csv
# CycloneDX (SBOM)
checkov -d . -o cyclonedx_json
# GitHub PR comment format
checkov -d . -o github_failed_only
Severity & Filters
# Specific check IDs
checkov -d . --check CKV_AWS_18,CKV_AWS_19
# Skip checks
checkov -d . --skip-check CKV_AWS_20
# Severity
checkov -d . --check HIGH,CRITICAL
ตัวอย่าง Common Failures
CKV_AWS_18: S3 logging
# ❌ Failed
resource "aws_s3_bucket" "data" {
bucket = "my-data"
}
# ✅ Pass
resource "aws_s3_bucket_logging" "data" {
bucket = aws_s3_bucket.data.id
target_bucket = aws_s3_bucket.logs.id
target_prefix = "logs/"
}
CKV_AWS_19: S3 encryption
# ✅ Pass
resource "aws_s3_bucket_server_side_encryption_configuration" "data" {
bucket = aws_s3_bucket.data.id
rule {
apply_server_side_encryption_by_default {
sse_algorithm = "AES256"
}
}
}
CKV_AWS_24: Open SSH
# ❌ Failed
resource "aws_security_group" "web" {
ingress {
from_port = 22
to_port = 22
protocol = "tcp"
cidr_blocks = ["0.0.0.0/0"] # ← public SSH
}
}
# ✅ Pass
ingress {
from_port = 22
to_port = 22
protocol = "tcp"
cidr_blocks = ["10.0.0.0/8"] # ← internal only
}
Skip Checks (Inline)
# checkov:skip=CKV_AWS_18:Reason here
resource "aws_s3_bucket" "test" {
bucket = "test-no-logging-needed"
}
Config File
.checkov.yaml
directory:
- .
skip-check:
- CKV_AWS_18
- CKV_AWS_20
soft-fail: true # exit 0 even if checks fail
quiet: false
framework:
- terraform
output: cli
skip-framework:
- dockerfile
checkov # auto-loads .checkov.yaml
Custom Policies (Python)
custom-checks/aws/S3PrivateAcl.py
from checkov.common.models.enums import CheckCategories, CheckResult
from checkov.terraform.checks.resource.base_resource_check import BaseResourceCheck
class S3PrivateAcl(BaseResourceCheck):
def __init__(self):
name = "Ensure S3 bucket ACL is private"
id = "CKV_CUSTOM_001"
supported_resources = ["aws_s3_bucket"]
categories = [CheckCategories.GENERAL_SECURITY]
super().__init__(
name=name, id=id,
categories=categories,
supported_resources=supported_resources
)
def scan_resource_conf(self, conf):
acl = conf.get("acl", [None])[0]
if acl in ["public-read", "public-read-write"]:
return CheckResult.FAILED
return CheckResult.PASSED
check = S3PrivateAcl()
checkov -d . --external-checks-dir custom-checks
YAML Custom Policies (Easier)
custom-policies/no-public-s3.yaml
metadata:
name: "Ensure S3 bucket is not public"
guideline: "https://internal.docs.example.com/s3-security"
category: "GENERAL_SECURITY"
severity: "HIGH"
scope:
provider: aws
definition:
cond_type: attribute
resource_types:
- aws_s3_bucket
attribute: acl
operator: not_within
value: [public-read, public-read-write]
checkov -d . --external-checks-dir custom-policies
Compliance Reports
# CIS AWS
checkov -d . --compliance CIS_AWS
# HIPAA
checkov -d . --compliance HIPAA
# PCI DSS
checkov -d . --compliance PCI_DSS
# SOC2
checkov -d . --compliance SOC2
Scan Plan File (Best Accuracy)
# Generate plan
terraform init
terraform plan -out=tfplan
terraform show -json tfplan > plan.json
# Scan
checkov -f plan.json
→ Checkov เห็นค่า variable + computed values ที่จะ apply จริง
Skip Modules
checkov -d . --download-external-modules false # ไม่ download remote modules
Run on Remote Modules
checkov -d ~/.terraform/modules
CI/CD Integration
GitHub Actions
.github/workflows/checkov.yml
on: pull_request
jobs:
checkov:
runs-on: ubuntu-latest
permissions:
contents: read
security-events: write
steps:
- uses: actions/checkout@v4
- name: Checkov
uses: bridgecrewio/checkov-action@master
with:
directory: .
framework: terraform
output_format: sarif
output_file_path: checkov.sarif
soft_fail: false
quiet: true
- name: Upload SARIF
uses: github/codeql-action/upload-sarif@v3
with:
sarif_file: checkov.sarif
GitLab CI
checkov:
image: bridgecrew/checkov:latest
script:
- checkov -d . -o junitxml > checkov-report.xml
artifacts:
reports:
junit: checkov-report.xml
Pre-commit
.pre-commit-config.yaml
- repo: https://github.com/bridgecrewio/checkov
rev: 3.2.0
hooks:
- id: checkov
args: [-d, .]
Compare with Other Scanners
| Feature | Checkov | KICS | Trivy | Terrascan |
|---|---|---|---|---|
| Policies | 750+ | 2,400+ | 1,000+ | 500+ |
| Custom (lang) | Python + YAML | Rego | Rego | Rego |
| Speed | Slow | Medium | Fast | Medium |
| Plan support | ✅ | ✅ | ✅ | ✅ |
| Compliance | ✅ Strong | ✅ | Limited | ✅ |
| Maintained by | Bridgecrew/Prisma | Checkmarx | Aqua | Tenable |
| Popularity | ⭐⭐⭐⭐⭐ | ⭐⭐⭐ | ⭐⭐⭐⭐ | ⭐⭐ |
→ Checkov = most popular เพราะ docs ดี, community ใหญ่
Best Practices
✅ DO:
- Run Checkov ใน CI ทุก PR
- Scan plan.json (more accurate than .tf)
- ใช้ SARIF + GitHub Code Scanning
- Compliance scan ตามอุตสาหกรรม (HIPAA, PCI)
- Custom policies for org-specific rules
❌ DON'T:
- ห้าม skip-check โดยไม่อ่านเหตุผล
- ห้าม soft-fail ใน prod CI
- ห้ามคิดว่า scanner = ปลอดภัย 100%
- ห้ามแค่ scan ครั้งเดียว — ต้อง continuous
ตัวอย่าง Workflow แบบเต็ม
#!/bin/bash
set -e
echo "=== Validation ==="
terraform fmt -check -recursive
terraform init -backend=false
terraform validate
echo "=== Linting ==="
tflint --recursive
echo "=== Security Scans ==="
trivy config --severity HIGH,CRITICAL .
checkov -d . --framework terraform --check HIGH,CRITICAL
echo "=== Cost ==="
infracost breakdown --path .
echo "=== Plan ==="
terraform plan -out=tfplan
echo "=== Plan-based Security ==="
terraform show -json tfplan > plan.json
checkov -f plan.json
สรุป
- Checkov = most popular IaC scanner
- 750+ policies สำหรับ Terraform + อื่นๆ
- Custom policies ใน Python หรือ YAML
- Compliance scan: CIS, HIPAA, PCI, SOC2
- ใช้ scan plan.json เพื่อ accuracy สูงสุด
- ใช้คู่กับ TFLint + Trivy + Infracost = security ครบ
ต่อไป → Section 19: HCP