skip to Main Content

I am trying to get flash messages to appear on both my login and registration pages. they work as expected on registration.html but do not appear at all on login.html. Both html pages include {% extends "layout.html" %}

here is my login and register python code

@app.route("/login", methods=["GET", "POST"])
def login():
    """Log user in"""

    # Forget any user_id
    session.clear()

    # User submitted form
    if request.method == "POST":

        # Ensure username was submitted
        if not request.form.get("username"):
            flash('Must provide username', 'error')
            return redirect("/login")


        # Ensure password was submitted
        elif not request.form.get("password"):
            flash('Must provide password', 'error')
            return redirect("/login")

        # Query database for username
        rows = db.execute("SELECT * FROM users WHERE username = ?", request.form.get("username"))

        # Ensure username exists and password is correct
        if len(rows) != 1 or not check_password_hash(rows[0]["hash"], request.form.get("password")):
            flash('Invalid username and/or password', 'error')
            return redirect("/login")

        # Remember which user has logged in
        session["user_id"] = rows[0]["id"]

        # Redirect user to home page
        return redirect("/")

    return render_template("login.html", messages=get_flashed_messages())


@app.route("/register", methods=["GET", "POST"])
def register():
    """Register user"""
    if request.method == "POST":

        if not request.form.get("username"):
            flash('Invalid Username.', 'error')
            return redirect("/register")


        elif not request.form.get("password"):
            flash('Invalid Password.', 'error')
            return redirect("/register")

        if request.form.get("password") != request.form.get("confirmation"):
            flash('Passwords do not match', 'error')
            return redirect("/register")

        rows = db.execute("SELECT * FROM users WHERE username = ?", request.form.get("username"))
        if len(rows) == 1:
            flash('Username already exists', 'error')
            return redirect("/register")

        username = request.form.get("username")
        hash = generate_password_hash(request.form.get("password"), method='pbkdf2:sha256', salt_length=8)

        db.execute("INSERT INTO users (username,hash) VALUES(?,?)", username, hash)
        return redirect("/login")

    return render_template("register.html", messages=get_flashed_messages())




and this is the code from layout.html

{% block content %}
<div class="text-center">
    {% for message in get_flashed_messages() %}
        <div class="alert alert-dark text-center" role="alert">
            {{ message }}
        </div>
    {% endfor %}
    {% block page_content %}{% endblock %}
</div>
{% endblock %}

any idea why its working on one page and not the other?

2

Answers


  1. Not sure how this works in either of them haha

    Since you’re rendering the html template with messages=get_flashed_messages(),
    the jinja variable call should be for messages, not get_flashed_messages(). Jinja will only know the variable name you give it and its associated value, not the function used in python.

    Therefore, your code should look like this…

    {% block content %}
    <div class="text-center">
        {% for message in messages %}
            <div class="alert alert-dark text-center" role="alert">
                {{ message }}
            </div>
        {% endfor %}
        {% block page_content %}{% endblock %}
    </div>
    {% endblock %}
    

    Hope this helps!

    Login or Signup to reply.
  2. A possible solution is trying to use the messages variable defined in

    return render_template("register.html", messages=get_flashed_messages())
    

    instead of

        {% for message in get_flashed_messages() %}
            <div class="alert alert-dark text-center" role="alert">
                {{ message }}
            </div>
        {% endfor %}
    

    as such:

    {% for message in messages %}
        <div class="alert alert-dark text-center" role="alert">
            {{ message }}
        </div>
    {% endfor %}
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search