I have problem with form validation in Flask. In login.html I have:
{% extends "base.html" %}
{% block content %}
<center>Sign In</center>
<form action="/login" method="post" >
<div class="login">
<input type="text" placeholder="Username" id="username" name="username">
<input type="password" placeholder="password" id="password" name="password">
<input type="submit" value="Sign In">
</div>
<div class="shadow"></div>
</form>
{% endblock %}
In routes.py I have:
#app.route('/login', methods=['GET', 'POST'])
def login():
if current_user.is_authenticated:
return redirect(url_for('index'))
if request.method == 'POST'and form.validate():
if(request.form["username"] is None or request.form["password"] is None):
flash("fill inputs")
else:
user = User.query.filter_by(username=request.form["username"]).first()
if user is None or not user.check_password(request.form["password"]):
flash('Invalid username or password')
return redirect(url_for('login'))
login_user(user)
userCookie = request.form['username']
resp = make_response(render_template('index.html'))
resp.set_cookie('user', userCookie)
next_page = request.args.get('next')
if not next_page or url_parse(next_page).netloc != '':
next_page = url_for('index')
return resp
return redirect(next_page)
return render_template('login.html', title='Sign In')
Unfortunately, after clicking to log in, nothing happens even if I write correct username and password. Before I was using WTForms and everything worked well, but I couldnt add css to modify form and after changing it, the validation dosnt work well. Can somebody help me with this problem?
Related
So this is my login page, and I have a login button that logins the user. However, I wish to add a "Home" button that when pressed, would redirect the user to the index.html page. However, I'm unsure of how to approach this.
In my app.py flask file:
#app.route('/login', methods=['GET', 'POST'])
def login():
form = LoginForm()
if form.validate_on_submit():
user = User.query.filter_by(username=form.username.data).first()
if user:
if check_password_hash(user.password, form.password.data):
login_user(user, remember=form.remember.data)
return redirect(url_for('dashboard'))
return '<h1>Invalid username or password</h1>'
elif request.form['home'] == 'Home':
print("Home pressed")
return render_template('index.html')
#return '<h1>' + form.username.data + ' ' + form.password.data + '</h1>'
return render_template('login.html', form=form)
In my login.html:
{% block content %}
<div class="container">
<form class="form-signin" method="POST" action="/login">
<h2 class="form-signin-heading">Please sign in</h2>
{{ form.hidden_tag() }}
{{ wtf.form_field(form.username) }}
{{ wtf.form_field(form.password) }}
{{ wtf.form_field(form.remember) }}
<button class="btn btn-lg btn-primary btn-block" type="submit">Sign in</button>
<input type="submit" name="home" value="Home">
</form>
</div> <!-- /container -->
{% endblock %}
If user do successfull login then it is redirecting to next but if user can not do login then I wants to change template and wants to redirect to next page but it is not working.
Views.py
def login(request, template_path='login.html'):
"""
"""
# We'll only allow staff to view this page after login.
if request.user.is_authenticated:
return redirect('home')
if request.method == 'POST':
if request.META['HTTP_REFERER'].split('/')[-1] == 'bs5':
template_path = 'theme/bs5_theme.html'
response = LoginView.as_view(
template_name=template_path,
redirect_field_name='next',
form_class=EmailAuthenticationForm,
)(request)
if request.is_ajax():
if request.user.is_authenticated:
return HttpResponse(
json.dumps(dict(success=True, next=request.POST.get("next"))),
content_type="application/json"
)
return HttpResponse(json.dumps(False), content_type="application/json")
else:
return response
else:
form = auth_forms.AuthenticationForm()
model = dict(login_form=form)
return render(request, template_path, model)
login.html
{% if form.non_field_errors %}
<div class="alert alert-danger alert-dismissible fade show" role="alert">
<button type="button" class="btn-close" data-bs-dismiss="alert" aria-label="Close"></button>
Login failed. Email and password case-sensitive.
</div>
{% endif %}
<form id="formLogin" action="{% url 'login' %}" method="post" role="form">
<input type="hidden" name="csrfmiddlewaretoken">
<input type="hidden" name="next" value="/bs5" />
<label for="id_username" class="form-label">Email address</label>
<input type="username" class="form-control" id="id_username" name="username" value="{{ form.username.value }}">
<label for="id_password" class="form-label">Password</label>
<input type="password" class="form-control" id="id_password" name="password">
<button class="btn btn-primary btn-lg" type="submit">Log In</button>
</form>
I have also try with
return HttpResponseRedirect('/bs5')
But then it is not showing login error.
Any help would be appreciated.
In case you want to redirect a user who couldn't log in to a different page, one of the ways that you may do it is:
from django.contrib import messages
from django.contrib.auth import authenticate, login
from django.shortcuts import redirect
def login(request, template_path='login.html'):
if request.user.is_authenticated:
redirect('home')
user = authenticate(request, username= request.POST.get('username'), password=request.POST.get('password'))
if user is not None:
next_url = request.POST.get('next') # get your next url
messages.error(request, _('Invalid credentials')) # display login error on the next page
return redirect(next_url)
else:
login(request, user)
# redirect to the successful url that you wish to
For more information on displaying messages in your template, you may consult django's documentation
I am trying to create a login page for my flask web app code shown below:
# Route for handling the login page logic
#app.route('/logins', methods=['GET', 'POST'])
def login():
error = None
if request.method == 'GET':
# Just render the initial form, to get input
return (render_template('login.html'))
if request.method == 'POST':
if request.form['username'] == 'admin' or request.form['password'] == 'P#55w0rd':
return redirect(url_for('main'))
else:
error = 'Invalid Credentials. Please try again.'
return render_template('login.html', error=error)
# Set up the main route
#app.route('/main', methods=['GET', 'POST'])
def main():
if request.method == 'GET':
# Just render the initial form, to get input
return(render_template('main.html'))
This is my HTML login page code
<form id="login" action="/logins" method="POST" class="login100-form validate-form">
<span class="login100-form-logo">
<i class="zmdi zmdi-landscape"></i>
</span>
<span class="login100-form-title p-b-34 p-t-27">
Log in
</span>
<div class="wrap-input100 validate-input" data-validate = "Enter username">
<input class="input100" type="text" id="username" name="username" placeholder="Username" value={{request.form.username}}>
<span class="focus-input100" data-placeholder=""></span>
</div>
<div class="wrap-input100 validate-input" data-validate="Enter password">
<input class="input100" type="password" id="password" name="pass" placeholder="Password" value="{{
request.form.password }}">
<span class="focus-input100" data-placeholder=""></span>
</div>
<div class="container-login100-form-btn">
<button type="submit" class="login100-form-btn">
Login
</button>
</div>
</form>
{% if error %}
<p class="error"><strong>Error:</strong> {{ error }}
{% endif %}
but after clicking on login button
404 Method Not allowed
error is coming. what changes to be done in my code so that it can properly redirect to main.html?
Change 'password' to 'pass' :
if request.form['username'] == 'admin' or request.form['pass'] == 'P#55w0rd':
I'm trying to write a simple app that let users to login, in Django. I've downloaded a pretty bootstrap login template, but I can't hook it up to my Django project. When I click submit, nothing happens, Here's the view:
def login_view2(request):
if request.method == 'POST':
print("POST METHOD")
form = LoginForm(request.POST)
if form.is_valid():
print("FORM VALID")
uname = form.cleaned_data['username']
pword = form.cleaned_data['password']
user = authenticate(username=uname, password=pword)
if user is not None:
if user.is_active:
login(request, user)
return HttpResponseRedirect('/')
else:
print("The account has been disabled!")
else:
print("The username and password were incorrect!")
else:
print("LOGIN FORM SHOWN")
form = LoginForm()
return render(request, 'login2.html', {'form': form})
and here's the form
<form id="login-form" action="login2/" method="post">
{% csrf_token %}
<div class="modal-body">
<div id="div-login-msg">
<div id="icon-login-msg" class="glyphicon glyphicon-chevron-right"></div>
<span id="text-login-msg">Type your username and password.</span>
</div>
<input id="login_username" class="form-control" type="text" placeholder="Username" required>
<input id="login_password" class="form-control" type="password" placeholder="Password" required>
</div>
<div class="modal-footer">
<div>
<input type="submit">Login</input>
</div>
</div>
</form>
Thank you very much in advance!
You haven't given your HTML fields a name attribute, so the browser can't send any data to the server.
Also you need to display errors for when the form is not valid, using {{ form.errors }}.
I'm new to python and CS so this question might be a bit too easy. Thanks for your help I'm getting an error:
Bad Request
The browser (or proxy) sent a request that this server could not understand.
After implementing a new html template and python function:
#app.route("/register", methods=["GET", "POST"])
def register():
"""Register user."""
session.clear()
if request.form["name"] == "" or request.form["password"] == "":
return render_template("apology.html")
elif request.form["password"] != request.form["confirmation"]:
return render_template("apology.html")
hash = pbkdf2_sha256.hash("password")
do.execute("INSERT INTO finance (name, password) VALUES(:name, :password)",
name=request.form.get["name"], hash=hash)
session["user_id"] = rows[0]["id"]
return redirect(url_for("index"))
{% extends "layout.html" %}
{% block title %}
Register
{% endblock %}
{% block main %}
<form action="{{ url_for('register') }}" method="post">
<fieldset>
<div class="form-group">
<input autocomplete="off" autofocus class="form-control" name="username" placeholder="Username" type="text"/>
</div>
<div class="form-group">
<input class="form-control" name="password" placeholder="Password" type="password"/>
</div>
<div class="form-group">
<input class="form-control" name="confirmation" placeholder="Confirm Password" type="password"/>
</div>
<div class="form-group">
<button class="btn btn-default" type="submit">Register</button>
</div>
</fieldset>
</form>
{% endblock %}
First you should check if the request type is 'POST', after that you check all the conditions. Do like below to resolve the issue:
#app.route("/register", methods=["GET", "POST"])
def register():
"""Register user."""
session.clear()
if request.method == 'POST':
if request.form["name"] == "" or request.form["password"] == "":
return render_template("apology.html")
elif request.form["password"] != request.form["confirmation"]:
return render_template("apology.html")
hash = pbkdf2_sha256.hash("password")
do.execute("INSERT INTO finance (name, password) VALUES(:name, :password)",
name=request.form.get["name"], hash=hash)
session["user_id"] = rows[0]["id"]
return redirect(url_for("index"))
else:
// you can render the template to be shown for registration.