GeoServer zero-day (GHSA-mqjf-5f49-2fjh): SQL injection in jsonArrayContains leads to RCE
In brief
The most concerning aspect of this case is that the vulnerability is a regression of CVE-2023-25158, a similar flaw patched in February 2023. The same class of bug surfacing three years later in the same project suggests a systemic problem in how CQL code is translated to SQL for PostGIS. This article breaks down the vulnerability, the exploitation chain, and the defensive measures any organization running GeoServer in production must apply immediately.
What GeoServer is and why it matters
GeoServer is an open-source Java platform that implements Open Geospatial Consortium (OGC) standards for serving geospatial data through protocols like WMS (Web Map Service), WFS (Web Feature Service), and WCS (Web Coverage Service). It is the most widely used map server in the open-source world and is present in infrastructure ranging from government agencies to logistics companies to environmental management organizations and cartographic service providers.
For DevSecOps teams, GeoServer is a component that often falls off the radar because:
- It is deployed by a GIS or data engineering team, not the security team. - Its CVEs are published in geospatial databases, not always in NVD. - Its attack surface includes WFS/WMS protocols that many firewalls do not inspect deeply. - GeoServer instances are often exposed in production to serve maps to external users.
That combination of low visibility and high exposure makes GeoServer a recurring target. CVE-2024-36401 (CVSS 9.8) was exploited in 2025 to turn compromised servers into DDoS botnets, cryptocurrency miners, and residential proxies. The 2026 vulnerability follows the same pattern: broad exposure, rapid exploitation, significant operational impact.
The vulnerability: jsonArrayContains without escaping
The technical detail of the bug was published by Hadrian in their blog "Here be dragons: GeoServer pre-auth SQL injection to RCE." The summary of the problem:
> "An attacker-controlled value is interpolated directly into a PostgreSQL jsonb_path_exists() expression without escaping."
The technical path is as follows. When GeoServer receives a WFS or WMS request that includes a CQL (Common Query Language) or CQL2 filter, the system translates that filter to SQL for execution against the PostGIS datastore. The specific function involved is `jsonArrayContains`, which PostGIS exposes as an extension on the PostgreSQL engine.
The vulnerable GeoServer implementation in the `org.geotools:gt-jdbc-postgis` package takes the attacker-controlled CQL filter value and inserts it directly into a `jsonb_path_exists()` call without escaping. That PostgreSQL function evaluates JSON path expressions against JSONB documents, and allows injecting arbitrary logic if the input is not validated.
The affected Maven package:
- `org.geotools:gt-jdbc-postgis` version 35.0 → fixed in 35.1 - `org.geotools:gt-jdbc-postgis` version 34.0 or higher → fixed in 34.5 - `org.geotools:gt-jdbc-postgis` version 33.1 or higher → fixed in 33.6
The vulnerability requires PostGIS 12 or higher with a String or JSON field. Without PostGIS 12+, the `jsonArrayContains` function is not available, so the vulnerability is not exploitable.
From SQL injection to RCE: the full chain
SQL injection on its own is serious, but the real risk is the conversion to remote code execution. Hadrian published the exact path.
WFS 1.0 in GeoServer allows, under certain configurations, executing a second SQL statement at the top level of the query. Combined with SQL injection in `jsonArrayContains`, that allows:
1. Injecting an arbitrary SQL statement that PostGIS executes with the privileges of the connection user. 2. Leveraging PostgreSQL functions that allow writing files to the system (if privileges permit). 3. Using PostGIS techniques to invoke functionality that ends up executing code on the GeoServer host.
The specific path to RCE depends on server configuration, but in most cases involves:
- PostGIS connection using the `postgres` user or equivalent superuser. - Use of PostgreSQL `lo_export`, `COPY ... TO`, or equivalent functions to write files to disk. - Loading the written file as a PostgreSQL shared extension that executes arbitrary code.
If the PostGIS user does not have elevated privileges, the chain stops at SQL injection with limited impact. But default configuration in many installations uses a user with sufficient privileges to reach RCE.
The CVE-2023-25158 regression
The most alarming aspect of the case is that this vulnerability is a regression of CVE-2023-25158, patched in February 2023. The GeoTools maintainers' description says it explicitly:
> "The maintainers also noted that the vulnerability is a regression of CVE-2023-25158 (CVSS score: 9.8), another critical SQL injection vulnerability that was addressed alongside CVE-2023-25157 in February 2023."
A regression of severity 9.8 three years after the original patch indicates a systemic problem:
- Regression tests did not cover this specific case. - Code refactoring in intermediate versions likely lost the validation. - Fuzzing coverage against malformed CQL inputs is insufficient.
For GeoServer consumers, this is a concerning pattern. It is not the first time the platform has had a critical SQL injection vulnerability; it is at least the second. The reasonable question for a DevSecOps team is: what else are we not seeing in this code?
Disclosure and exploitation timeline
The timeline shows a reasonably fast reaction from maintainers but a significant exposure window:
- **August 12, 2026, 10:46 UTC**: @q1uf3ng publishes the initial advisory on X. - **First hours**: watchTowr detects the first exploitation attempts against systems exposed on the internet. - **First day**: hundreds of confirmed attempts originating from a small pool of IPs. - **August 14, 2026**: GeoServer ships patches in versions 3.0.1, 2.28.5, and 2.27.6. - **GHSA-mqjf-5f49-2fjh assignment**: GitHub advisory published with CVSS 9.8.
The window between public disclosure and patch was 48 hours. For a vulnerability of this severity, 48 hours is enough for multiple actors to scan the internet, identify vulnerable targets, and successfully exploit them.
Observed attacker behavior
Jake Knott, principal security researcher at watchTowr, confirmed the exploitation pattern:
> "Currently, we're seeing attackers probe to identify vulnerable systems across the internet, triggering errors and not proceeding further. However, this is unlikely to remain the case for long: GeoServer has a track record of being targeted and exploited at scale, with multiple vulnerabilities listed in CISA's Known Exploited Vulnerabilities catalog. More importantly, under certain configurations, this latest vulnerability could ultimately lead to remote code execution."
Attackers are in reconnaissance phase, not mass exploitation yet. That means the window to patch before mass exploitation is open, but closing. The time to patch is now.
Immediate mitigation
**1. Apply the patch.** If you run GeoServer, upgrade to one of the patched versions:
- GeoServer 3.0.1 or higher - GeoServer 2.28.5 or higher - GeoServer 2.27.6 or higher
Verify your current version:
```bash # Verify GeoServer version # In the web console: About > Build Information # Or from the server command line: unzip -p /opt/geoserver/webapps/geoserver/WEB-INF/lib/gt-jdbc-postgis-*.jar META-INF/MANIFEST.MF | grep Implementation-Version ```
**2. Identify exposed instances.** Scan your infrastructure with Shodan or Censys to detect GeoServer instances with port 8080 (or configured) reachable from the internet. Any exposed instance without business need is a candidate for immediate isolation.
**3. Configure authentication on WFS endpoints.** Although GeoServer allows anonymous access by default for many operations, WFS endpoints that execute CQL queries should require authentication when possible. Verify configuration under `Security > Data > Security settings`.
**4. WAF with specific rules.** Deploy WAF rules to block WFS requests with suspicious CQL patterns. Functions that should not appear in external queries (`jsonArrayContains`, `ST_AsText`, `lo_export`, etc.) should be on the deny list.
```nginx # Example nginx rule for basic WAF location /geoserver/ows { if ($args ~ "jsonArrayContains") { return 403; } if ($args ~ "lo_export|copy.*to|pg_read_file") { return 403; } # ... rest of proxy configuration } ```
**5. PostGIS user audit.** Verify which user is used to connect GeoServer to PostGIS. If it is a superuser, switch to a least-privilege user. That drastically reduces the scope of any SQL injection.
```sql -- Create dedicated user with minimum privileges CREATE USER geoserver_user WITH PASSWORD 'secure_password'; GRANT SELECT, INSERT, UPDATE, DELETE ON ALL TABLES IN SCHEMA public TO geoserver_user; GRANT USAGE ON ALL SEQUENCES IN SCHEMA public TO geoserver_user; ```
**6. Network segmentation.** GeoServer instances should not be directly reachable from the internet unless absolutely necessary. A reverse proxy with authentication and rate limiting is preferable to direct exposure.
**7. CQL query telemetry.** Activate detailed logging of executed CQL queries and centralize in SIEM. Queries with unexpected functions or escape characters should generate an alert.
Regulatory implications
For organizations subject to NIS2, a compromised GeoServer instance can have serious implications. If the server stores or serves geospatial data that includes critical infrastructure (power grids, military installations, sensitive biodiversity data), the compromise may escalate to a reportable incident.
Under GDPR, if data served by GeoServer includes personal information (facility addresses, geolocated employee data), the compromise is a personal data breach with notification obligations within 72 hours.
For the public sector, compromised GeoServer instances serving official cartographic data can affect the integrity of public information. In some cases this triggers specific obligations to communicate to citizens.
Comparison with CVE-2024-36401
CVE-2024-36401 was a property evaluation vulnerability in GeoTools that also allowed RCE. It was exploited in 2025 to:
- Build DDoS botnets using the network capacity of compromised servers. - Install cryptocurrency miners on map processing infrastructure. - Turn servers into residential proxies to anonymize other malicious activities.
The pattern repeats: GeoServer as a priority target for commodity campaigns because its instances are typically:
- Exposed on the internet. - Maintained by teams with low security priority. - On infrastructure with significant compute capacity (useful for mining). - With data that can be exfiltrated and monetized.
The 2026 vulnerability follows the same profile. Organizations that did not patch GeoServer after CVE-2024-36401 should be on red alert.
Response plan for confirmed compromises
If you detect exploitation attempts or confirmed compromise on a GeoServer instance:
1. **Isolate the instance immediately.** Disconnect from the corporate network to prevent lateral movement. 2. **Capture forensic image.** Snapshot the system before any change for later analysis. 3. **Audit PostGIS logs.** Look for queries with `jsonArrayContains` or injection patterns. 4. **Review system files.** Look for new files in `/tmp`, `/var/tmp`, and PostgreSQL extension directories. 5. **Rotate credentials.** Change all PostGIS credentials, TLS certificates, and any stored secrets. 6. **Reinstall from scratch.** After capturing evidence, reinstall the instance from verified clean backups. 7. **Notify legal and compliance teams.** If personal data is involved, activate the authority notification protocol.
Immediate checklist
- [ ] Current GeoServer version verified against GHSA-mqjf-5f49-2fjh advisory. - [ ] Upgrade plan to 3.0.1, 2.28.5, or 2.27.6 by line. - [ ] External exposure scan completed. - [ ] WAF rules specific to OWS endpoints deployed. - [ ] PostGIS user verified with minimum privileges. - [ ] CQL query telemetry centralized in SIEM. - [ ] Incident response plan specific to GeoServer. - [ ] Backups verified and tested for clean restoration.
Call to action
If your organization runs GeoServer in production, the remediation window is hours, not days. Patch now, deploy WAF with rules for OWS endpoints, and verify the rest of your geospatial infrastructure is not in the same situation.
Every week we publish technical analyses of critical vulnerabilities with actionable context for DevSecOps teams. Follow X-Ops on X, Instagram, LinkedIn, and YouTube, and Hacker Dreams on X, Instagram, and LinkedIn, so you don't miss the next analysis.
---
*Sources: GHSA-mqjf-5f49-2fjh advisory on GitHub (github.com/geotools/geotools/security/advisories/GHSA-mqjf-5f49-2fjh), Hadrian technical analysis (hadrian.io/blog/here-be-dragons-geoserver-pre-auth-sql-injection-to-rce), watchTowr report, The Hacker News original report, initial advisory by researcher @q1uf3ng on X.*