Flask SQL Alchemy - 如何通过表单一次更新多条记录
Flask SQL Alchemy - How do I update several records at once through a form
我正在为如何在 SQL Alchemy 中使用表单而苦苦挣扎。我所做的每个教程和示例都专注于单个记录表单,其中每个字段都是更新的 table 以最终创建记录。
我想将我的数据呈现为 table 充满(c100 行)事务,仅更新一列上的每一行。这是一个支出清单,我想确定哪些交易要从分析中排除。我可以将其呈现为每行一个表单字段的 table,但是当我将其提交回我的视图时,我无法获取 table 行 ID 以将其写入数据库。
有谁知道重点是管理多条记录的示例或教程?也许是管理数据库中所有条目的管理功能?例如select 所有这些记录然后删除它们。
我的代码如下,但老实说,我想知道我是否以正确的方式进行处理。
我的模特:
class Transaction(db.Model):
__tablename__ = 'transactions'
id = db.Column(db.Integer, primary_key=True)
date = db.Column(db.Date, index=True)
description = db.Column(db.String(128), index=True)
amount = db.Column(db.Float, index=True)
balance = db.Column(db.Float)
excluded = db.Column(db.Integer, index=True)
source_id = db.Column(db.Integer, db.ForeignKey('sources.id'))
category_id = db.Column(db.Integer, db.ForeignKey('categories.id'))
我的表格:
class TransExclude(FlaskForm):
excluded = SelectField('Exclude', choices = EXCLUDED_CHOICES, validators=[DataRequired()])
submit = SubmitField('Add')
我的看法:
@app.route('/exclude_transactions', methods=['GET', 'POST'])
def exclude_transactions():
form = TransExclude()
if request.method == "POST":
# This is where I need the ID of the record as well as the excluded return...
# excluded = dict(EXCLUDED_CHOICES).get(form.excluded.data)
req = request.form
df = pd.DataFrame(list(req.items(1)))
print(df)
flash('Congratulations, you have updated the exclusions!')
return redirect(url_for('process_new_month'))
transactions = Transaction.query.all()
return render_template('excludes.html', title= 'Monthly Excludes',transactions=transactions, form=form)
和我的 HTML:
{% extends "base.html" %}
{% import 'bootstrap/wtf.html' as wtf %}
{% block app_content %}
<div class="container">
<div class="row">
<div class="col-sm">
<br>
<h2>Exclude Transactions</h2>
<hr>
<form method="post">
<table class="table table-striped">
<thead>
<tr>
<th>ID</th>
<th> Date</th>
<th>Description</th>
<th> Amount</th>
<th>Exclude?</th>
<th></th>
</tr>
</thead>
<tbody>
{% for transaction in transactions %}
<tr>
<td>{{transaction.id}}</td>
<td>{{transaction.date}}</td>
<td>{{transaction.description}}</td>
<td>{{transaction.amount}}</td>
<td>{{form.excluded}}</td>
</tr>
{% endfor %}
</tbody>
</table>
<button type="submit" class="btn btn-primary">Exclude Items</button>
</form>
</div>
</div>
</div>
{% endblock %}
以下代码向您展示了一个示例,其中FieldList 类型的字段与FormFields 结合使用。在每个嵌套表单中都有一个包含数据记录 ID 的隐藏字段。为此,在创建父表单时用所需数据填充字典。
为了方便理解,我在代码里写了注释
这个解决方案当然不是最优的,但有可能。
我认为您应该能够将此变体应用到您的代码中。
class Item(db.Model):
id = db.Column(db.Integer, primary_key=True)
title = db.Column(db.String, nullable=False)
class _SubForm(Form):
# The HiddenField later contains the id of the data record.
id = HiddenField('id')
excluded = SelectField('Exclude', choices=EXCLUDED_CHOICES, validators=[DataRequired()])
# The constructor is overwritten in order to bypass further fields for the csrf token.
def __init__(self, csrf_enabled=False, *args, **kwargs):
super(_SubForm, self).__init__(csrf_enabled=csrf_enabled, *args, **kwargs)
class EditForm(FlaskForm):
items = FieldList(FormField(_SubForm))
@app.route('/edit', methods=['GET', 'POST'])
def edit():
# Fill in the form with the necessary data.
items = Item.query.all()
form = EditForm(request.form, data={ 'items': items })
if form.validate_on_submit():
# Iterate over the FieldList here.
for field in form.items.data:
id = item_field.get('id')
excluded = item_field.get('excluded')
print(id, excluded)
return render_template('edit.html', **locals())
<form method="post">
{{ form.csrf_token }}
<table>
{% for field in form.items -%}
<tr>
<td>
{{ items[loop.index0].title }}
</td>
<td>
{{ field.hidden_tag() }}
{{ field.excluded }}
</td>
</tr>
{% endfor -%}
</table>
<input type="submit" />
</form>
我正在为如何在 SQL Alchemy 中使用表单而苦苦挣扎。我所做的每个教程和示例都专注于单个记录表单,其中每个字段都是更新的 table 以最终创建记录。
我想将我的数据呈现为 table 充满(c100 行)事务,仅更新一列上的每一行。这是一个支出清单,我想确定哪些交易要从分析中排除。我可以将其呈现为每行一个表单字段的 table,但是当我将其提交回我的视图时,我无法获取 table 行 ID 以将其写入数据库。
有谁知道重点是管理多条记录的示例或教程?也许是管理数据库中所有条目的管理功能?例如select 所有这些记录然后删除它们。
我的代码如下,但老实说,我想知道我是否以正确的方式进行处理。
我的模特:
class Transaction(db.Model):
__tablename__ = 'transactions'
id = db.Column(db.Integer, primary_key=True)
date = db.Column(db.Date, index=True)
description = db.Column(db.String(128), index=True)
amount = db.Column(db.Float, index=True)
balance = db.Column(db.Float)
excluded = db.Column(db.Integer, index=True)
source_id = db.Column(db.Integer, db.ForeignKey('sources.id'))
category_id = db.Column(db.Integer, db.ForeignKey('categories.id'))
我的表格:
class TransExclude(FlaskForm):
excluded = SelectField('Exclude', choices = EXCLUDED_CHOICES, validators=[DataRequired()])
submit = SubmitField('Add')
我的看法:
@app.route('/exclude_transactions', methods=['GET', 'POST'])
def exclude_transactions():
form = TransExclude()
if request.method == "POST":
# This is where I need the ID of the record as well as the excluded return...
# excluded = dict(EXCLUDED_CHOICES).get(form.excluded.data)
req = request.form
df = pd.DataFrame(list(req.items(1)))
print(df)
flash('Congratulations, you have updated the exclusions!')
return redirect(url_for('process_new_month'))
transactions = Transaction.query.all()
return render_template('excludes.html', title= 'Monthly Excludes',transactions=transactions, form=form)
和我的 HTML:
{% extends "base.html" %}
{% import 'bootstrap/wtf.html' as wtf %}
{% block app_content %}
<div class="container">
<div class="row">
<div class="col-sm">
<br>
<h2>Exclude Transactions</h2>
<hr>
<form method="post">
<table class="table table-striped">
<thead>
<tr>
<th>ID</th>
<th> Date</th>
<th>Description</th>
<th> Amount</th>
<th>Exclude?</th>
<th></th>
</tr>
</thead>
<tbody>
{% for transaction in transactions %}
<tr>
<td>{{transaction.id}}</td>
<td>{{transaction.date}}</td>
<td>{{transaction.description}}</td>
<td>{{transaction.amount}}</td>
<td>{{form.excluded}}</td>
</tr>
{% endfor %}
</tbody>
</table>
<button type="submit" class="btn btn-primary">Exclude Items</button>
</form>
</div>
</div>
</div>
{% endblock %}
以下代码向您展示了一个示例,其中FieldList 类型的字段与FormFields 结合使用。在每个嵌套表单中都有一个包含数据记录 ID 的隐藏字段。为此,在创建父表单时用所需数据填充字典。
为了方便理解,我在代码里写了注释
这个解决方案当然不是最优的,但有可能。
我认为您应该能够将此变体应用到您的代码中。
class Item(db.Model):
id = db.Column(db.Integer, primary_key=True)
title = db.Column(db.String, nullable=False)
class _SubForm(Form):
# The HiddenField later contains the id of the data record.
id = HiddenField('id')
excluded = SelectField('Exclude', choices=EXCLUDED_CHOICES, validators=[DataRequired()])
# The constructor is overwritten in order to bypass further fields for the csrf token.
def __init__(self, csrf_enabled=False, *args, **kwargs):
super(_SubForm, self).__init__(csrf_enabled=csrf_enabled, *args, **kwargs)
class EditForm(FlaskForm):
items = FieldList(FormField(_SubForm))
@app.route('/edit', methods=['GET', 'POST'])
def edit():
# Fill in the form with the necessary data.
items = Item.query.all()
form = EditForm(request.form, data={ 'items': items })
if form.validate_on_submit():
# Iterate over the FieldList here.
for field in form.items.data:
id = item_field.get('id')
excluded = item_field.get('excluded')
print(id, excluded)
return render_template('edit.html', **locals())
<form method="post">
{{ form.csrf_token }}
<table>
{% for field in form.items -%}
<tr>
<td>
{{ items[loop.index0].title }}
</td>
<td>
{{ field.hidden_tag() }}
{{ field.excluded }}
</td>
</tr>
{% endfor -%}
</table>
<input type="submit" />
</form>