返回首页

Semgrep+CodeQL替代Checkmarx:开源SAST最佳实践

+替代Checkmarx:开源最佳实践

为什么我们要逃离商业SAST?

每年花5万美金买Checkmarx授权,结果扫描出来的漏洞还是靠人工review确认——这是很多安全团队的真实写照。商业SAST工具确实功能全面,但价格不透明、规则黑盒、部署依赖厂商支持,这些痛点让人头疼。

好消息是:2024年开源SAST生态已经成熟到可以完全替代商业方案。本文将手把手教你用Semgrep+CodeQL搭建一套企业级静态应用安全测试平台,覆盖代码审计全流程。

付费工具定价对比

在开始之前,先看看主流商业SAST工具的价格区间:

工具 年费估算 授权模式 核心卖点
Checkmarx SAST $50,000+/年 按开发者数量 语言覆盖全面,企业级支持
Fortify (OpenText) $40,000+/年 按扫描量/开发者 老牌厂商,合规报告
SonarQube $18,000+/年 按项目规模 质量+安全一体化
Veracode $30,000+/年 按扫描次数 部署,合规审计

注意:以上价格均为公开渠道估算,实际报价通常更高,且包含强制的年度维护费。对于100人开发团队,年花费轻松突破10万美元。

开源替代方案全景图

我们的开源组合拳:

  • Semgrep:规则编写极其灵活,支持自定义模式匹配,-first设计,集成无痛
  • CodeQL出品,语义分析能力强大,能追踪数据流,对公共仓库完全免费
  • SonarQube Community:质量门禁+基础安全扫描,适合日常开发
  • Bandit专用安全扫描器,轻量快速

功能对比表:

功能 Checkmarx Semgrep CodeQL SonarQube CE Bandit
语言支持 25+ 30+ 10+ 20+ Python
自定义规则 支持 极佳 支持(需学QL) 有限 有限
数据流分析 极强
CI/CD集成 支持 极佳 GitHub原生 支持 支持
扫描速度 慢(首次) 极快
学习曲线 极低
许可证费用 $50K+ 免费 免费(公共) 免费 免费

实战一:Semgrep安装与配置

安装Semgrep

# 方式一:pip安装(推荐)
pip3 install semgrep

# 方式二: Homebrew
brew install semgrep

# 方式三:Docker
docker pull semgrep/semgrep

# 验证安装
semgrep --version

基础扫描

# 使用OWASP Top 10规则集扫描项目
semgrep --config=p/owasp-top-ten ./src

# 使用Python安全规则
semgrep --config=p/python ./src

# 多规则组合扫描
semgrep --config=p/owasp-top-ten --config=p/security-audit ./src

# 输出JSON报告
semgrep --config=p/owasp-top-ten --json -o report.json ./src

编写自定义规则

创建 custom-rules.yaml

rules:
  - id: detect-
    patterns:
      - pattern: |
          $CURSOR.execute("..." + $VAR + "...")
      - pattern-not-inside: |
          $CURSOR.execute("..." + $PARAMS ...)
    message: >
      检测到SQL拼接,存在SQL注入风险。请使用参数化查询。
    severity: ERROR
    languages: [python]
    metadata:
      cwe:
        - "CWE-89: SQL Injection"
      owasp:
        - A03:2021 - Injection

  - id: detect-hardcoded-password
    patterns:
      - pattern-either:
          - pattern: password = "..."
          - pattern: passwd = "..."
          - pattern: secret = "..."
          - pattern: api_key = "..."
    message: 检测到硬编码密码/密钥,存在泄露风险。
    severity: 
    languages: [python]

  - id: detect-unsafe-deserialization
    patterns:
      - pattern-either:
          - pattern: pickle.loads(...)
          - pattern: yaml.load(..., Loader=yaml.FullLoader)
          - pattern: yaml.load(...)
    message: 不安全的反序列化操作,可能导致远程代码执行。
    severity: ERROR
    languages: [python]

运行自定义规则:

semgrep --config=custom-rules.yaml ./src

CI/CD集成(GitHub Actions)

创建 .github/workflows/semgrep.yml

name: Semgrep SAST
on:
  push:
    branches: [main, develop]
  pull_request:
    branches: [main]

jobs:
  semgrep:
    runs-on: ubuntu-latest
    container:
      : semgrep/semgrep
    steps:
      - uses: actions/checkout@
      - run: semgrep ci --config=p/owasp-top-ten --config=p/security-audit

实战二:CodeQL安装与配置

安装CodeQL CLI

# 下载CodeQL CLI
wget https://github.com/github/codeql-cli-binaries/releases/latest/download/codeql-linux64.zip
unzip codeql-linux64.zip -d /opt/
export PATH=$PATH:/opt/codeql

# 验证
codeql --version

# 下载代码查询包
git clone https://github.com/github/codeql-.git
git clone https://github.com/github/codeql.git

创建CodeQL数据库

# Python项目
codeql  create my-db --language=python --source-root=./src

