CVE-2026-26198
📋 TL;DR
CVE-2026-26198 is a critical SQL injection vulnerability in Ormar ORM for Python that allows attackers to execute arbitrary SQL queries. Unauthorized users can exploit this to read entire database contents, including tables unrelated to the queried model. All applications using Ormar versions 0.9.9 through 0.22.0 with aggregate queries are affected.
💻 Affected Systems
- Ormar ORM for Python
📦 What is this software?
Ormar by Collerek
⚠️ Risk & Real-World Impact
Worst Case
Complete database compromise including data exfiltration, data modification, and potential privilege escalation through SQL injection.
Likely Case
Unauthorized data access and exfiltration from any database table accessible to the application's database user.
If Mitigated
Limited impact with proper input validation and database user privilege restrictions.
🎯 Exploit Status
The vulnerability is straightforward to exploit as it requires only passing a malicious string to min() or max() methods. No authentication bypass needed if the vulnerable endpoint is exposed.
🛠️ Fix & Mitigation
✅ Official Fix
Patch Version: 0.23.0
Vendor Advisory: https://github.com/collerek/ormar/security/advisories/GHSA-xxh2-68g9-8jqr
Restart Required: No
Instructions:
1. Update Ormar to version 0.23.0 or later using pip: pip install ormar>=0.23.0
2. Verify no breaking changes in your application
3. Test aggregate queries with min() and max() methods
4. Deploy updated application
🔧 Temporary Workarounds
Input Validation Wrapper
allImplement custom validation for column parameters before passing to min() and max() methods
# Python code to validate column names
import re
def safe_column_name(column):
if not re.match(r'^[a-zA-Z_][a-zA-Z0-9_]*$', column):
raise ValueError('Invalid column name')
return column
Database User Privilege Restriction
allLimit database user permissions to read-only access on specific tables
-- SQL example for PostgreSQL
REVOKE ALL PRIVILEGES ON ALL TABLES IN SCHEMA public FROM app_user;
GRANT SELECT ON specific_table TO app_user;
🧯 If You Can't Patch
- Disable or restrict endpoints using min() and max() aggregate methods with user input
- Implement web application firewall (WAF) rules to detect and block SQL injection patterns in query parameters
🔍 How to Verify
Check if Vulnerable:
Check if your code uses ormar.QuerySet.min() or ormar.QuerySet.max() with user-supplied parameters. Review requirements.txt or pyproject.toml for ormar version.
Check Version:
python -c "import ormar; print(ormar.__version__)"
Verify Fix Applied:
After updating to 0.23.0+, test that malicious column names (e.g., "(SELECT * FROM users)") are rejected or properly escaped.
📡 Detection & Monitoring
Log Indicators:
- Unusual SQL queries in database logs with subqueries in aggregate functions
- Multiple failed login attempts followed by aggregate query attempts
- Database queries accessing tables not referenced in application code
Network Indicators:
- Unusually large database response sizes from aggregate query endpoints
- Rapid sequential requests to aggregate endpoints with varying parameters
SIEM Query:
source="application.logs" AND ("ormar.QuerySet.min" OR "ormar.QuerySet.max") AND ("SELECT" OR "UNION" OR "FROM" NOT IN expected_columns)