I'm making a web page with python. My login render function looks something like this:
#app.route('/Login', methods = ['GET', 'POST'])
def Login():
if request.method == 'POST':
username = request.form.get('loginUsername')
password = request.form.get('loginPassword')
if //username password doesn't exist:
flash('No such username and password', category='error')
else: //username password does exist:
flash('Successful Login!', category = 'success')
return render_template('home.html')
else:
return render_template('Login.html')
My current google link would be something like:
If I sign in, I want my link to change to:
But it stays at /Login. How do I get the link to change? This is causing me a lot of trouble.
This is my Login.html
{% extends "layout.html" %}
{% block content %}
<div class="jumbotron">
<h1>Login</h1>
</div>
<div class="container">
<form method="POST">
<!-- Username input -->
<div class="form-outline mb-4">
<p>Username: </p><input type="text" id="loginUsername" class="form-control" name="loginUsername" placeholder="Username" />
<label class="form-label" for="floatingInput"></label>
</div>
<!-- Password input -->
<div class="form-outline mb-4">
<p>Password: </p><input type="password" id="loginPassword" class="form-control" name="loginPassword" placeholder="Password" />
<label class="form-label" for="floatingInput"></label>
</div>
<br />
<!-- Submit button -->
<button type="submit" class="btn btn-primary mb-4">Sign in</button>
</form>
</div>
{% endblock %}
Related
I have this code which runs in the navbar, it's meant to implement a login/registration form but without leaving the home page, its a toggler with a data-target="#login-form":
<i class="icon-user"></i> Sign In
How do I change the #app.route so that it targets the login-form that's implemented within the home page? Python code used:
#app.route('/')
def home():
# Check if user is loggedin
if 'loggedin' in session:
# User is loggedin show them the home page
return render_template('home.html', username=session['username'])
# User is not loggedin redirect to login page
return redirect(url_for('home'))
#app.route('/login/', methods=['GET', 'POST'])
def login():
cursor = conn.cursor(cursor_factory=psycopg2.extras.DictCursor)
# Check if "username" and "password" POST requests exist (user submitted form)
if request.method == 'POST' and 'username' in request.form and 'password' in request.form:
username = request.form['username']
password = request.form['password']
print(password)
# Check if account exists using MySQL
cursor.execute('SELECT * FROM users WHERE username = %s', (username,))
# Fetch one record and return result
account = cursor.fetchone()
if account:
password_rs = account['password']
print(password_rs)
# If account exists in users table in out database
if check_password_hash(password_rs, password):
# Create session data, we can access this data in other routes
session['loggedin'] = True
session['id'] = account['id']
session['username'] = account['username']
# Redirect to home page
return redirect(url_for('home'))
else:
# Account doesnt exist or username/password incorrect
flash('Incorrect username/password')
else:
# Account doesnt exist or username/password incorrect
flash('Incorrect username/password')
return render_template('home.html')
<div class="modal fade c-content-login-form" id="login-form" role="dialog">
<div class="modal-dialog">
<div class="modal-content c-square">
<div class="modal-header c-no-border">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button>
</div>
<div class="modal-body">
<h3 class="c-font-24 c-font-sbold">Good Afternoon!</h3>
<p>Let's make today a great day!</p>
<form>
<div class="form-group" method="post">
<label for="username" class="hide">Username</label>
<input type="username" class="form-control input-lg c-square" name="username" id="username" placeholder="Username">
</div>
<div class="form-group">
<label for="password" class="hide">Password</label>
<input type="password" class="form-control input-lg c-square" name="password" id="password" placeholder="Password">
</div>
<div class="form-group">
<div class="c-checkbox">
<input type="checkbox" id="login-rememberme" class="c-check">
<label for="login-rememberme" class="c-font-thin c-font-17">
<span></span>
<span class="check"></span>
<span class="box"></span>
Remember Me
</label>
</div>
</div>
<div class="form-group">
<input type="submit" value="Login" class="form-control btn btn-success btn c-theme-btn btn-md c-btn-uppercase c-btn-bold c-btn-square c-btn-login" name="">Login</input>
Forgot Your Password ?
</div>
<div class="clearfix">
<div class="c-content-divider c-divider-sm c-icon-bg c-bg-grey c-margin-b-20">
<span>or signup with</span>
</div>
<ul class="c-content-list-adjusted">
<li>
<a class="btn btn-block c-btn-square btn-social btn-twitter">
<i class="fa fa-twitter"></i>
Twitter
</a>
</li>
<li>
<a class="btn btn-block c-btn-square btn-social btn-facebook">
<i class="fa fa-facebook"></i>
Facebook
</a>
</li>
<li>
<a class="btn btn-block c-btn-square btn-social btn-google">
<i class="fa fa-google"></i>
Google
</a>
</li>
</ul>
</div>
</form>
I understand linking specific pages but what if it isn't exactly a page you want to link
You already have the navbar and the modal form there. Now you need some javascript that makes the link toggle the modal box visibility.
And also some javascript that intercepts the form submission, prevents it from loading another page, grabs the form data, and posts it to the flask endpoint. Please lookup javascript fetch() post data.
Edit: please check Matiiss comment below. It seems Bootstrap already provides the js code you need.
This is my approach to have a login forma and home page on the same route (could probably use two templates but this works too):
The main file:
from flask import Flask, redirect, url_for, request, render_template
from wtforms import StringField, SubmitField
from wtforms.validators import InputRequired
from flask_wtf import FlaskForm
app = Flask(__name__)
app.config['SECRET_KEY'] = 'your_key_'
user_logged_in = False
class LoginForm(FlaskForm):
username = StringField('Username', validators=[InputRequired()])
password = StringField('Password', validators=[InputRequired()])
submit = SubmitField('Login')
#app.route('/', methods=['GET', 'POST'])
def home():
global user_logged_in
if user_logged_in:
return render_template('home.html', logged_in=user_logged_in)
else:
form = LoginForm()
if form.validate_on_submit():
user_logged_in = True
return redirect(url_for('home'))
return render_template('home.html', logged_in=user_logged_in, form=form)
if __name__ == '__main__':
app.run(debug=True)
Obviously you need to use your user login validation, this is just to for testing (logged_in variable)
(Also I spent like 20 min trying to figure out why I couldn't submit form and it was because I didn't include {{ form.hidden_tag() }} in my form)
The template (super simple):
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Home</title>
</head>
<body>
{% if logged_in %}
<h1>You are logged in</h1>
<p>{{ logged_in }}</p>
{% else %}
<form action="{{ url_for('home') }}" method="POST">
{{ form.hidden_tag() }}
<div>
{{ form.username.label }}
{{ form.username }}
</div>
<div>
{{ form.password.label }}
{{ form.password }}
</div>
{{ form.submit }}
</form>
<p>{{ logged_in }}</p>
{% endif %}
</body>
</html>
Basically You check if user is logged in and then just simply pass that variable to the template and there is a huge if statement, I should tho point out that using a modal in this case is not the best idea, you have to just show completely only the login part otherwise someone may open DevTools and just delete that modal and gain accesss to the home page
If You have any questions, ask
I'm trying to display an error message for a certain error that user makes while registering, for now I've only covered an error regarding password and conf_passowrd not matching, but only that scenario works, whenever there is an error regarding, for example, too short password entered, it still displays the error regarding password mismatch.
What I've tried so far:
view.py:
from django.shortcuts import render, redirect
from django.contrib import messages
from django.contrib.auth.forms import UserCreationForm
def indexsignup(request):
form = UserCreationForm()
if request.method == 'POST':
regForm = UserCreationForm(request.POST)
if regForm.is_valid():
regForm.save()
return redirect('login')
else:
for msg in form.error_messages:
if len('password1') < 6:
messages.error(request, f"PAss short")
print(msg)
else:
messages.error(request, f"Two passwords don't match.")
print(msg)
return render(request, 'registration/register.html', {'form':form})
register.html:
{% load static %}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Forum - SignUp</title>
<link rel="stylesheet" href="{% static 'signup/style.css' %}">
</head>
<body>
<div class="signin-box">
<h1> Sign Up</h1>
<form method="post" action="">
{% csrf_token %}
<div class="textbox">
<input type="text" name="username" placeholder="Username" maxlength="10" autocapitalize="none"
autocomplete="username" autofocus="" required="" id="id_username">
</div>
<div class="textbox">
<input type="password" name="password1" placeholder="Password" autocomplete="new-password" required=""
id="id_password1">
<script type="text/javascript">
function reveal() {
if (document.getElementById('box').checked) { document.getElementById("id_password1").type = 'text'; }
else
document.getElementById("id_password1").type = 'password';
}
</script>
<div class="check">
<input title="Reveal password" type="checkbox" id="box" onclick="reveal()">
</div>
</div>
<div class="textbox">
<input type="password" name="password2" placeholder="Confirm Password" autocomplete="new-password"
required="" id="id_password2">
<script type="text/javascript">
function reveal2() {
if (document.getElementById('box').checked) { document.getElementById("id_password2").type = 'text'; }
else
document.getElementById("id_password2").type = 'password';
}
</script>
<div class="check">
<input title="Reveal password" type="checkbox" id="box" onclick="reveal2()">
</div>
</div>
{% if messages %}
{% for message in messages %}
<div class="help">
<p><span style="font-size: 20px">⚠</span> {{message}}</p>
</div>
{% endfor %}
{% endif %}
<input class="btn" type="submit" style="opacity: 1 !important;" value="Sign Up">
</form>
</div>
</body>
Best thing would be to add ValidationErrorin django form. You need to override clean method for password1 field (or any field where you want to add customization). Add the below function in UserCreationForm class.
def clean_password1(self):
entered_password = self.cleaned_data['password1']
if len(entered_password) <= 6:
raise forms.ValidationError("Password should include more than 6 characters")
return entered_password
You will be able to access these form errors in template using {{ form.errors }}. You can further check this on how to render form errors in template
Reference: https://docs.djangoproject.com/en/3.2/ref/forms/validation/#cleaning-a-specific-field-attribute
I am trying to make a website's contact page using django where client enters data and it gets submitted in database, the form gets submitted the project runs without errors and yet no data gets added in the db.
Here's my views.py file
from datetime import datetime
from firstapp.models import Contact
# Create your views here.
def index(request):
return render(request,'index.html',)
def apply(request):
return render(request,'apply.html')
def about(request):
return render(request,'about.html')
def socials(request):
return render(request,'social.html')
def contact(request):
if request.method == "POST":
name = request.POST.get("name")
email = request.POST.get("email")
subject = request.POST.get("subject")
message= request.POST.get("message")
contact=Contact(name=name,email=email,subject=subject,message=message,date=datetime.today())
contact.save
return render(request,'contact.html')
here is my contact.html
{% block title %}Contact {% endblock title %}
{% block body %}
<h2 align="center">CONTACT US </h2>
<div class="container-md">
<form method="POST" action="/contact/">
{% csrf_token %}
<div class="form-group">
<label for="exampleFormControlInput1">Name</label>
<input type="text" class="form-control" id="exampleFormControlInput1" name="name" placeholder="John Smith">
</div>
<div class="form-group">
<label for="exampleFormControlInput1">Email address</label>
<input type="email" class="form-control" id="exampleFormControlInput1" name="email" placeholder="name#example.com">
</div>
<div class="form-group">
<label for="exampleFormControlInput1">Subject</label>
<input type="text" class="form-control" id="exampleFormControlInput1" name="subject" placeholder="Business
| Suggestions | Query | Complaint | Other">
</div>
<div class="form-group">
<label for="exampleFormControlTextarea1">Message</label>
<textarea class="form-control" name="message" id="exampleFormControlTextarea1" rows="3"></textarea>
</div>
<button type="submit" class="btn btn-primary">Submit</button>
</form>
</div>
{% endblock body%}
And here's my models.py
from django.db import models
# Create your models here.
class Contact(models.Model):
name = models.CharField(max_length=50)
email =models.EmailField(max_length=254)
subject=models.CharField(max_length=10)
message=models.CharField(max_length=1000)
date=models.DateField()
As I wrote at the comments before, you have forgotten to type brackets following the save: contact.save() instead of contact.save.
It would be better and more beautiful if you do it like this:
def contact(request):
if request.method == "POST":
Contact.objects.create(**request.POST)
return render(request,'contact.html')
I would like to display the login logs (who connected and when) after the login screen, on the home page for example (so the user sees when he logged in last time) and store the data in a file if possible (that way we see who logged in and when).
I have a simple authentification with Flask/MySQL :
#app.route('/login', methods=['GET', 'POST'])
#app.route('/', methods=['GET','POST'])
def login():
# Open database connection
db = MySQLdb.connect("localhost","root","#{elma3alem}","FilesList")
# prepare a cursor object using cursor() method
cursor = db.cursor()
# execute SQL query using execute() method.
cursor.execute("SELECT userName, password FROM User")
# Fetch a single row using fetchone() method.
data = cursor.fetchall()
error = None
if request.method == 'POST':
for row in data:
if request.form['username'] != row[0] or request.form['password'] != row[1]:
error = 'Invalid Credentials. Please try again.'
else:
return render_template('files_list.html')
return render_template('login.html', error=error)
# disconnect from server
db.close()
And this is my login page :
<link rel="stylesheet" href="/static/style.css" type="text/css">
{% block body %}
{% if session['logged_in'] %}
<p>You're logged in already!</p>
{% else %}
<form action="/login" method="POST" name="login">
<div class="login">
<div class="login-screen">
<div class="app-title">
<h1>Login</h1>
</div>
<div class="login-form">
<div class="control-group">
<input type="text" class="login-field" value="" placeholder="username" name="username">
<label class="login-field-icon fui-user" for="login-name"></label>
</div>
<div class="control-group">
<input type="password" class="login-field" value="" placeholder="password" name="password">
<label class="login-field-icon fui-lock" for="login-pass"></label>
</div>
<input type="submit" value="Log in" class="btn btn-primary btn-large btn-block" >
<br>
</div>
</div>
</div>
</form>
{% endif %}
{% endblock %}
I guess I need to use stuff like login manager,login_required etc...but I don't know how to start.
Thanks beforehand.
I am trying to get the value of a textbox from views.py but its not working for some reason.
Below is my code
base.html
<form method="POST" role="form" >
{% csrf_token %}
<div class="tab-content">
<div class="tab-pane active" role="tabpanel" id="step1">
<div class="mobile-grids">
<div class="mobile-left text-center">
<img src="{% static 'images/mobile.png' %}" alt="" />
</div>
<div class="mobile-right">
<h4>Enter your mobile number</h4>
<!-- <label>+91</label><input type="text" name="mobile_number" class="mobile-text" value="asdfasd" onfocus="this.value = '';" onblur="if (this.value == '') {this.value = '';}" required=""> -->
<label>+91</label><input type="text" name="mobile_number" class="mobile-text" value="" >
</div>
</div>
<ul class="list-inline pull-right">
<li><button type="button" class="mob-btn btn btn-primary btn-info-full" data-dismiss="modal">Finish</button></li>
</ul>
</div>
<div class="clearfix"></div>
</div>
</form>
views.py
def home(request):
mobile_number = request.POST.get('mobile_number')
print(mobile_number)
return render(request,"home.html", {'mobile_number': mobile_number})
I am getting None when I try to get the value of textbox mobile_number.
How can I get the correct value?
You are missing a submit-button (<input type="submit" value="submit"/>) from the from.
To see the value on the form after submitting it, change value=""on the mobile_number -row, to value="{{ mobile_number }}".
My solution
1. You have to set action in form field as your functon in view.py
<form class="forms-sample" name="form" action="{% url "update_size" %}" method="post">
You have make button type as submit.
<button type="Submit" value="Submit" name="Submit" class="btn btn-primary">
url.py
path('updatesize/', views.updatesize, name='update_size')
View.py
def updatesize(request):
if (request.method == 'POST'):
temp = request.POST.get('size_name')
print("==================form================",temp)
return redirect("/collection.html")