Как отфильтровать значения связанных полей в django admin?

models.py

class GoodOptions(models.Model):
    option = models.CharField(max_length=32, default=None, verbose_name=u'Характеристика', blank=False)

    class Meta:
        verbose_name = u'Характеристика'
        verbose_name_plural = u'Характеристики'

    def __str__(self):
        return self.option
		
class OptionValue(models.Model):
    value = models.CharField(max_length=255, blank=True, verbose_name=u'Значение опции', default=u'Значение')
    option = models.ForeignKey('GoodOptions', verbose_name=u'Характеристика', default=None, on_delete=models.CASCADE)

    class Meta:
        verbose_name = (u'Значение характеристики')
        verbose_name_plural = (u'Значения характеристик')

    def __str__(self):
        return self.value
		
class OptionsDef(models.Model):
    good = models.ForeignKey('Products', verbose_name=u'Товар', default=None, on_delete=models.CASCADE)
    option = models.ForeignKey('GoodOptions', verbose_name=u'Характеристика', default=None, on_delete=models.CASCADE)
    value = models.ForeignKey('OptionValue', verbose_name=u'Значение', default=None, on_delete=models.CASCADE)

    class Meta:
        verbose_name = (u'Значение характеристики товара')
        verbose_name_plural = (u'Значения характеристик товаров')

    def __str__(self):
        return self.option.option
		
forms.py

class MyOptionsDefForm(forms.ModelForm):
    class Meta:
        model = OptionsDef
        fields = '__all__'
		
	def clean(self):
        cleaned_data = super(MyOptionsDefForm, self).clean()
        sel_option = cleaned_data.get("option") # получить выбранное из выпадающего списка значение характеристики
		option_id = sel_option.id  # получить id характеристики 
		value = OptionValue.objects.filter(option__optionvalue__option=option_id) # получить отфильтрованные по характеристике значения
		self.value = value
		return self.cleaned_data
		
admin.py

from catalog.forms import MyOptionsDefForm
class OptionsDefAdmin(admin.ModelAdmin):
    list_display = ('option', 'good')
    form = MyOptionsDefForm
admin.site.register(OptionsDef, OptionsDefAdmin)


Необходимо сделать так, чтобы в админке после выбора из выпадающего списка Характеристики, в выпадающем списке Значений показывались только те, которые принадлежат к данной характеристике. А сейчас у меня выпадают все Значения, вне зависимости от выбранной Характеристики. Предполагаю решить задачу с помощью переопределении формы в админке и функции def clean - но с текущим кодом админка вообще на нее никак не реагирует.
  • Вопрос задан
  • 863 просмотра
Решения вопроса 1
sergey-gornostaev
@sergey-gornostaev Куратор тега Django
Седой и строгий
Путь web-разработчика должен начинаться с понимания, что сайт - это на самом деле не одно приложение, а два, написанные на разных языках, работающие на разных компьютерах, в разном окружении и в разное время.

В случае Django работу сайта можно разбить на следующие этапы:
  1. Пользователь запустил браузер и ввёл адрес сайта
  2. Браузер установить tcp-соединение с сервером
  3. Браузер отправил в соединение http-запрос
  4. Сервер в ответ на запрос запустил соответствующий python-скрипт
  5. Python-cкрипт в процессе работы сформировал некоторое количество текста и отправил в tcp-соединение
  6. Python-скрипт завершил работу
  7. Браузер принял весь текст от сервера и закрыл соединение
  8. Браузер проанализировал полученных текст и нарисовал пользователю html-форму


Все дальнейшие действия пользователя будут обрабатываться только в браузере, самим браузером и\или javascript'ом. И javascript, и браузер будут работать с теми данными, которые получили от сервера. Если понадобятся другие данные, придётся повторить операции из списка выше, или с помощью отправки формы или с помощью ajax-запроса.

Отсюда ответ на ваш вопрос, если хотите изменения данных в выпадающих списка формы, вам придётся написать javascript-обработчик изменения полей формы, делающий ajax-запросы к серверу и изменяющий значения полей формы в соответствии с полученными от сервера данными, а так же дополнительные представления на сервере для обработки этих ajax-запросов. Для этих целей можно попробовать использовать готовое решение - django-select2.
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы