CVE-2026-58501 Overview
CVE-2026-58501 affects Zeep, a widely used Python SOAP client library. The vulnerability exists in versions 4.0.0 through 4.3.2, where the Settings.forbid_external option is defined but never enforced when parsing Web Services Description Language (WSDL) or XML Schema Definition (XSD) documents. Attackers who supply crafted WSDL or XSD content can trigger transitive xsd:import, xsd:include, wsdl:import, and lxml entity or Document Type Definition (DTD) references. These references fetch arbitrary attacker-chosen HTTP or HTTPS URLs, resulting in Server-Side Request Forgery [CWE-918]. Version 4.3.3 remediates the issue by wiring the setting into the resolution logic.
Critical Impact
Applications loading WSDL or XSD documents from untrusted sources can be coerced into issuing outbound HTTP/HTTPS requests to attacker-selected internal or external endpoints.
Affected Products
- Zeep versions 4.0.0 through 4.3.2 (Python SOAP client)
- Applications embedding Zeep to parse third-party WSDL or XSD documents
- Services accepting user-supplied SOAP endpoint URLs for WSDL discovery
Discovery Timeline
- 2026-07-08 - CVE-2026-58501 published to the National Vulnerability Database (NVD)
- 2026-07-09 - Last updated in NVD database
Technical Details for CVE-2026-58501
Vulnerability Analysis
Zeep is a Python SOAP client that resolves WSDL and XSD schema graphs at runtime. The Settings.forbid_external flag was introduced to block transitive external resource loads. When Zeep migrated away from defusedxml in the 4.0 release, this control was left defined but disconnected from the resolver code paths. As a result, parsing any WSDL or XSD document caused Zeep to follow every transitive import, include, and lxml entity reference without policy checks. An attacker who influences the schema graph can force the client to issue HTTP or HTTPS requests to arbitrary hosts. This yields Server-Side Request Forgery (SSRF) against internal metadata services, cloud APIs, and unauthenticated internal endpoints reachable from the Zeep process.
Root Cause
The root cause is a missing enforcement point. The forbid_external setting existed in the configuration object but the WSDL, XSD, and lxml entity resolution routines did not consult it. External URLs referenced by xsd:import, xsd:include, wsdl:import, or DTD entity declarations were fetched unconditionally.
Attack Vector
An attacker supplies a malicious WSDL or XSD document, or influences a legitimate one to include a transitive import pointing at an attacker-controlled host or an internal target. When the vulnerable Zeep instance parses the document, it issues the outbound request. The attacker can pivot to internal services, exfiltrate schema fetch metadata, or probe network topology.
Unreleased
----------
- Wire up the ``forbid_external`` setting (previously defined but unused
since the move off ``defusedxml`` in 4.0). When enabled it refuses to
transitively fetch ``http``/``https`` resources via ``xsd:import``,
``xsd:include``, ``wsdl:import`` or lxml entity resolution, raising
``zeep.exceptions.ExternalReferenceForbidden``. The user-supplied
entry-point WSDL/schema URL is still loaded. The default remains
``False`` to preserve existing behaviour; enable when loading WSDLs from
untrusted sources to mitigate SSRF via attacker-controlled import
targets.
4.3.2 (2025-09-15)
-----------------
- Support newer versions of httpx (#1447)
Source: GitHub Commit 83eb07b
The fix also introduces a new exception class raised when a forbidden reference is encountered:
def __str__(self):
tpl = "EntitiesForbidden(name='{}', content={!r})"
return tpl.format(self.name, self.content)
class ExternalReferenceForbidden(Error):
def __init__(self, url):
super().__init__("External reference to %r is forbidden" % (url,))
self.url = url
def __str__(self):
return "ExternalReferenceForbidden(url=%r)" % (self.url,)
Source: GitHub Commit 83eb07b
Detection Methods for CVE-2026-58501
Indicators of Compromise
- Outbound HTTP/HTTPS connections from Python application hosts to unexpected external domains during WSDL or XSD parsing operations.
- Requests from application servers to cloud metadata endpoints such as 169.254.169.254 originating from Zeep-hosting processes.
- Application logs showing WSDL loads referencing xsd:import, xsd:include, or wsdl:import with attacker-controlled URLs.
- Unexpected DTD or entity resolution requests traced to lxml activity within the Zeep process.
Detection Strategies
- Inventory Python environments with pip show zeep or software composition analysis tools to identify installations in the 4.0.0 through 4.3.2 range.
- Instrument the Zeep process with an HTTP client hook or egress proxy to log every URL fetched during WSDL and XSD parsing.
- Correlate outbound traffic from application tiers with SOAP client invocations to identify anomalous destinations.
- Alert on any occurrence of zeep.exceptions.ExternalReferenceForbidden after patching, indicating attempted exploitation.
Monitoring Recommendations
- Route Zeep egress through an explicit allowlist proxy and monitor blocked requests.
- Baseline expected schema fetch destinations for each service consuming Zeep and alert on deviations.
- Track EPSS trend data (currently 0.252%) alongside your own exposure to prioritize monitoring.
How to Mitigate CVE-2026-58501
Immediate Actions Required
- Upgrade Zeep to version 4.3.3 or later using pip install --upgrade zeep.
- Set Settings(forbid_external=True) in every Zeep client that loads WSDL or XSD documents from untrusted or partially trusted sources.
- Audit application code paths that accept user-supplied WSDL URLs and restrict them to a vetted allowlist.
- Segment application networks so Zeep processes cannot reach internal metadata services or administrative endpoints.
Patch Information
The fix ships in Zeep 4.3.3, released on GitHub. Review the GitHub Release 4.3.3 and the GitHub Security Advisory GHSA-4cc2-g9w2-fhf6 for full details. After upgrading, enable forbid_external=True because the default remains False to preserve backward compatibility.
Workarounds
- Restrict egress from application servers to a strict allowlist of required SOAP service hosts.
- Preprocess incoming WSDL and XSD documents to strip xsd:import, xsd:include, wsdl:import, and DTD declarations before passing them to Zeep.
- Run Zeep parsing in a sandboxed process without network access to internal resources when full patching is not yet possible.
# Upgrade Zeep and enable the SSRF mitigation
pip install --upgrade 'zeep>=4.3.3'
# Example client instantiation with forbid_external enforced
python - <<'PY'
from zeep import Client, Settings
settings = Settings(forbid_external=True)
client = Client('https://trusted.example.com/service?wsdl', settings=settings)
print(client.service)
PY
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