# Java项目
codeql database create my-db --language=java --source-root=./src   --command='mvn clean compile -DskipTests'

# 项目
codeql database create my-db --language=javascript --source-root=./src

# Go项目
codeql database create my-db --language=go --source-root=./src

运行安全查询

# 使用标准安全查询套件
codeql database analyze my-db   codeql/python/ql/src/Security   --format=sarif-latest   --output=results.sarif

# 自定义QL查询示例:检测SQL注入

创建 sql_injection.ql

/**
 * @name SQL injection via string concatenation
 * @description Detecting SQL injection vulnerabilities
 * @kind problem
 * @problem.severity error
 * @id py/sql-injection-custom
 * @tags 
 *       external/cwe/cwe-89
 */

import python
import semmle.python.security.dataflow.SqlInjectionQuery
import semmle.python.security.dataflow.SqlInjectionCustomizations

from SqlInjection::FlowPath source, SqlInjection::FlowPath sink
where SqlInjection::flowPath(source, sink)
select sink.getNode(), "This query depends on $@, which is user-controlled.",
       source.getNode(), "user input"

运行自定义查询:

codeql database analyze my-db sql_injection.ql   --format=csv --output=sql_results.csv

GitHub原生CodeQL

在GitHub仓库中启用CodeQL极其简单:

  1. 进入仓库 Settings > Code security and
  2. 点击 Code 下的 "Set up" 按钮
  3. 选择 "Default" 配置即可自动扫描

或手动配置 .github/workflows/codeql.yml

name: CodeQL Analysis
on:
  push:
    branches: [main]
  pull_request:
    branches: [main]
  schedule:
    - cron: '0 6 * * 1'

jobs:
  analyze:
    runs-on: ubuntu-latest
    permissions:
      security-events: write
    strategy:
      matrix:
        language: ['python', 'javascript']
    steps:
      - uses: actions/checkout@v4
      - uses: github/codeql-action/init@v3
        with:
          languages: ${{ matrix.language }}
          queries: security-extended
      - uses: github/codeql-action/autobuild@v3
      - uses: github/codeql-action/analyze@v3

组合方案:Semgrep + CodeQL最佳实践

两条工具各有侧重,组合使用效果最佳:

阶段 工具 用途
开发阶段 Semgrep 实时提示,快速反馈
PR阶段 Semgrep + CodeQL 双重扫描,互为补充
定期审计 CodeQL 深度数据流分析
合规报告 SonarQube CE 质量门禁+趋势追踪

统一扫描脚本

#!/bin/bash
# sast-scan.sh - 统一SAST扫描脚本
set -e
PROJECT_DIR=${1:-.}
REPORT_DIR="./sast-reports/$(date +%Y%m%d)"
mkdir -p $REPORT_DIR

echo "[*] 开始Semgrep扫描..."
semgrep --config=p/owasp-top-ten --config=p/security-audit   --json -o $REPORT_DIR/semgrep.json $PROJECT_DIR

echo "[*] 开始CodeQL扫描..."
codeql database create $REPORT_DIR/codeql-db   --language=python --source-root=$PROJECT_DIR --overwrite
codeql database analyze $REPORT_DIR/codeql-db   codeql/python/ql/src/Security   --format=sarif-latest   --output=$REPORT_DIR/codeql.sarif

echo "[*] 扫描完成,报告位于: $REPORT_DIR"
echo "[*] Semgrep发现: $(python3 -c "import json; print(len(json.load(open('$REPORT_DIR/semgrep.json'))['results']))") 个问题"

常见问题与排错

Q:Semgrep规则匹配率低怎么办? A:使用 semgrep --config=p/r2c-security-audit 扩大覆盖,或在 https://semgrep.dev/explore 浏览社区规则。

Q:CodeQL首次扫描太慢? A:首次需要构建数据库,后续增量扫描会快很多。建议只对变更文件做增量分析。

Q:误报率高怎么处理? A:Semgrep可用 paths.exclude 排除测试目录;CodeQL可用 @precision medium 标记过滤低置信度结果。

总结

用Semgrep+CodeQL替代Checkmarx,不仅能省下每年5万美元的授权费,还能获得更高的透明度和灵活性。Semgrep的规则即代码特性让安全策略可版本化管理,CodeQL的语义分析能力在深度上不输商业工具。

关键建议:先从Semgrep上手(学习曲线低),跑稳后再引入CodeQL做深度分析。两者组合,覆盖90%以上的SAST场景,且完全开源免费。团队的安全左移,从今天开始。

常见问题

为什么我们要逃离商业SAST?

>为什么我们要逃离商业SAST?每年花5万美金买Checkmarx授权,结果扫描出来的漏洞还是靠人工review确认——这是很多安全团队的真实写照。商业SAST工具确实功能全面,但价格不透明、规则黑盒、部署依赖厂商支持,这些痛点让人头疼。 好消息是:2024年开源SAST生态已经成熟到可以完全替代商业方案。本文将手把手教你用Semgrep+CodeQL搭建一套企业级静态应用安全测试平台,覆盖代码审计全流程。

评论