[5.1.x] Fixed CVE-2025-13372 -- Protected FilteredRelation against SQL injection in column aliases on PostgreSQL.

Follow-up to CVE-2025-57833.

Thanks Stackered for the report, and Simon Charette and Mariusz Felisiak
for the reviews.

Backport of 5b90ca1e75 from main.
This commit is contained in:
Jacob Walls
2025-11-17 17:09:54 -05:00
committed by Natalia
parent e419ad896d
commit 9c6a5bde24
5 changed files with 53 additions and 0 deletions

View File

@@ -0,0 +1,24 @@
from django.db.models.sql.compiler import ( # isort:skip
SQLAggregateCompiler,
SQLCompiler as BaseSQLCompiler,
SQLDeleteCompiler,
SQLInsertCompiler,
SQLUpdateCompiler,
)
__all__ = [
"SQLAggregateCompiler",
"SQLCompiler",
"SQLDeleteCompiler",
"SQLInsertCompiler",
"SQLUpdateCompiler",
]
class SQLCompiler(BaseSQLCompiler):
def quote_name_unless_alias(self, name):
if "$" in name:
raise ValueError(
"Dollar signs are not permitted in column aliases on PostgreSQL."
)
return super().quote_name_unless_alias(name)

View File

@@ -24,6 +24,7 @@ def get_json_dumps(encoder):
class DatabaseOperations(BaseDatabaseOperations):
compiler_module = "django.db.backends.postgresql.compiler"
cast_char_field_without_max_length = "varchar"
explain_prefix = "EXPLAIN"
explain_options = frozenset(

View File

@@ -7,6 +7,14 @@ Django 4.2.27 release notes
Django 4.2.27 fixes one security issue with severity "high", one security issue
with severity "moderate", and one bug in 4.2.26.
CVE-2025-13372: Potential SQL injection in ``FilteredRelation`` column aliases on PostgreSQL
============================================================================================
:class:`.FilteredRelation` was subject to SQL injection in column aliases,
using a suitably crafted dictionary, with dictionary expansion, as the
``**kwargs`` passed to :meth:`.QuerySet.annotate` or :meth:`.QuerySet.alias` on
PostgreSQL.
Bugfixes
========

View File

@@ -7,6 +7,14 @@ Django 5.1.15 release notes
Django 5.1.15 fixes one security issue with severity "high", one security issue
with severity "moderate", and one bug in 5.1.14.
CVE-2025-13372: Potential SQL injection in ``FilteredRelation`` column aliases on PostgreSQL
============================================================================================
:class:`.FilteredRelation` was subject to SQL injection in column aliases,
using a suitably crafted dictionary, with dictionary expansion, as the
``**kwargs`` passed to :meth:`.QuerySet.annotate` or :meth:`.QuerySet.alias` on
PostgreSQL.
Bugfixes
========

View File

@@ -2,6 +2,7 @@ import datetime
from decimal import Decimal
from django.core.exceptions import FieldDoesNotExist, FieldError
from django.db import connection
from django.db.models import (
BooleanField,
Case,
@@ -1454,3 +1455,14 @@ class AliasTests(TestCase):
)
with self.assertRaisesMessage(ValueError, msg):
Book.objects.alias(**{crafted_alias: FilteredRelation("authors")})
def test_alias_filtered_relation_sql_injection_dollar_sign(self):
qs = Book.objects.alias(
**{"crafted_alia$": FilteredRelation("authors")}
).values("name", "crafted_alia$")
if connection.vendor == "postgresql":
msg = "Dollar signs are not permitted in column aliases on PostgreSQL."
with self.assertRaisesMessage(ValueError, msg):
list(qs)
else:
self.assertEqual(qs.first()["name"], self.b1.name)