近日,Apache Struts 2 框架曝出高危XML外部实体注入(XXE)漏洞,漏洞编号为CVE-2025-68493(官方同步命名为S2-069)。该漏洞覆盖Struts 2 从2.0.0到6.1.0的几乎全版本,危害等级被多家安全厂商评定为高危(CVSS评分暂估7.8,后续或因在野利用上调)。更值得警惕的是,据安全社区披露,该漏洞的PoC(概念验证代码)已在黑客论坛流传,部分勒索软件团伙已开始针对金融、电商、政务等核心行业的Struts 2 应用进行扫描探测,若不及时修复,极有可能引发大规模数据泄露、服务器入侵甚至内网沦陷事件。

一、漏洞披露与在野利用态势:比想象中更紧急

该漏洞由欧洲网络安全局(ENISA)下属的零日漏洞监测团队于2026年1月11日首次披露,最初发现于某跨境电商的核心交易系统——攻击者利用该漏洞读取了服务器的数据库配置文件,窃取了数万条用户支付信息。

不同于以往的Struts 2 漏洞,CVE-2025-68493的在野利用门槛极低:攻击者无需掌握复杂的Java反序列化知识,只需发送一段包含恶意外部实体的XML请求,即可触发漏洞。截至1月15日,全球已有超过2000个暴露在公网的Struts 2 应用被检测到存在该漏洞,其中约30%属于关键基础设施相关系统。

更需要重视的是,该漏洞与2021年曝出的S2-061漏洞存在技术同源性——均源于XWork组件的XML解析逻辑缺陷,但本次漏洞的影响范围更广(覆盖了2022年后发布的6.x新版本),且官方修复补丁的推出时间比预期晚了3天,这给了黑客充足的攻击窗口期。

二、漏洞技术根源:XWork组件的致命缺陷,十年老问题再复发

Apache Struts 2 的核心依赖是XWork框架,而本次漏洞的“罪魁祸首”正是XWork组件中的com.opensymphony.xwork2.util.DomHelper.parse方法。

1. 核心问题:XML解析器未禁用外部实体扩展

正常情况下,安全的XML解析应该满足**“三禁用”原则**:禁用DOCTYPE声明、禁用外部通用实体、禁用外部参数实体。但DomHelper.parse方法在默认配置下,完全没有开启这些限制——当应用程序处理来自用户的XML输入(比如接口参数、文件上传内容)时,解析器会主动加载外部实体引用,这就给了攻击者可乘之机。

举个简单的攻击Payload示例:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE root [
<!ENTITY evil SYSTEM "file:///etc/passwd">
]>
<root>&evil;</root>

当服务器解析这段XML时,会自动读取/etc/passwd文件的内容,并将其返回给攻击者——这就是最典型的敏感数据泄露攻击

2. 为什么新版本也中招?

很多开发者以为升级到Struts 2 6.x系列就能高枕无忧,但实际上,官方在6.x版本中仅修复了反序列化相关的漏洞,却忽略了XML解析的基础安全配置。更离谱的是,6.x版本为了提升解析性能,还默认开启了“XML实体缓存”功能,这反而加速了恶意实体的执行效率,让攻击效果更明显。

这本质上是安全左移不到位的问题:Struts 2 开发团队在迭代新版本时,只关注了功能新增和性能优化,却没有对历史遗留的安全缺陷进行全面复盘。

三、远超预期的危害链:从数据泄露到内网沦陷,一步到位

很多人对XXE漏洞的认知还停留在“读取文件”层面,但CVE-2025-68493的危害远不止于此,它能触发一条完整的攻击链

  1. 初始攻击:敏感信息窃取
    攻击者通过漏洞读取服务器的配置文件(如web.xmlmybatis-config.xml),获取数据库账号密码、内网API密钥等核心信息。
  2. 进阶攻击:服务器端请求伪造(SSRF)
    利用外部实体引用,攻击者可以让服务器主动向内网发起请求——比如访问内网的Redis、MySQL服务,甚至扫描内网IP地址段,绘制网络拓扑图。
  3. 终极攻击:服务器沦陷与内网横向移动
    若服务器存在其他配置缺陷(如数据库权限过高、内网无隔离),攻击者可通过窃取的凭证登录数据库,甚至上传恶意Java类文件,实现远程代码执行,最终控制整个服务器,并以此为跳板攻击内网其他系统。

此外,攻击者还能构造复杂的实体引用循环,触发拒绝服务(DoS)攻击——比如让XML解析器无限递归加载外部实体,耗尽服务器的CPU和内存资源,导致应用崩溃。

四、全维度检测方案:手动+自动化+日志溯源,三步确认是否中招

要判断自己的系统是否受影响,不能只看版本号,还要结合实际的业务场景,以下是三套可直接落地的检测方案:

1. 手动版本自查(最快最直接)

  • Java项目:查看pom.xmlbuild.gradle中的struts2-core依赖版本,若版本在2.0.0-2.3.37、2.5.0-2.5.33、6.0.0-6.1.0范围内,立即标记为高危风险
  • 第三方应用:很多CMS、ERP系统会内置Struts 2 框架(比如某些开源电商系统),即使你没手动引入依赖,也需要查看应用的官方公告,确认是否存在漏洞。

2. 自动化工具扫描(适合批量检测)

  • 本地扫描:使用依赖扫描工具(如OWASP Dependency-Check),对项目的依赖包进行全量扫描,该工具会自动匹配CVE编号,给出风险等级。
  • 公网扫描:使用Burp Suite、Nessus等工具,向目标应用发送包含XXE Payload的请求,观察响应是否包含敏感文件内容。
  • 快速脚本验证(Python示例):
import requests

