summaryrefslogtreecommitdiff
path: root/tests/postgres_tests/test_constraints.py
diff options
context:
space:
mode:
authorHannes Ljungberg <hannes.ljungberg@gmail.com>2021-11-03 22:21:50 +0100
committerMariusz Felisiak <felisiak.mariusz@gmail.com>2021-12-24 11:39:00 +0100
commit0e656c02fe945389246f0c08f51c6db4a0849bd2 (patch)
treee61981acccc088365ca767c8a2b61883313f0231 /tests/postgres_tests/test_constraints.py
parenta0d43a7a6e1c30c08f853ba64e17e148fb6921e6 (diff)
Fixed #33342 -- Added support for using OpClass() in exclusion constraints.
Diffstat (limited to 'tests/postgres_tests/test_constraints.py')
-rw-r--r--tests/postgres_tests/test_constraints.py47
1 files changed, 47 insertions, 0 deletions
diff --git a/tests/postgres_tests/test_constraints.py b/tests/postgres_tests/test_constraints.py
index bf0b57488a..f67210097f 100644
--- a/tests/postgres_tests/test_constraints.py
+++ b/tests/postgres_tests/test_constraints.py
@@ -198,6 +198,7 @@ class SchemaTests(PostgreSQLTestCase):
Scene.objects.create(scene='ScEnE 10', setting="Sir Bedemir's Castle")
+@modify_settings(INSTALLED_APPS={'append': 'django.contrib.postgres'})
class ExclusionConstraintTests(PostgreSQLTestCase):
def get_constraints(self, table):
"""Get the constraints on the table using a new cursor."""
@@ -604,6 +605,24 @@ class ExclusionConstraintTests(PostgreSQLTestCase):
)
self._test_range_overlaps(constraint)
+ def test_range_overlaps_custom_opclass_expression(self):
+ class TsTzRange(Func):
+ function = 'TSTZRANGE'
+ output_field = DateTimeRangeField()
+
+ constraint = ExclusionConstraint(
+ name='exclude_overlapping_reservations_custom_opclass',
+ expressions=[
+ (
+ OpClass(TsTzRange('start', 'end', RangeBoundary()), 'range_ops'),
+ RangeOperators.OVERLAPS,
+ ),
+ (OpClass('room', 'gist_int4_ops'), RangeOperators.EQUAL),
+ ],
+ condition=Q(cancelled=False),
+ )
+ self._test_range_overlaps(constraint)
+
def test_range_overlaps(self):
constraint = ExclusionConstraint(
name='exclude_overlapping_reservations',
@@ -914,6 +933,34 @@ class ExclusionConstraintTests(PostgreSQLTestCase):
editor.add_constraint(RangesModel, constraint)
self.assertIn(constraint_name, self.get_constraints(RangesModel._meta.db_table))
+ def test_opclass_expression(self):
+ constraint_name = 'ints_adjacent_opclass_expression'
+ self.assertNotIn(
+ constraint_name,
+ self.get_constraints(RangesModel._meta.db_table),
+ )
+ constraint = ExclusionConstraint(
+ name=constraint_name,
+ expressions=[(OpClass('ints', 'range_ops'), RangeOperators.ADJACENT_TO)],
+ )
+ with connection.schema_editor() as editor:
+ editor.add_constraint(RangesModel, constraint)
+ constraints = self.get_constraints(RangesModel._meta.db_table)
+ self.assertIn(constraint_name, constraints)
+ with editor.connection.cursor() as cursor:
+ cursor.execute(SchemaTests.get_opclass_query, [constraint_name])
+ self.assertEqual(
+ cursor.fetchall(),
+ [('range_ops', constraint_name)],
+ )
+ # Drop the constraint.
+ with connection.schema_editor() as editor:
+ editor.remove_constraint(RangesModel, constraint)
+ self.assertNotIn(
+ constraint_name,
+ self.get_constraints(RangesModel._meta.db_table),
+ )
+
def test_range_equal_cast(self):
constraint_name = 'exclusion_equal_room_cast'
self.assertNotIn(constraint_name, self.get_constraints(Room._meta.db_table))