Django динамическое поле выбора, слоты назначений - PullRequest
0 голосов
/ 31 октября 2018

Мне нужно руководство по созданию поля динамического выбора для формы. Контекст - это назначения. Я хочу дать людям возможность записывать свои встречи, однако это должно основываться на некоторых критериях. Критерии: дата, время и количество человек.

Я хочу, чтобы поле времени было полем динамического выбора. На основании даты и размера партии "psize" Первоначально я думал, что это может быть достигнуто с помощью фильтра, агрегирования и суммы. Используя вход от кого бы то ни было подачи из.

Я думал, что смогу взять из формы дату и размер партии и использовать их для фильтрации и суммирования числа людей, которые выбрали один и тот же выбор (это важно, потому что я хочу, чтобы 15 или менее человек подписались на любой данный период времени) мои периоды времени с шагом 15 минут и перечислены в кортеже (как поле обычного выбора). Есть идеи?

models.py

class Reservation(models.Model):
"""This tuple is for the Inside, Outside, First Available 
drop down menu for the reservations tab """
    INSIDEOUTSIDE = (
        ('Inside','Inside'),
        ('Outside', 'Outside'),
        ('First Available', 'First Available'),
    )

    STATUS = (
        ('Reservation','Reservation'),
        ('Checked In','Checked In'),
        ('Seated','Seated'),
    )

    PARTYSIZE = (
        (1,'1'),
        (2,'2'),
        (3,'3'),
        (4,'4'),
        (5,'5'),
        (6,'6'),
        (7,'7'),
        (8,'8'),
        (9,'9'),
        (10,'10'),
        (11,'11'),
        (12,'12'),
    )    

    TIMEPERIOD= (
        ('11:30','11:30'),
        ('11:45','11:45'), 
        ('12:00','12:00'), 
        ('12:15','12:15'), 
    )


    name = models.CharField(max_length=22)
    psize = models.IntegerField('Party Size', choices= PARTYSIZE)
    Date = models.DateField()
    Time = models.CharField(max_length=15, choices=TIMEPERIOD)
    location = models.CharField(max_length=15, choices= INSIDEOUTSIDE, default= 'First Available')
    status = models.CharField(max_length=15, choices=STATUS, default='Reservation')

ниже приведен фильтр, который работает, ну не совсем так. Он возвращает элементы, которые я ввожу в него, я хочу иметь возможность передать ему список и сделать так, чтобы он выполнял вычисления с размером детали "psize" и передавал список обратно в форму, в которой есть доступные временные интервалы (временные интервалы). которые имеют менее 15 человек, включая число, которое вменяется в форму).

Reservation.objects.filter(Date='2018-01-01',Time='2:30').aggregate(Sum('psize'))

Кто-нибудь может указать мне правильное направление? Есть мысли?

Обновление Ниже приведен код, который я использую в оболочке для определения вариантов выбора.

def getchoices(request):
    DATE = request.POST.get('Date')
    psize_input = request.post.get('psize')
    slots = Reservation.objects.filter(Date=DATE).values_list('Time').annotate(Sum('psize'))
    TIMEPERIOD= (
    ('11:30','11:30'),
    ('11:45','11:45'),
    ('12:00','12:00'),
    ('12:15','12:15'),
    ('12:30','12:30'),
    ('12:45','12:45'),
    ('01:00','01:00'),
    ('01:15','01:15'),
    ('01:30','01:30'),
    ('01:45','01:45'),
    ('02:00','02:00'),
    ('02:15','02:15'),
    ('02:30','02:30'),
    )
    def checkpsize():
            fullslots1=[]
            fullslots2=[]
            for object in slots:
                    if object[1] > 15-psize_input:
                            fullslots1.append(object[0])
                            fullslots2.append(object[0])
                            fullslotszip = zip(fullslots1, fullslots2)
                            fullslotstup = list(fullslotszip)
                            newchoices = list(filter(lambda x: x not in fullslotstup, TIMEPERIOD))
            return newchoices

Однако мне трудно связать это с моей формой. Я не могу понять, как реализовать Ajax в моей форме, чтобы заполнить мое поле времени на основе ввода psize и date. Любые идеи о хорошем месте, чтобы начать? Учебник возможно?

1 Ответ

0 голосов
/ 31 октября 2018

Если ваш пользователь вставил значение psize_input, вы можете использовать:

 Reservation.objects
    .order_by('Date', 'Time')
    .values('Date', 'Time')
    .annotate(Sum('psize'))  # adds psize sum for each distinct data/time combo
    .filter(psize__sum__lte=15-psize_input)  # filters combos with enough capacity

для получения списка (фактически ValuesIterable) словарей в форме:

[
    {'Date': datetime.date(2018, 10, 31), 'Time': '11:30', 'psize__sum': 5},
    {'Date': datetime.date(2018, 10, 31), 'Time': '12:15', 'psize__sum': 2},
    {'Date': datetime.date(2018, 11, 1), 'Time': '11:45', 'psize__sum': 7},
    # ...
]

содержит ровно те временные интервалы, которые имеют достаточную емкость, с текущим общим значением psize в этом слоте.

...