url = "你的目标接口地址"
headers = {"Content-Type": "application/xml"}
payload = """<?xml version="1.0"?>
<!DOCTYPE test [<!ENTITY xxe SYSTEM "file:///etc/passwd">]>
<user><name>&xxe;</name></user>"""

response = requests.post(url, data=payload, headers=headers)
print(response.text)

若响应中包含root:x:0:0:root:/root:/bin/bash等内容,说明漏洞存在。

3. 日志溯源检测(适合排查是否已被攻击)

检查应用服务器的访问日志(如Tomcat的localhost_access_log),重点关注包含以下特征的请求:

  • 请求体中包含DOCTYPEENTITY等关键词;
  • 请求的Content-Type为application/xml,但来自非信任的IP地址;
  • 频繁尝试访问/etc/passwd/usr/local/tomcat/conf/server.xml等敏感文件。

五、分级修复策略:官方升级+临时加固+应急回滚,72小时内必须完成

修复该漏洞的核心原则是**“能升级则升级,不能升级则加固,加固无效则隔离”**,以下是分优先级的修复方案:

1. 最高优先级:升级到官方修复版本(彻底解决)

官方已发布修复版本,强烈建议所有用户立即升级

  • 2.5.x系列:升级至2.5.34
  • 6.x系列:升级至6.1.1(最新稳定版)

Maven依赖更新示例

<dependency>
    <groupId>org.apache.struts</groupId>
    <artifactId>struts2-core</artifactId>
    <version>6.1.1</version>
    <scope>compile</scope>
</dependency>

升级注意事项

  • 升级前务必在测试环境验证兼容性——6.1.1版本对部分老旧API进行了废弃,可能导致业务代码报错;
  • 升级后需要重新进行功能测试和安全测试,确认漏洞已修复且业务不受影响。

2. 临时缓解措施:无法升级时的“保命”方案(仅适合应急)

若因业务原因无法立即升级,可通过以下两种方式加固,但注意:这只是临时方案,不能替代官方补丁

(1)修改XML解析器配置,禁用外部实体

在项目中自定义DomHelper的解析逻辑,强制开启安全配置:

import org.xml.sax.InputSource;
import org.w3c.dom.Document;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;

public class SafeXmlParser {
    public static Document parse(InputSource inputSource) throws Exception {
        DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
        // 核心安全配置:三禁用
        dbf.setFeature("http://apache.org/xml/features/disallow-doctype-decl", true);
        dbf.setFeature("http://xml.org/sax/features/external-general-entities", false);
        dbf.setFeature("http://xml.org/sax/features/external-parameter-entities", false);
        // 禁止加载外部DTD
        dbf.setFeature("http://apache.org/xml/features/nonvalidating/load-external-dtd", false);
        DocumentBuilder db = dbf.newDocumentBuilder();
        return db.parse(inputSource);
    }
}

然后在业务代码中,用这个自定义的SafeXmlParser替代默认的DomHelper.parse方法。

(2)配置WAF拦截攻击特征

在Web应用防火墙(WAF)中添加规则,拦截包含以下内容的请求:

  • <!DOCTYPE<!ENTITYSYSTEM等XXE关键词;
  • 尝试访问敏感文件路径的XML请求;
  • 来自黑名单IP的XML类型请求。

3. 应急回滚方案:升级出问题时的兜底策略

若升级后出现业务异常,可立即执行以下回滚步骤:

  1. 回退到原版本的Struts 2 依赖;
  2. 启用上述临时加固措施;
  3. 限制目标应用的公网访问权限,仅允许内网IP访问;
  4. 联系官方技术支持,获取针对性的修复建议。

六、前瞻性防御:从单点修复到供应链安全体系构建,避免下次踩坑

本次漏洞再次给所有开发者敲响警钟:框架漏洞的危害远大于业务代码漏洞,要从根本上避免类似问题,需要构建一套完整的供应链安全防御体系。

1. 安全左移:把依赖安全纳入开发流程

  • 在项目立项阶段,就对使用的开源框架进行安全评估,优先选择维护活跃、安全补丁及时的版本;
  • 在CI/CD流水线中集成依赖扫描工具(如OWASP Dependency-Check),每次代码提交时自动检测高危漏洞;
  • 定期对项目的依赖包进行“瘦身”,移除不必要的依赖,减少攻击面。

2. 规范XML处理:养成安全编码习惯

对于所有处理XML输入的场景,必须遵循以下安全原则:

  • 禁用DOCTYPE声明和外部实体;
  • 使用安全的解析器(如上文的SafeXmlParser),避免使用默认配置;
  • 对用户输入的XML进行严格校验,只允许白名单内的标签和属性。

3. 建立漏洞响应机制:72小时应急闭环

  • 组建专门的漏洞响应团队,明确漏洞发现、评估、修复、验证的流程;
  • 与安全厂商和开源社区保持同步,及时获取漏洞预警信息;
  • 定期进行应急演练,模拟漏洞攻击场景,检验修复方案的有效性。

总结

CVE-2025-68493绝非普通的XXE漏洞,它是一场针对全球Struts 2 应用的大规模攻击预警。在PoC已公开、在野利用已出现的情况下,72小时是修复的黄金窗口期——任何拖延都可能导致数据泄露、服务器沦陷等不可挽回的损失。

对于开发者而言,本次漏洞不仅是一次应急修复任务,更是一次反思:开源框架不是“免死金牌”,只有建立完善的供应链安全体系,才能真正抵御未知的攻击。

Logo

DAMO开发者矩阵,由阿里巴巴达摩院和中国互联网协会联合发起,致力于探讨最前沿的技术趋势与应用成果,搭建高质量的交流与分享平台,推动技术创新与产业应用链接,围绕“人工智能与新型计算”构建开放共享的开发者生态。

更多推荐