I have seen lots of posts about updating SQLAlchemy data, but I haven't been able to find exactly what I've been looking for, if even exists.
I'm working on a blog website using flask, SQLAlchemy and wtforms and have a page that allows users to update their blog posts with a form. Blog posts are stored in a database, and when the user clicks "submit" on the edit page, the SQLAlchemy ORM object should get updated with any changes. The following is the code for my edit_post
route:
@app.route("/edit/<int:post_id>", methods=["GET", "POST"])
def edit_post(post_id):
post_to_edit = BlogPost.query.get(post_id)
edit_form = CreatePostForm(
title=post_to_edit.title,
subtitle=post_to_edit.subtitle,
img_url=post_to_edit.img_url,
author=post_to_edit.author,
body=post_to_edit.body
)
if edit_form.validate_on_submit():
post_to_edit.title = edit_form.title.data
post_to_edit.subtitle = edit_form.subtitle.data
post_to_edit.img_url = edit_form.img_url.data
post_to_edit.author = edit_form.author.data
post_to_edit.body = edit_form.body.data
db.session.commit()
return redirect(url_for("show_post", index=post_id))
return render_template("make-post.html", form=edit_form)
This code works, but I was trying to figure out if I can make it a little more concise or elegant, I suppose. I know SQLAlchemy has an update()
method, and I tried the following, but it didn't work.
post_to_edit.update(
{
BlogPost.title: edit_form.title.data,
BlogPost.subtitle: edit_form.subtitle.data,
BlogPost.date: post_to_edit.date,
BlogPost.body: edit_form.body.data,
BlogPost.author: edit_form.author.data,
BlogPost.img_url: edit_form.img_url.data,
},
synchronize_session=False,
)
Since I don't know what fields from the form that a user wants to update, I'd like an easy way to just update the entire record with having to individually update each field as I've got it now. Any help or advice would be greatly appreciated.
CodePudding user response:
You might want to take a look at flask-wtf's populate_obj
function. Furthermore, the given example shows you how to fill the form by passing the requested database object to your form using the obj
argument.
@app.route('/edit/<int:post_id>', methods=['GET', 'POST'])
def edit_post(post_id):
post = BlogPost.query.get_or_404(post_id)
form = CreatePostForm(request.form, obj=post)
if form.validate_on_submit():
form.populate_obj(post)
db.session.commit()
return redirect(url_for('show_post', index=post_id))
return render_template('make-post.html', **locals())