Преглед изворни кода

Fixed #34858 -- Corrected resolving output_field for PositiveIntegerField.

Regression in 40b8a6174f001a310aa33f7880db0efeeb04d4c4.
toan пре 1 година
родитељ
комит
4de31ec680
3 измењених фајлова са 38 додато и 0 уклоњено
  1. 1 0
      AUTHORS
  2. 19 0
      django/db/models/expressions.py
  3. 18 0
      tests/expressions/tests.py

+ 1 - 0
AUTHORS

@@ -978,6 +978,7 @@ answer newbie questions, and generally made Django that much better:
     Tim Heap <tim@timheap.me>
     Tim McCurrach <tim.mccurrach@gmail.com>
     Tim Saylor <tim.saylor@gmail.com>
+    Toan Vuong <me@toanvuong.io>
     Tobias Kunze <rixx@cutebit.de>
     Tobias McNulty <https://www.caktusgroup.com/blog/>
     tobias@neuyork.de

+ 19 - 0
django/db/models/expressions.py

@@ -512,6 +512,25 @@ class Expression(BaseExpression, Combinable):
 
 _connector_combinations = [
     # Numeric operations - operands of same type.
+    # PositiveIntegerField should take precedence over IntegerField (except
+    # subtraction).
+    {
+        connector: [
+            (
+                fields.PositiveIntegerField,
+                fields.PositiveIntegerField,
+                fields.PositiveIntegerField,
+            ),
+        ]
+        for connector in (
+            Combinable.ADD,
+            Combinable.MUL,
+            Combinable.DIV,
+            Combinable.MOD,
+            Combinable.POW,
+        )
+    },
+    # Other numeric operands.
     {
         connector: [
             (fields.IntegerField, fields.IntegerField, fields.IntegerField),

+ 18 - 0
tests/expressions/tests.py

@@ -34,6 +34,7 @@ from django.db.models import (
     Model,
     OrderBy,
     OuterRef,
+    PositiveIntegerField,
     Q,
     StdDev,
     Subquery,
@@ -2455,6 +2456,23 @@ class CombinableTests(SimpleTestCase):
 
 
 class CombinedExpressionTests(SimpleTestCase):
+    def test_resolve_output_field_positive_integer(self):
+        connectors = [
+            Combinable.ADD,
+            Combinable.MUL,
+            Combinable.DIV,
+            Combinable.MOD,
+            Combinable.POW,
+        ]
+        for connector in connectors:
+            with self.subTest(connector=connector):
+                expr = CombinedExpression(
+                    Expression(PositiveIntegerField()),
+                    connector,
+                    Expression(PositiveIntegerField()),
+                )
+                self.assertIsInstance(expr.output_field, PositiveIntegerField)
+
     def test_resolve_output_field_number(self):
         tests = [
             (IntegerField, AutoField, IntegerField),