hkc-8010 commented on code in PR #66696:
URL: https://github.com/apache/airflow/pull/66696#discussion_r3218184315


##########
airflow-core/src/airflow/api_fastapi/common/parameters.py:
##########
@@ -908,17 +937,15 @@ def depends_datetime(
         upper_bound_lt: datetime | None = Query(alias=f"{filter_name}_lt", 
default=None),
     ) -> RangeFilter:
         attr = getattr(model, attribute_name or filter_name)
-        if filter_name in ("start_date", "end_date"):
-            attr = func.coalesce(attr, func.now())
-        return RangeFilter(
-            Range(
-                lower_bound_gte=lower_bound_gte,
-                lower_bound_gt=lower_bound_gt,
-                upper_bound_lte=upper_bound_lte,
-                upper_bound_lt=upper_bound_lt,
-            ),
-            attr,
+        range_val = Range(
+            lower_bound_gte=lower_bound_gte,
+            lower_bound_gt=lower_bound_gt,
+            upper_bound_lte=upper_bound_lte,
+            upper_bound_lt=upper_bound_lt,
         )
+        if filter_name in ("start_date", "end_date"):

Review Comment:
   Good catch, fixed. The check now uses `attribute_name or filter_name` so 
callers like `datetime_range_filter_factory("dag_run_end_date", DagRun, 
"end_date")` in `dags.py` correctly return `NullableDatetimeRangeFilter`. Added 
a test to cover the alias case.



##########
airflow-core/src/airflow/api_fastapi/common/parameters.py:
##########
@@ -898,6 +898,35 @@ def is_active(self) -> bool:
         )
 
 
+class NullableDatetimeRangeFilter(RangeFilter):
+    """
+    RangeFilter for nullable datetime columns that preserves NULL-as-now 
semantics.
+
+    Uses explicit OR conditions instead of COALESCE(column, now()) so 
PostgreSQL
+    can use btree indexes on each branch via BitmapOr plans rather than forcing
+    a full table scan.
+    """
+
+    def to_orm(self, select: Select) -> Select:
+        if self.value is None:
+            return select

Review Comment:
   Deliberate — it follows the same pattern as the parent `RangeFilter` class. 
`value is None` here means the filter block was not requested at all (i.e., no 
bounds were passed in), not "filter WHERE attribute IS NULL". Since all bounds 
are typed `datetime | None` at the HTTP layer, the only way `value` is `None` 
is if the caller constructs the filter object without a `Range`, which doesn't 
happen via the factory. The IS NULL coverage for running tasks is already 
embedded in the OR branches below.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to