Home > Mobile >  easier method to update SQLAlchemy object from form data
easier method to update SQLAlchemy object from form data

Time:06-14

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())
  • Related