Django Autocomplete reversed ForeignKey field
I have two models
models.py
class Group(models.Model):
name = models.CharField()
class Book(models.Model):
name = models.CharField()
group = models.ForeignKey(Group, on_delete=models.SET_NULL, related_name='books', related_query_name="book", null=True, blank=True)
I need in admin panel add to Group form multiple select for books.
I have successfully solved this problem using the code below.
admin.py
from .models import Group, Book
from django.forms import ModelForm, ModelMultipleChoiceField
from django.contrib.admin import widgets
class Group_ModelForm(ModelForm):
books = ModelMultipleChoiceField(queryset=Book.objects.all(), widget=widgets.FilteredSelectMultiple('Books', False), required=True, label='Books')
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
if 'instance' in kwargs and kwargs['instance'] is not None:
self.fields['books'].initial = kwargs['books'].books.all()
@admin.register(Group)
class Group_ModelAdmin(admin.ModelAdmin):
list_display = ['name']
list_display_links = ['name']
fields = ['books', 'name']
form = Group_ModelForm
def save_model(self, request, obj, form, change):
super().save_model(request, obj, form, change)
if change:
Book.objects.filter(group=obj).update(group=None)
form.cleaned_data['books'].update(group=obj)
But, when the number of books exceeded 100 000, the Group form took a long time to load, because FilteredSelectMultiple load all 100 000 objects on init.
I try replace FilteredSelectMultiple widget to AutocompleteSelectMultiple widget, but AutocompleteSelectMultiple do not work without many-to-many field in Group model. I try override AutocompleteMixin class to create custom AutocompleteSelectMultiple widget, but I didn’t succeed: the AutocompleteSelectMultiple widget still required a many-to-many field in Group model.
How to do autocomplete select widget for custom field books in Group form?
P.S. In the Group form I need to select existing books. I don't need a inline form that creates new books.
I use Django 4.2