Home > database >  FlaskForm had to reload select choices
FlaskForm had to reload select choices

Time:02-25

I am new to Python and Flask. I am trying to use WTForm FlaskForm, and having problems with choices in SelectField. I am building my forms like this.

class FightForm(FlaskForm):
    fight_id = StringField('fight_id', render_kw={'readonly': True})
    fight_type_id = SelectField('fight_type_id', 
        choices=[(t.fight_type_id, t.type_name) for t in fight_type.query.all()], validate_choice=False, validators=[DataRequired()])

These choices appear to only load 1 time. If I go add a new fight_type, I have to stop the application and restart if for it to refresh.

Also, I found this answer, flask wtforms selectfield choices not update, but FlaskForm does not trigger the __init__ function this suggests.

I changed it temporarily to Form anyway and got an error saying fight_type_id does not belong to form (paraphrasing).

I would like for these to refresh every time I call the page.

CodePudding user response:

I think you should take a look at the WTForms-SQLAlchemy extension.
The QuerySelectField dynamically loads all database entries based on a submitted database query. A column can be defined for the label of an entry. When the form is submitted, the selected object is automatically queried from the database and is returned by the field.

class FightType(db.Model):
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String, nullable=False, unique=True)
from flask_wtf import FlaskForm
from wtforms.validators import InputRequired
from wtforms_sqlalchemy.fields import QuerySelectField

class FightForm(FlaskForm):
    fight_type = QuerySelectField(
        get_label='name',
        query_factory=lambda: FightType.query.all(),
        validators=[InputRequired()]
    )
@app.route('/new', methods=['GET', 'POST'])
def create():
    form = FightForm(request.form)
    if form.validate_on_submit():
        fight_type = form.fight_type.data
        print(fight_type)
    return render_template('create.html', **locals())
<form method="post">
  {{ form.csrf_token }}
  {{ form.fight_type.label }} {{ form.fight_type() }}
  <input type="submit" value="Go">
</form>
  • Related