PHP 怎么SAST 工具

wen PHP项目 1

本文目录导读:

PHP 怎么SAST 工具

  1. 主流 PHP SAST 工具
  2. 具体实施方法
  3. 自定义 PHP SAST 实现
  4. CI/CD 集成
  5. 最佳实践建议

在 PHP 中进行 SAST(静态应用安全测试),可以通过以下方式和工具实现:

主流 PHP SAST 工具

商业工具

  • SonarQube - 最流行的开源的代码质量平台,支持 PHP
  • Checkmarx - 企业级 SAST 工具
  • Fortify SCA - 商业安全扫描工具
  • Veracode - 云安全平台

开源工具

# RIPS - 最早的 PHP 安全扫描器
# PHPStan - 静态分析工具
# Psalm - 静态类型检查器
# PHP_CodeSniffer - 编码标准检查
# 专门的 PHP 安全工具:
# - Progpilot
# - Wapiti
# - Phan

具体实施方法

使用 PHPStan

# 安装
composer require --dev phpstan/phpstan
# 配置 phpstan.neon
parameters:
    level: 8
    paths:
        - src
    reportUnmatchedIgnoredErrors: false
    checkMissingIterableValueType: true

使用 Psalm

# 安装
composer require --dev vimeo/psalm
# 初始化
vendor/bin/psalm --init
# 运行扫描
vendor/bin/psalm --alter --issues=Security

使用 SonarQube

# Docker 部署
docker run -d --name sonarqube -p 9000:9000 sonarqube
# 安装 PHP 分析器
sonar-scanner -Dsonar.projectKey=your-project \
  -Dsonar.sources=src \
  -Dsonar.host.url=http://localhost:9000 \
  -Dsonar.login=your-token

自定义 PHP SAST 实现

基础扫描脚本

<?php
class PHPCodeScanner {
    private $dangerousFunctions = [
        'eval', 'system', 'exec', 'shell_exec', 'passthru',
        'popen', 'proc_open', 'assert', 'unserialize',
        'include', 'require', 'file_get_contents', 'fopen'
    ];
    private $vulnerabilities = [];
    public function scanFile($filePath) {
        $content = file_get_contents($filePath);
        $lines = explode("\n", $content);
        foreach ($lines as $lineNum => $line) {
            $this->checkDangerousFunctions($line, $lineNum + 1);
            $this->checkSQLInjection($line, $lineNum + 1);
            $this->checkXSS($line, $lineNum + 1);
        }
        return $this->vulnerabilities;
    }
    private function checkDangerousFunctions($line, $lineNum) {
        foreach ($this->dangerousFunctions as $func) {
            if (preg_match('/\b' . $func . '\s*\(/', $line)) {
                $this->vulnerabilities[] = [
                    'type' => 'dangerous_function',
                    'line' => $lineNum,
                    'description' => "使用危险函数: {$func}()",
                    'code' => $line
                ];
            }
        }
    }
    private function checkSQLInjection($line, $lineNum) {
        if (preg_match('/(SELECT|INSERT|UPDATE|DELETE).*\$_(GET|POST|REQUEST)/i', $line)) {
            $this->vulnerabilities[] = [
                'type' => 'sql_injection',
                'line' => $lineNum,
                'description' => '可能存在 SQL 注入风险',
                'code' => $line
            ];
        }
    }
    private function checkXSS($line, $lineNum) {
        if (preg_match('/echo.*\$_(GET|POST|REQUEST)/i', $line) && 
            !preg_match('/htmlspecialchars|htmlentities|filter_var/i', $line)) {
            $this->vulnerabilities[] = [
                'type' => 'xss',
                'line' => $lineNum,
                'description' => '存在 XSS 漏洞风险',
                'code' => $line
            ];
        }
    }
}
// 使用示例
$scanner = new PHPCodeScanner();
$result = $scanner->scanFile('path/to/your/file.php');
print_r($result);

目录递归扫描

<?php
function scanDirectory($dir, $scanner) {
    $files = scandir($dir);
    $allVulnerabilities = [];
    foreach ($files as $file) {
        if ($file == '.' || $file == '..') continue;
        $path = $dir . '/' . $file;
        if (is_dir($path)) {
            $allVulnerabilities = array_merge(
                $allVulnerabilities, 
                scanDirectory($path, $scanner)
            );
        } elseif (pathinfo($file, PATHINFO_EXTENSION) == 'php') {
            $vulns = $scanner->scanFile($path);
            foreach ($vulns as $v) {
                $v['file'] = $path;
                $allVulnerabilities[] = $v;
            }
        }
    }
    return $allVulnerabilities;
}
// 使用
$scanner = new PHPCodeScanner();
$results = scanDirectory('./src', $scanner);

CI/CD 集成

GitLab CI 配置

# .gitlab-ci.yml
php-sast:
  stage: test
  image: php:8.2
  script:
    - composer install --dev
    - vendor/bin/phpstan analyse src --no-progress
    - vendor/bin/psalm --no-cache
  artifacts:
    reports:
      sast: gl-sast-report.json

GitHub Actions

name: PHP SAST
on: [push, pull_request]
jobs:
  security-scan:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v3
      - name: Setup PHP
        uses: shivammathur/setup-php@v2
        with:
          php-version: '8.2'
      - name: Install dependencies
        run: composer install --dev
      - name: Run PHPStan
        run: vendor/bin/phpstan analyse src --level=8
      - name: Run Psalm
        run: vendor/bin/psalm --show-info=true

最佳实践建议

扫描策略

  1. 定期扫描 - 在每次代码提交时进行扫描
  2. 分层扫描 - 基础扫描 + 深度扫描
  3. 误报处理 - 建立误报库,减少干扰

关注重点

  • SQL 注入
  • XSS 跨站脚本
  • 命令注入
  • 文件包含漏洞
  • 不安全的反序列化
  • 敏感信息泄露

集成流程

选择工具组合
2. 配置扫描规则
3. 集成到 CI/CD
4. 建立问题追踪
5. 定期更新规则库

通过以上方法,你可以实现 PHP 代码的静态安全扫描,帮助在开发早期发现潜在的安全问题。

抱歉,评论功能暂时关闭!