Как фильтровать опции с другим значением select в админ-формах django

У меня есть модели Address, city, state с отношением один к одному, и я пытаюсь фильтровать города по штату, когда хочу добавить новый адрес, поэтому проблема в том, что я могу видеть все города для любого штата, и я понятия не имею, как это исправить. Есть идеи?

модели

class State(models.Model):
    state_name = models.CharField(max_length=50)
    def __str__(self) -> str:
        return self.state_name
    
class City(models.Model):
    cityـname = models.CharField(max_length=50)
    state = models.ForeignKey(to=State,on_delete=models.CASCADE)
    def __str__(self) -> str:
        return self.cityـname

class Adrress(models.Model):
    user = models.ForeignKey(to=User,on_delete=models.CASCADE)
    
    city = models.ForeignKey(to=City,on_delete=models.CASCADE)
    description = models.TextField()
    def __str__(self) -> str:
        return self.description

admin

@admin.register(State)
class StateAdmin(admin.ModelAdmin):
    pass
@admin.register(City)
class CityAdmin(admin.ModelAdmin):
    pass
@admin.register(Adrress)
class AdrressAdmin(admin.ModelAdmin):
    pass

поэтому я ожидаю, что когда я хочу добавить новый адрес, я увижу форму, подобную этой expected admin form и при смене штата в выпадающем списке городов, чтобы был виден только город для этого штата

Как я пробовал использование пользовательской формы поэтому я изменил код вот так в админке и сделал пользовательский виджет и Jquery

admin

@admin.register(Adrress)
class AdrressAdmin(admin.ModelAdmin):
    form = AdrressAdminForm

Формы

class RelatedChoieField(forms.widgets.Select):
    
    def __init__(self, attrs=None, choices=()):
        super().__init__(attrs,choices)
        self.data = {}
        for obj in City.objects.all():
            if not obj.state in self.data.keys():
                self.data[obj.state.state_name] = [obj.cityـname]
            else:    
                self.data[obj.state.state_name].append(obj.cityـname)
        
            
    
    def render(self, name, value, attrs=None, renderer=None):
        html = super().render(name, value, attrs)
        
        inline_code = mark_safe(
            f"<script>obj ={dumps(self.data,indent=4)};$(\"#id_state\").change(()=>{{$(\"#id_city\").innerHTML=\"\";for(var i=0;i<obj[$(\"#id_state\").find(\":selected\").text()].length;i++){{$(\"#id_city\").innerHTML+=$(\"<option></option>\").innerHTML=obj[$(\"#id_state\").find(\":selected\").text()][i]}} }})</script>"
        )
        return html + inline_code
    

class AdrressAdminForm(forms.ModelForm):
    
    state = forms.ModelChoiceField(
        queryset=State.objects.all(),
        widget=RelatedChoieField,
    )
    
    class Meta:
        model= Adrress
        fields = ["user","state","city","description"]

Но все еще не происходит фильтрации, так что же мне делать? Любая идея будет оценена по достоинству!

Может быть, это сработает.

class AdrressAdminForm(forms.ModelForm):
    
    state = forms.ModelChoiceField(
        queryset=State.objects.all(),
        widget=RelatedChoieField,
    )
    
    class Meta:
        model= Adrress
        fields = ["user","state","city","description"]
    def __init(self, city=None, *args, **kwargs):
       super().__init__()
       if city: self.fields['state'].queryset = State.objects.filter(city=city)
          
Вернуться на верх