Souza2003/Vulnerability_Remediation_-_Verification

GitHub: Souza2003/Vulnerability_Remediation_-_Verification

这是一个针对 WebGoat 漏洞靶场的代码级安全修复实战项目,详细记录了结合 SAST 与 DAST 工具发现并修复 Java Spring Boot 应用中高危漏洞的全流程。

Stars: 0 | Forks: 0

# 🔼 漏洞修复与验证 — WebGoat 2023.4 **模块:** 软件开发网络安全 **项目:** 网络安全理学硕士 2025–26 | 都柏林商学院 **工具:** Semgrep · OWASP ZAP · Burp Suite · Windsurf · Java Spring Boot · Docker ## 概述 对 OWASP 的 intentionally vulnerable Java Spring Boot Web 应用程序 **WebGoat 2023.4** 进行了安全审计和代码级修复。使用 SAST (Semgrep) 和 DAST (OWASP ZAP) 工具识别出了三个高/严重级别漏洞,随后对其进行了全面修复和验证。 ## 安全态势:修复前 vs 修复后 | | 修复前 | 修复后 | |---|---|---| | Semgrep 发现总数 | 156 | 153 | | 严重漏洞 | 3 个活跃 | 0 (已全部修复) | | 风险评级 | 高风险 | 已降低 | | ZAP 重新扫描中的 PII 泄露 | 已检测到 | 未检测到 | ## 已修复漏洞 | # | 漏洞 | 工具 | 受影响文件 | 严重性 | 状态 | |---|---|---|---|---|---| | 1 | SQL 注入 | SAST — Semgrep | `Assignment5.java` (第 59–65 行) | 高危/严重 | ✅ 已完全修复 | | 2 | 路径遍历 | SAST — Semgrep | `ProfileUploadRetrieval.java` + `FileServer.java` | 高危/严重 | ✅ 已完全修复 | | 3 | PII 泄露 | DAST — OWASP ZAP | `CrossSiteScriptingLesson5a.java` (第 76 行) | 高危 | ✅ 已完全修复 | ## 漏洞 1 — SQL 注入 (CWE-89) **根本原因:** 用户输入被直接拼接到 SQL 字符串中。虽然调用了 `prepareStatement()` 但从未真正实现参数化 —— 没有 `?` 占位符或 `setString()` 调用。 **修复措施:** 将字符串拼接替换为正确的参数化查询。 ``` // BEFORE — vulnerable PreparedStatement statement = connection.prepareStatement( "select password from challenge_users where userid = '" + username_login + "' and password = '" + password_login + "'"); // AFTER — fixed PreparedStatement statement = connection.prepareStatement( "select password from challenge_users where userid = ? and password = ?"); statement.setString(1, username_login); statement.setString(2, password_login); ``` **新增安全层:** - 使用 `?` 占位符和 `setString()` 绑定的参数化查询 - 通过 `StringUtils.hasText()` (已有) 进行输入验证 - 通用错误处理 —— 原始数据库错误不会到达 HTTP 响应 ## 漏洞 2 — 路径遍历 (CWE-22) **根本原因:** 现有的过滤器只检查了字面上的 `..` 和 `/` —— 很容易被 URL 编码(`%2e%2e`, `%2f`)绕过。`getOriginalFilename()` 被直接使用而未经验证。 **修复措施:** 对两个受影响的文件实施了三层防御。 ``` // AFTER — ProfileUploadRetrieval.java // Layer 1: Whitelist — reject non-alphanumeric IDs if (id != null && !id.matches("[a-zA-Z0-9_-]+")) { return ResponseEntity.badRequest().body("Invalid id parameter"); } // Layer 2: Strip directory components String safeId = id != null ? FilenameUtils.getName(id) : null; var catPicture = new File(catPicturesDirectory, (safeId == null ? RandomUtils.nextInt(1,11) : safeId) + ".jpg"); // Layer 3: Canonical path boundary check if (!catPicture.getCanonicalPath().startsWith(catPicturesDirectory.getCanonicalPath())) { return ResponseEntity.badRequest().body("Access denied"); } ``` ``` // AFTER — FileServer.java String originalName = myFile.getOriginalFilename(); if (originalName == null || !originalName.matches("[a-zA-Z0-9._-]+")) { throw new IllegalArgumentException("Invalid filename"); } String safeFilename = FilenameUtils.getName(originalName); File destination = new File(destinationDir, safeFilename); if (!destination.getCanonicalPath().startsWith(destinationDir.getCanonicalPath())) { throw new SecurityException("Path traversal attempt detected"); } ``` ## 漏洞 3 — PII 泄露 (CWE-359) **根本原因:** 用户提供的信用卡号(Maestro BIN `505664`)在 `/CrossSiteScripting/attack5a` 端点的 HTTP 响应体中未经屏蔽地回传。 **修复措施:** 在卡号出现在任何 HTTP 响应之前对其进行屏蔽,将最后 4 位以外的所有数字替换为 `*`。 ## 使用的工具 | 工具 | 用途 | |---|---| | Semgrep | SAST — 静态源代码分析 | | OWASP ZAP | DAST — 运行时漏洞扫描 | | Burp Suite | HTTP 请求/响应的手动验证 | | Windsurf | 具有差异比较视图的 IDE,用于查看代码更改 | | Docker | WebGoat 环境容器化 | ## 核心要点 - 仅使用 `prepareStatement()` **并不** 能使查询参数化 —— 还需要 `?` 占位符和 `setString()` 调用。 - URL 编码可以绕过简单的字符串匹配过滤器;规范路径解析才是防御路径遍历的正确方法。 - SAST 和 DAST 是互补的 —— Semgrep 捕获了代码级的缺陷;ZAP 捕获了静态分析遗漏的运行时 PII 泄露。 - 消除了 3 个严重发现;应用程序从高风险转变为安全态势得到了显著改善。
标签:AppImage, Burp Suite, CISA项目, CWE-200, CWE-22, CWE-89, DAST, DevSecOps, Docker, JS文件枚举, MSc网络安全, OWASP ZAP, PII泄露, SAST, Semgrep, Spring Boot, SQL查询, WebGoat, Web应用防火墙, WordPress安全扫描, 上游代理, 个人信息泄露, 代码安全审计, 安全扫描, 安全防御评估, 恶意软件分析, 数据泄露, 时序注入, 漏洞修复, 盲注攻击, 网络安全, 网络安全培训, 请求拦截, 路径遍历, 软件安全开发, 隐私保护