Zion
Zion

Reputation: 1610

Flask routing error with custom decorator

blueprint.py

### Standard Library Imports ###

################################

### 3rd Party Imports ###
from flask import Blueprint
################################

### Local Imports ###

################################


main = Blueprint('main', __name__)
from .views import *

views.py:

@main.route("/", methods=["GET", "POST"])
@login_required
@check_confirmation
def index():
    users=None
    form = UserSearchForm()
    now = datetime.datetime.now()
    current_month = now.month
    current_year = now.year
    days_in_month = calendar.monthrange(current_year, current_month)[1]
    calendar_info = {
        "days_in_month": days_in_month,
        "current_year": current_year,
        "current_month": get_month(),
    }
    if form.validate_on_submit():
        searched = form.username.data
        return redirect(url_for("main.search", searched_user=searched))
    return render_template('/main/main_index.html',
                           **calendar_info,
                           months=months,
                           users=users,
                           form=form)

check confirmation decorator:

def check_confirmation(func):
    def wrap(*args, **kwargs):
        if not current_user.confirmed:
            flash("Please confirm your account")
            return redirect(url_for("main.unconfirmed"))
        else:
            return func(*args, **kwargs)
    return wrap

what's interesting is. using class based views the decorator works fine but not for function based views. infact all custom decorators I make with flask using function based views and blueprints returns a routing build error

any thoughts as to why this is happening?

Upvotes: 2

Views: 469

Answers (1)

Zion
Zion

Reputation: 1610

well as it turns out

def check_confirmation(func):
    @wraps(func)
    def wrap(*args, **kwargs):
        if not current_user.confirmed:
            flash("Please confirm your account")
            return redirect(url_for("main.unconfirmed"))
        else:
            return func(*args, **kwargs)
    return wrap

you need to import the wraps function from the functools library I didn't think you'd need to because I thought the wraps decorator just gets the info on the function. but my guess is it does this to differentiate from a regularly defined function vs a view function. Is my guess right?

but judging from this I'd assume that flask introspects the functions and im pretty sure it does.

but what bothered me was when you use class based views the check_confirmation doesn't need the @wraps

Upvotes: 1

Related Questions