Передать целое число из вида в форму в колбе python

У меня есть wtform с queryselectfield, который в настоящее время заполняется данными из базы данных со всеми командами:

class PitScoutingForm(FlaskForm):
    team = QuerySelectField(
        query_factory=lambda: Teams.query.all(), get_label='number')

И вид:

@app.route('/competitions/pit-scouting', methods=['GET', 'POST'])
@login_required
def pit_scouting():
    form = PitScoutingForm(request.values)
    form.team.choices = [(a.id, a.number) for a in
                         Teams.query.order_by('number')]

Все это прекрасно работает. Но список команд растет довольно большой, и я хотел бы ограничить команды, которые показывают в этой области, выбранными в настоящее время конкурентами, поэтому я бы изменил представление на

@app.route('competitions/<int: comp_id>/pit-scouting', methods=['GET', 'POST'])

но я не уверен, как передать comp_id из представления в форму, чтобы я мог фильтровать идентификатор соревнования, поэтому я получаю только команды, которые находятся в этом соревновании. Я видел эту запись, но я не совсем понимаю решение. Любые указатели оценены.

3 ответа

  1. Comp_id используется в представлении только для выбора команд из этого соревнования. Измените comp_id, как бы он ни назывался в вашем классе Teams.

    @app.route('competitions/<int: comp_id>/pit-scouting', methods=['GET',  'POST'])
    @login_required
    def pit_scouting(comp_id):
        form = PitScoutingForm(request.values)
        form.team.choices = [(a.id, a.number) for a in Teams.query.filter_by(comp_id=comp_id).order_by('number')]
    
  2. Из колбы документация по регистрации маршрута URL:

    Переменные части передаются в функцию view в качестве аргументов ключевых слов.

    Это означает, что вам просто нужно обновить функцию представления, чтобы иметь comp_idв качестве параметра, как так:

    @app.route('competitions/<int: comp_id>/pit-scouting', methods=['GET', 'POST'])
    @login_required
    def pit_scouting(comp_id):
        form = PitScoutingForm(request.values)
        form.team.choices = [(a.id, a.number) for a in
                         Teams.query.order_by('number')]
    
  3. Спасибо за указания, ребята, вы привели меня в направлении, которое помогло. Я нашел другое решение, которое предложило использовать простое поле выбора, а затем загрузить варианты в init вместо этого, как это:

    class PitScoutingForm(FlaskForm):
        team = SelectField('Team', coerce=int)
        ...
        def __init__(self, *args, **kwargs):
            super(PitScoutingForm, self).__init__(*args, **kwargs)
            self.team.choices = [(a.id, a.number) for a in Teams.query.order_by('number')]
    

    затем мое представление (игнорировать sql…иногда это проще, чем синтаксис sqlalchemy) остается как есть wrt установка вариантов, за исключением использования данных конкуренции, переданных в представление.

    @app.route('/pit-scouting/', defaults={'comp': 2}, methods=['GET', 'POST'])
    @app.route('/pit-scouting/competitions/<int:comp>', methods=['GET', 'POST'])
    @login_required
    def pit_scouting(comp):
        sql_text = '''query here'''.format(comp)
        result = db.engine.execute(sql_text)
    
        form = PitScoutingForm(request.values)
        form.team.choices = [(a.id, a.number) for a in result]