1- from django .contrib .admin import SimpleListFilter
1+ from collections .abc import Callable , Sequence
2+
3+ from django .contrib .admin import SimpleListFilter , ModelAdmin
24from django .core .paginator import Paginator
35from django .db import connection , transaction , OperationalError
6+ from django .db .models import Model
47from django .utils .functional import cached_property
58from django .urls import reverse
69from django .utils .html import format_html
@@ -46,27 +49,31 @@ def admin_link_html(linked_obj):
4649 return format_html ('<a href="{}">{}</a>' , url , repr (linked_obj ))
4750
4851
49- def linked_fk (field_name ) :
52+ def linked_fk [ T : type [ ModelAdmin ]] (field_name : str ) -> Callable [[ T ], T ] :
5053 """Decorator that adds a link for a foreign key field
5154 """
5255 def add_link (cls ):
5356 def link (self , instance ):
5457 linked_obj = getattr (instance , field_name )
5558 return admin_link_html (linked_obj )
5659 link_field = '{}_link' .format (field_name )
57- link .short_description = field_name .replace ('_' , ' ' )
60+ link .short_description = field_name .replace ('_' , ' ' ) # type: ignore[attr-defined]
5861 setattr (cls , link_field , link )
5962 append_to_cls_property (cls , 'readonly_fields' , link_field )
6063 append_to_cls_property (cls , 'exclude' , field_name )
6164 return cls
6265 return add_link
6366
6467
65- def linked_many (field_name , order_by = None , select_related = None , defer = None ):
66- """Decorator that adds links for a *-to-many field
67- """
68- def add_links (cls ):
69- def links (self , instance ):
68+ def linked_many [T : type [ModelAdmin ]](
69+ field_name : str ,
70+ order_by : Sequence [str ] = (),
71+ select_related : Sequence [str ] = (),
72+ defer : Sequence [str ] = (),
73+ ) -> Callable [[T ], T ]:
74+ """Decorator that adds links for a *-to-many field"""
75+ def add_links (cls : T ) -> T :
76+ def links (self , instance : Model ) -> str :
7077 linked_qs = getattr (instance , field_name ).all ()
7178 if select_related :
7279 linked_qs = linked_qs .select_related (* select_related )
@@ -81,8 +88,8 @@ def links(self, instance):
8188 for obj in linked_qs
8289 ))
8390 )
84- links_field = '{ }_links'. format ( field_name )
85- links .short_description = field_name .replace ('_' , ' ' )
91+ links_field = f' { field_name } _links'
92+ links .short_description = field_name .replace ('_' , ' ' ) # type: ignore[attr-defined]
8693 setattr (cls , links_field , links )
8794 append_to_cls_property (cls , 'readonly_fields' , links_field )
8895 append_to_cls_property (cls , 'exclude' , field_name )
0 commit comments