P
P
Pavel Korchagin2020-08-13 01:10:01
Django
Pavel Korchagin, 2020-08-13 01:10:01

How to make dependent filters correctly?

The main question is how to use 2 drop-down filters dependent on each other, while getting the result in the form of the same list when it is selected, pass it to CreateView.

Simply put: By selecting a city from the drop-down list, get a list of groups in the selected city. Next, selecting a group - get a list of Surnames and taking the selected surname, make an entry in the table, adding the rest of the data, also assigning the user who made it to the members field.

In models.py:

class Group(models.Model):

    group = models.CharField('Группа', max_length=5, unique=True)

    def __str__(self):
        return self.group



class Cities(models.Model):
    
    city = models.CharField('Город', max_length=255, unique=True)

    
    def __str__(self):
        return self.city


class Numbers(models.Model):
   

    FIO = models.CharField('ФИО', max_length=255)
    GROUP = models.ForeignKey(Group, on_delete=models.PROTECT, verbose_name='Группа')
    CITY = models.ForeignKey(Cities, on_delete=models.PROTECT, verbose_name='Город')
    DATE_ADD = models.DateTimeField('Дата добавления', auto_now_add=True)
    DATE_DELETE = models.DateTimeField('Дата удаления', blank=True, null=True)
    DATE_UPDATE = models.DateTimeField('Дата обновления', auto_now=True, null=True)
    MEMBERS = models.ForeignKey(User, on_delete=models.PROTECT, verbose_name='Логин изменившего')

    
    def __str__(self):
        return self.FIO


class Clear(models.Model):
   
    chas = [
        ('0', '0'), ('1', '1'), ('2', '2'), ('3', '3'),
        ('4', '4'), ('5', '5'), ('6', '6'),
        ('7', '7'), ('8', '8'), ('9', '9'),
        ('10', '10'), ('11', '11'), ('12', '12'),
        ('13', '13'), ('14', '14'), ('15', '15'),
        ('16', '16'), ('17', '17'), ('18', '18'),
        ('19', '19'), ('20', '20'), ('21', '21'),
        ('22', '22'), ('23', '23')
    ]

    FIO = models.ForeignKey(Numbers, verbose_name='ФИО', on_delete=models.PROTECT)
    DATE_CLEAR = models.DateField('Дата чистки')
    HOUR_FROM = models.CharField('с', max_length=2, choices=chas)
    HOUR_TO = models.CharField('по', max_length=2, choices=chas)
    COMMENT = models.CharField('Комментарий', max_length=255, null=True, blank=True)
    DATE_ADD = models.DateTimeField('Дата добавления', auto_now_add=True)
    DATE_DELETE = models.DateTimeField('Дата удаления', blank=True, null=True)
    DATE_UPDATE = models.DateTimeField('Дата обновления', auto_now=True, null=True)
    MEMBERS = models.ForeignKey(User, on_delete=models.PROTECT, verbose_name='Логин изменившего')

In views.py:
class AddClear(PermissionRequiredMixin, CreateView):
    permission_required = 'clear.add_clear'
    model = Clear
    template_name = 'clear/add_clear.html'
    form_class = ClearForm
    success_url = reverse_lazy('clear')
    extra_context = {'title': 'Добавить в чистку'}

in forms.py:
class ClearForm(forms.ModelForm):
    class Meta:
        model = Clear
        fields = ['FIO', 'DATE_CLEAR', 'HOUR_FROM', 'HOUR_TO', 'COMMENT',]

    def clean(self):
        hour_from = self.cleaned_data['HOUR_FROM']
        hour_to = self.cleaned_data['HOUR_TO']
        if hour_from > hour_to:
            raise ValidationError('"Время C" должно быть меньше')
        return self.cleaned_data

    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        for field in self.fields:
            self.fields[field].widget.attrs['class'] = 'form-control'

in urls.py:
path('add_clear/', views.AddLine2Clear.as_view(), name='add_clear')

in HTML:
{% extends 'base.html' %}

{% block title %}{{ title }}{% endblock %}
<h1 class="mt-3">{{ title }}</h1>

<div class="col-3 ml-4">

<form class="mt-4" action="{% url 'add_clear' %}" method = 'post'>
    {% csrf_token %}

{{ form }}

        <button type="submit" class="btn btn-danger btn-block mt-2">Добавить запись</button>


</form>
</div>
{% endblock %}

I understand that this should be done on the client side using AJAX, or something like that. But in ajax I am a complete 0, and in django I have not gone far. I would be grateful for at least a similar implementation example.

Answer the question

In order to leave comments, you need to log in

1 answer(s)
S
Sergey Tikhonov, 2020-08-15
@tumbler

Either after a few form steps, by reloading the page, or (since ajax==0) using libraries that can do this, for example, django-autocompletelight .

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question