Search code examples
pythonflasksqlalchemywtformsweb-development-server

Flask WTForms submit button not working at all


I'm trying to make a registeration page using WTForms but I'm having difficulties getting the submit button to work. When I fill all the page's fields and click the 'Submit' button nothing happens whatsoever, I checked the database to see if the form instance was even created and it wasn't, I also don't get redirected to the desired URL after submitting.

I'm currently following a Flask tutorial for Python on YT by JimShapedCoding Link to video

Here's my code:

init.py

from flask import Flask, render_template 
from flask_sqlalchemy import SQLAlchemy    #tables using classes

app = Flask(__name__)
app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///market.db'
app.config['SECRET_KEY'] = 'b61198e1258118d75478e8e4'
db = SQLAlchemy(app)


from market import routes

forms.py

from flask_wtf import FlaskForm
from wtforms import StringField, PasswordField, SubmitField


class RegisterForm(FlaskForm):
    username = StringField(label='Enter your username:')
    email_address = StringField(label='Email:')
    pw1 = PasswordField(label='Password:')
    pw2 = PasswordField(label='Confirm Password:')
    submit = SubmitField(label='Create Account')

models.py

from market import db

class User(db.Model):
    id = db.Column(db.Integer(), primary_key=True)
    username = db.Column(db.String(length=18), nullable=False, unique=True)
    email_address = db.Column(db.String(length=40), nullable=False, unique=True)
    password_hash = db.Column(db.String(length=60), nullable=False)
    budget = db.Column(db.Integer(), nullable=False, default=1000)
    items = db.relationship('Item', backref='owned_user', lazy=True)

    def __repr__(self):
        return f"Item: {self.name}"

routes.py

from market import app
from flask import Flask, render_template, redirect, url_for
from market.models import Item, User
from market.forms import RegisterForm
from market import db

@app.route('/register', methods=['GET', 'POST'])
def register_page():
    form = RegisterForm()
    if form.validate_on_submit():
        user_to_create = User(username=form.username.data,
                              email_address=form.email_address.data,
                              password_hash=form.pw1.data)    
        db.session.add(user_to_create)
        db.session.commit()
        return redirect(url_for('market_page'))

    return render_template('register.html', form=form)

run.py

from market import app

if __name__ == '__main__':
    app.run(debug=True)

templates folder:

register.html

{% extends 'base.html' %}
{% block title %}
    Register 
{% endblock %}   
{% block content %}
<body  class='text-center'>
    <div class="container"
        <form method="POST" action="/market" class="form-register" style="color:white">
            {{ form.hidden_tag() }}
            <img class="mb-4" src="" alt="">
            <h1 class="h3 mb-3 font-weight-normal">
                Please Create your Account
            </h1>
            <br>
            
            {{ form.username.label() }}
            {{ form.username(class="form-control", placeholder="Username") }}
            
            {{ form.email_address.label() }}
            {{ form.email_address(class="form-control", placeholder="Email Address") }}
            
            {{ form.pw1.label() }}
            {{ form.pw1(class="form-control", placeholder="Password") }}
            
            {{ form.pw2.label() }}
            {{ form.pw2(class="form-control", placeholder="Confirm Password") }}
            
            <br>
            
            {{ form.submit(class="btn btn-lg btn-block btn-primary") }} 
        </form>
    </div>
</body>  
{% endblock %}  

base.html

<!doctype html>
<html lang="en">
   <head>
      <!-- Required meta tags -->
      <meta charset="utf-8">
      <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
      <title>
        {% block title %}

        {% endblock%}
      </title>
   </head>
   <body>
      <nav class="navbar navbar-expand-md navbar-dark bg-dark">
        <a class="navbar-brand" href="#">Flask Market</a>
        <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarNav">
          <span class="navbar-toggler-icon"></span>
        </button>
        <div class="collapse navbar-collapse" id="navbarNav">
          <ul class="navbar-nav mr-auto">
              <li class="nav-item active">
                  <a class="nav-link" href="{{ url_for('home_page') }}">Home <span class="sr-only">(current)</span></a>
              </li>
              <li class="nav-item">
                  <a class="nav-link" href="{{ url_for('market_page') }}">Market</a>
              </li>
          </ul>
          <ul class="navbar-nav">
              <li class="nav-item">
                  <a class="nav-link" href="#">Login</a>
              </li>
              <li class="nav-item">
                  <a class="nav-link" href="{{ url_for('register_page') }}">Register</a>
              </li>
          </ul>
        </div>
      </nav>
        {% block content %}

        {% endblock %}
   </body>
   <style>
      body {
      background-color: #212121;
      color: white
      }
   </style>
</html>

Photo of my project layout

How the registeration page looks like

After revising my code multiple times & making sure it's like what was in the video, I still couldn't manage to fix my issue or even impact it.

What I tried:

I tried using app.app_context().push()

before the db.session.add(user_to_create) line in routes.py

I made sure all the variable names matched

I tried running it using $env:FLASK_APP = 'init.py' followed by flask run

This is how my terminal looks like whenever the page is refreshed:

127.0.0.1 - - [10/Apr/2023 23:09:02] "GET /register HTTP/1.1" 200 - 127.0.0.1 - - [10/Apr/2023 23:09:11] "GET /favicon.ico HTTP/1.1" 404 -

If anyone may offer some help that'll be wonderful as I have been trying to debug this issue for around 3 days now.


Solution

  • Your code contains a typo in the register.html file. The div element that encloses the form is missing the trailing > before the form element begins.

    <div class="container">
        <!-- Your form here. -->
    </div>