1- from collections .abc import Callable
1+ from collections .abc import Callable , Iterable
22from typing import Any
33
44from django import forms
55from django .db .models import Q , QuerySet
66from django .forms import Field
7+ from django_stubs_ext import StrOrPromise
78
89from .fields import (
910 BaseCSVField ,
@@ -12,6 +13,7 @@ from .fields import (
1213 DateTimeRangeField ,
1314 IsoDateTimeField ,
1415 IsoDateTimeRangeField ,
16+ Lookup ,
1517 LookupChoiceField ,
1618 ModelChoiceField ,
1719 ModelMultipleChoiceField ,
@@ -65,15 +67,15 @@ class Filter:
6567 field_name : str | None = None ,
6668 lookup_expr : str | None = None ,
6769 * ,
68- label : str | None = None ,
70+ label : StrOrPromise | None = None ,
6971 method : Callable [..., Any ] | str | None = None , # Filter methods can return various types
7072 distinct : bool = False ,
7173 exclude : bool = False ,
7274 ** kwargs : Any , # Field kwargs stored as extra (required, help_text, etc.)
7375 ) -> None : ...
7476 def get_method (self , qs : QuerySet [Any ]) -> Callable [..., QuerySet [Any ]]: ... # Returns QuerySet filtering methods
7577 method : Callable [..., Any ] | str | None # Custom filter methods return various types
76- label : str | None # Filter label for display
78+ label : StrOrPromise | None # Filter label for display
7779 @property
7880 def field (self ) -> Field : ...
7981 def filter (self , qs : QuerySet [Any ], value : Any ) -> QuerySet [Any ]: ... # Filter value can be any user input type
@@ -87,7 +89,19 @@ class BooleanFilter(Filter):
8789class ChoiceFilter (Filter ):
8890 field_class : type [Any ] # Base class for choice-based filters
8991 null_value : Any # Null value can be any type (None, empty string, etc.)
90- def __init__ (self , * args : Any , ** kwargs : Any ) -> None : ... # Uses kwargs for null_value config
92+ def __init__ (
93+ self ,
94+ field_name : str | None = None ,
95+ lookup_expr : str | None = None ,
96+ * ,
97+ null_value : Any = ..., # Null value can be any type (None, empty string, etc.)
98+ # Inherited from Filter
99+ label : StrOrPromise | None = None ,
100+ method : Callable [..., Any ] | str | None = None , # Filter methods can return various types
101+ distinct : bool = False ,
102+ exclude : bool = False ,
103+ ** kwargs : Any , # Field kwargs stored as extra (required, help_text, etc.)
104+ ) -> None : ...
91105 def filter (self , qs : QuerySet [Any ], value : Any ) -> QuerySet [Any ]: ...
92106
93107class TypedChoiceFilter (Filter ):
@@ -101,7 +115,20 @@ class MultipleChoiceFilter(Filter):
101115 always_filter : bool
102116 conjoined : bool
103117 null_value : Any # Multiple choice null values vary by implementation
104- def __init__ (self , * args : Any , ** kwargs : Any ) -> None : ... # Uses kwargs for distinct, conjoined, null_value config
118+ def __init__ (
119+ self ,
120+ field_name : str | None = None ,
121+ lookup_expr : str | None = None ,
122+ * ,
123+ distinct : bool = True , # Overrides distinct default
124+ conjoined : bool = False ,
125+ null_value : Any = ..., # Multiple choice null values vary by implementation
126+ # Inherited from Filter
127+ label : StrOrPromise | None = None ,
128+ method : Callable [..., Any ] | str | None = None , # Filter methods can return various types
129+ exclude : bool = False ,
130+ ** kwargs : Any , # Field kwargs stored as extra (required, help_text, etc.)
131+ ) -> None : ...
105132 def is_noop (self , qs : QuerySet [Any ], value : Any ) -> bool : ... # Value can be any filter input
106133 def filter (self , qs : QuerySet [Any ], value : Any ) -> QuerySet [Any ]: ...
107134 def get_filter_predicate (self , v : Any ) -> Q : ... # Predicate value can be any filter input type
@@ -126,18 +153,50 @@ class DurationFilter(Filter):
126153
127154class QuerySetRequestMixin :
128155 queryset : QuerySet [Any ] | None
129- def __init__ (self , * args : Any , ** kwargs : Any ) -> None : ... # Uses kwargs for queryset config
156+ def __init__ (self , * , queryset : QuerySet [ Any ] | None ) -> None : ...
130157 def get_request (self ) -> Any : ... # Request can be HttpRequest or other request types
131158 def get_queryset (self , request : Any ) -> QuerySet [Any ]: ... # Request parameter accepts various request types
132159 @property
133160 def field (self ) -> Field : ...
134161
135162class ModelChoiceFilter (QuerySetRequestMixin , ChoiceFilter ):
136163 field_class : type [ModelChoiceField ] # More specific than parent ChoiceField
137- def __init__ (self , * args : Any , ** kwargs : Any ) -> None : ... # Uses kwargs for empty_label config
164+ def __init__ (
165+ self ,
166+ field_name : str | None = None ,
167+ lookup_expr : str | None = None ,
168+ * ,
169+ # Inherited from QuerySetRequestMixin
170+ queryset : QuerySet [Any ] | None = None ,
171+ # Inherited from ChoiceFilter
172+ null_value : Any = ..., # Null value can be any type (None, empty string, etc.)
173+ # Inherited from Filter
174+ label : StrOrPromise | None = None ,
175+ method : Callable [..., Any ] | str | None = None , # Filter methods can return various types
176+ distinct : bool = False ,
177+ exclude : bool = False ,
178+ ** kwargs : Any , # Field kwargs stored as extra (required, help_text, etc.)
179+ ) -> None : ...
138180
139181class ModelMultipleChoiceFilter (QuerySetRequestMixin , MultipleChoiceFilter ):
140182 field_class : type [ModelMultipleChoiceField ] # More specific than parent MultipleChoiceField
183+ def __init__ (
184+ self ,
185+ field_name : str | None = None ,
186+ lookup_expr : str | None = None ,
187+ * ,
188+ # Inherited from QuerySetRequestMixin
189+ queryset : QuerySet [Any ] | None = None ,
190+ # Inherited from MultipleChoiceFilter
191+ distinct : bool = True , # Overrides distinct default
192+ conjoined : bool = False ,
193+ null_value : Any = ..., # Multiple choice null values vary by implementation
194+ # Inherited from Filter
195+ label : StrOrPromise | None = None ,
196+ method : Callable [..., Any ] | str | None = None , # Filter methods can return various types
197+ exclude : bool = False ,
198+ ** kwargs : Any , # Field kwargs stored as extra (required, help_text, etc.)
199+ ) -> None : ...
141200
142201class NumberFilter (Filter ):
143202 field_class : type [forms .DecimalField ]
@@ -159,7 +218,20 @@ class DateRangeFilter(ChoiceFilter):
159218 choices : list [tuple [str , str ]] | None
160219 filters : dict [str , Filter ] | None
161220 def __init__ (
162- self , choices : list [tuple [str , str ]] | None = None , filters : dict [str , Filter ] | None = None , * args : Any , ** kwargs : Any
221+ self ,
222+ choices : list [tuple [str , str ]] | None = None ,
223+ filters : dict [str , Filter ] | None = None ,
224+ field_name : str | None = None ,
225+ lookup_expr : str | None = None ,
226+ * ,
227+ # Inherited from ChoiceFilter
228+ null_value : Any = ..., # Null value can be any type (None, empty string, etc.)
229+ # Inherited from Filter
230+ label : StrOrPromise | None = None ,
231+ method : Callable [..., Any ] | str | None = None , # Filter methods can return various types
232+ distinct : bool = False ,
233+ exclude : bool = False ,
234+ ** kwargs : Any , # Field kwargs stored as extra (required, help_text, etc.)
163235 ) -> None : ... # Uses args/kwargs for choice and filter configuration
164236 def filter (self , qs : QuerySet [Any ], value : Any ) -> QuerySet [Any ]: ...
165237
@@ -186,45 +258,64 @@ class AllValuesMultipleFilter(MultipleChoiceFilter):
186258class BaseCSVFilter (Filter ):
187259 base_field_class : type [BaseCSVField ] = ...
188260 field_class : type [Any ] # Base class for CSV-based filters
189- def __init__ (self , * args : Any , ** kwargs : Any ) -> None : ... # Uses kwargs for help_text and widget config
190261
191- class BaseInFilter (BaseCSVFilter ):
192- def __init__ (self , * args : Any , ** kwargs : Any ) -> None : ... # Sets lookup_expr and passes through
262+ class BaseInFilter (BaseCSVFilter ): ...
193263
194264class BaseRangeFilter (BaseCSVFilter ):
195265 base_field_class : type [BaseRangeField ] = ...
196- def __init__ (self , * args : Any , ** kwargs : Any ) -> None : ... # Sets lookup_expr and passes through
197266
198267class LookupChoiceFilter (Filter ):
199268 field_class : type [forms .CharField ]
200269 outer_class : type [LookupChoiceField ] = ...
201- empty_label : str | None
202- lookup_choices : list [tuple [str , str ]] | None
270+ empty_label : StrOrPromise | None
271+ lookup_choices : list [tuple [str , StrOrPromise ]] | None
203272 def __init__ (
204273 self ,
205274 field_name : str | None = None ,
206- lookup_choices : list [tuple [str , str ]] | None = None ,
275+ lookup_choices : list [tuple [str , StrOrPromise ]] | None = None ,
207276 field_class : type [Field ] | None = None ,
208- ** kwargs : Any , # Handles empty_label and other field config
277+ * ,
278+ empty_label : StrOrPromise = ...,
279+ # Inherited from Filter
280+ label : StrOrPromise | None = None ,
281+ method : Callable [..., Any ] | str | None = None , # Filter methods can return various types
282+ distinct : bool = False ,
283+ exclude : bool = False ,
284+ ** kwargs : Any , # Field kwargs stored as extra (required, help_text, etc.)
209285 ) -> None : ...
210286 @classmethod
211- def normalize_lookup (cls , lookup : Any ) -> tuple [Any , str ]: ...
212- def get_lookup_choices (self ) -> list [tuple [str , str ]]: ...
287+ def normalize_lookup (cls , lookup : str | tuple [ str , StrOrPromise ] ) -> tuple [str , StrOrPromise ]: ...
288+ def get_lookup_choices (self ) -> list [tuple [str , StrOrPromise ]]: ...
213289 @property
214290 def field (self ) -> Field : ...
215291 lookup_expr : str
216- def filter (self , qs : QuerySet [Any ], lookup : Any ) -> QuerySet [Any ]: ...
292+ def filter (self , qs : QuerySet [Any ], lookup : Lookup ) -> QuerySet [Any ]: ...
217293
218294class OrderingFilter (BaseCSVFilter , ChoiceFilter ):
219295 field_class : type [BaseCSVField ] # Inherits CSV field behavior for comma-separated ordering
220296 descending_fmt : str
221297 param_map : dict [str , str ] | None
222- def __init__ (self , * args : Any , ** kwargs : Any ) -> None : ... # Uses kwargs for fields and field_labels config
298+ def __init__ (
299+ self ,
300+ field_name : str | None = None ,
301+ lookup_expr : str | None = None ,
302+ * ,
303+ fields : dict [str , str ] | Iterable [tuple [str , str ]] = ...,
304+ field_labels : dict [str , StrOrPromise ] = ...,
305+ # Inherited from ChoiceFilter
306+ null_value : Any = ..., # Null value can be any type (None, empty string, etc.)
307+ # Inherited from Filter
308+ label : StrOrPromise | None = None ,
309+ method : Callable [..., Any ] | str | None = None , # Filter methods can return various types
310+ distinct : bool = False ,
311+ exclude : bool = False ,
312+ ** kwargs : Any , # Field kwargs stored as extra (required, help_text, etc.)
313+ ) -> None : ...
223314 def get_ordering_value (self , param : str ) -> str : ...
224315 def filter (self , qs : QuerySet [Any ], value : Any ) -> QuerySet [Any ]: ...
225316 @classmethod
226317 def normalize_fields (cls , fields : Any ) -> list [str ]: ...
227- def build_choices (self , fields : Any , labels : dict [str , str ] | None ) -> list [tuple [str , str ]]: ...
318+ def build_choices (self , fields : Any , labels : dict [str , StrOrPromise ] | None ) -> list [tuple [str , str ]]: ...
228319
229320class FilterMethod :
230321 f : Filter
0 commit comments