request not going through - flask

im creating a login page the code im posting doesnt give any errors if request.method == 'POST' and formLogin.validate():
if formLogin.username_signin == 'admin' and formLogin.password_signin == 'admin':
return redirect(url_for('home'))
this piece of code gets skipped even when i put admin in box boxes(wtforms) here is the code im using:
app = Flask(__name__)
app.secret_key = 'jjjjjjj'
#app.route('/')
def home():
return render_template('home.html')
#app.route('/login/', methods=['GET', 'POST'])
def login():
formLogin = LoginForm(request.form)
error = None
if request.method == 'POST' and formLogin.validate():
if formLogin.username_signin == 'admin' and formLogin.password_signin == 'admin':
return redirect(url_for('home'))
else:
error = 'Please enter right credentials.'
return render_template('login.html', error=error, formLogin=formLogin)
return render_template('login.html', error=error, formLogin=formLogin)
if __name__ == '__main__':
app.debug = True
app.run()
my login.html:
{% extends 'base.html' %}
{% block head %}
<div class='container'>
<div class='row'>
<form method= post action='/login/'>
{{ formLogin.username_signin(class='form-control', placeholder='Username') }}
{{ formLogin.password_signin(class='form-control', placeholder='Password') }}
{{ formLogin.submit_signin(class='btn btn-primary') }}
</form>
<p><strong>Error:</strong>{{ error }}</p>
</div>
</div>
{% endblock %}
Form.py
from wtforms import Form,StringField, PasswordField, TextField, BooleanField, SubmitField, validators
class LoginForm(Form):
username_signin = StringField('SigninU', [validators.Required('please enter name')])
password_signin = PasswordField('signinP', [validators.Required('need password')])
submit_signin = SubmitField('Signin')
Like i said everything renders ok and im not getting a error loading my problem is that when i put 'admin' in both boxes instead of redirect me to the home() function it just skips straight to the else statement.

You have to use .data to access the get_data.
if request.method == 'POST' and formLogin.validate():
if formLogin.username_signin.data == 'admin' and formLogin.password_signin.data == 'admin':
return redirect(url_for('home'))

Related

error messages are not shown in django form. and how to solve this value error?

error messages are not working in Django templates.
after add error code in html template it shows no error message in webapp when fields are empty and press on submit button. html5 error is "novalidate" in template.
ValueError at /signup/
The view blog.views.user_signup didn't return an HttpResponse object. It returned None instead.
forms.py
from django import forms
from django.contrib.auth.forms import UserCreationForm, AuthenticationForm, UsernameField
from django.contrib.auth.models import User
from django.utils.translation import gettext,gettext_lazy as _
class SignUpForm(UserCreationForm):
password1 = forms.CharField(label='Password',widget=forms.PasswordInput(attrs={'class':'form-control'}))
password2 = forms.CharField(label='Confirm Password(again)',widget=forms.PasswordInput(attrs={'class':'form-control'}))
class Meta:
model = User
fields = ['username','first_name','last_name','email']
labels = {'username':'Username','first_name':'First Name','last_name':'Last Name','email':'Email'}
widgets = {'username':forms.TextInput(attrs={'class':'form-control'}),
'first_name':forms.TextInput(attrs={'class':'form-control'}),
'last_name':forms.TextInput(attrs={'class':'form-control'}),
'email':forms.EmailInput(attrs={'class':'form-control'}),}
class LoginForm(AuthenticationForm):
username = UsernameField(widget=forms.TextInput(attrs={'autofocus':True, 'class':'form-control'}))
password = forms.CharField(label=_('password'),strip=False, widget=forms.PasswordInput(attrs={'autocomplete':'current-password','class':'form-control'}))
signup.html
{% extends 'blog/base.html' %}
{% load static %}
{% block content %}
<div class="col-sm-10">
<h3 class="text-white my-5">Signup Page</h3>
<form action="" class="post" novalidate>
{% csrf_token %}
{% for fm in form %}
<div class="form-group">
{{fm.label_tag}} {{fm}} {{fm.errors | striptags}}
</div>
{% endfor %}
<input type="submit" value='Submit' class='btn btn-primary'>
{% if form.non_field_errors %}
{% for error in form.non_field_errors %}
<p> {{error}} </p>
{% endfor %}
{% endif %}
</form>
</div>
{% endblock content %}
views.py
from django.shortcuts import render,HttpResponseRedirect
from django.contrib import messages
# Create your views here.
# home
def home(request):
return render(request, 'blog/home.html')
# about
def about(request):
return render(request, 'blog/about.html')
# contact
def contact(request):
return render(request, 'blog/contact.html')
# Dashboard
def dashboard(request):
return render(request, 'blog/dashboard.html')
# Logout
def user_logout(request):
return HttpResponseRedirect('/')
# Signup
def user_signup(request):
if request.method == 'POST':
form = SignUpForm(request.POST)
if form.is_valid():
messages.success(request, 'Congratulations You have become an Author.')
form.save()
else:
form = SignUpForm()
return render(request, 'blog/signup.html',{'form':form})
# Login
def user_login(request):
form = LoginForm()
return render(request, 'blog/login.html', {'form':form})
You need to handle GET and POST request :
def user_signup(request):
if request.method == 'POST':
form = SignUpForm(request.POST)
if form.is_valid():
messages.success(request, 'Congratulations You have become an Author.')
form.save()
else:
form = SignUpForm()
return render(request, 'blog/signup.html',{'form':form})
Please make sure to use POST method in your html :
<form action="" method="POST" class="post" novalidate>
...
</form>

Django view not sending context data to ReactJS/Axios application

It appears I have come across very strange behavior. I am building a ReactJS+Django 3.0 application. Here is the problem...
I have a <form onSubmit={handleSubmit}> that wraps the form on the frontend.
const handleSubmit = (e) => {
e.preventDefault();
axios.post(paths.login, qs.stringify({
email: emailVal,
password: passwordVal
}));
}
This works perfectly fine in sending data to the Django view! But when I try to then pass context variable through the Django view, it just fails completely. Meaning,
def login(request):
data = {}
'''
Handle Logging in
'''
if request.method == 'POST':
login_form = forms.LoginForm(request.POST)
if login_form.is_valid():
user = login_form.authenticate_user()
#login(request, user)
return redirect('home')
else:
data['errorMessage'] = ''
for field, errors in login_form.errors.items():
for error in errors:
data['errorMessage'] += error
print(data)
return render(request, 'index.html', context=data)
Given this, the data dictionary will be empty at first, but even when the print(data) shows that the data dictionary is populated, the context data that is sent to the index.html file is still empty.
WHY MIGHT THIS BE? I've been stuck on this forever.
I can work around this if I just use form submission instead of axios like this: <form method='POST'> However, I need to use axios. SOS
You can also use the Django messages framework for this, which might be a better option (assuming you are re-rendering the page after POST):
from django.contrib import messages
def login(request):
data = {}
'''
Handle Logging in
'''
if request.method == 'POST':
login_form = forms.LoginForm(request.POST)
if login_form.is_valid():
user = login_form.authenticate_user()
#login(request, user)
return redirect('home')
else:
error_message = ''
for field, errors in login_form.errors.items():
for error in errors:
error_message += error
messages.add_message(request, messages.ERROR, error_message)
return render(request, 'index.html')
Then in your template (this is an example using Bootstrap, but you can modify it to fit your needs):
{% if messages %}
{% for message in messages %}
{% if message.tags == 'error' %}
<div class="alert alert-danger alert-with-icon alert-dismissible fade show" role="alert">
{% else %}
<div class="alert alert-{{ message.tags }} alert-with-icon alert-dismissible fade show" role="alert">
{% endif %}
{{ message|safe }}
<button type="button" class="close" data-dismiss="alert" aria-label="Close">
<span aria-hidden="true">×</span>
</button>
</div>
{% endfor %}
{% endif %}
If you are sending data back as an AJAX JSON response instead:
from django.http import JsonResponse
def login(request):
data = {}
'''
Handle Logging in
'''
if request.method == 'POST':
login_form = forms.LoginForm(request.POST)
if login_form.is_valid():
user = login_form.authenticate_user()
#login(request, user)
return redirect('home')
else:
error_message = ''
for field, errors in login_form.errors.items():
for error in errors:
error_message += error
data['error_message'] = error_message
return JsonResponse(data)
else:
return render(request, 'index.html')
In your Axios code:
const handleSubmit = (e) => {
e.preventDefault();
axios.post(paths.login, qs.stringify({
email: emailVal,
password: passwordVal
}).then((response) => {
//do something with JSON response
}, (error) => {
//do something with JSON response
});
});

How to Fix UnboundLocalError at /signup/ in Django

I Want To Create A User Like Signup or register when i hit submit button i got this error:
UnboundLocalError at /signup/
i want to signup user:
local variable 'usercustom' referenced before assignment
here is my Views.py
def signup(request):
registered = False
if request.method == "POST":
user_form = UserForm(request.POST or None)
custom_form = UserCustom(request.POST or None)
if user_form.is_valid() and custom_form.is_valid():
user = user_form.save(commit=False)
user.save()
custom = custom_form.save(commit=False)
custom.user = user
custom.save()
registered = True
else:
print(user_form.errors,custom_form.errors)
else:
user_form = UserForm()
usercustom = UserCustom()
return render(request,'form.html',{'user_form':user_form,'usercustom':usercustom,'registered':registered})
here is my Form.html
{% extends "base.html" %}
{% block body_block %}
<div class="content-section">
{% if registerd %}
<h1>Thank Your For registering!</h1>
{% else %}
<h1>Register Here</h1>
<h3>Fill out the form</h3>
<form enctype="multipart/form-data" method="POST">
{% csrf_token %}
{{ user_form.as_p }}
{{ usercustom.as_p }}
<input type="submit" value="Register!" class="btn btn-danger">
</form>
{% endif %}
</div>
{% endblock %}
It is because usercustom is not declared when you tried to send POST request. You need to rename custom_form variable to usercustom. I have simplified your code for you.
def signup(request):
registered = False
if request.method == "POST":
user_form = UserForm(request.POST or None)
usercustom = UserCustom(request.POST or None)
if user_form.is_valid() and usercustom.is_valid():
user = user_form.save(commit=False)
user.save()
custom = usercustom.save(commit=False)
custom.user = user
custom.save()
registered = True
else:
print(user_form.errors, usercustom.errors)
else:
user_form = UserForm()
usercustom = UserCustom()
return render(request,'form.html',{'user_form':user_form,'usercustom':usercustom,'registered':registered})

wtforms will not return form.validate() as true [duplicate]

This question already has an answer here:
Form is never valid with WTForms
(1 answer)
Closed 3 years ago.
I'm trying to validate inputs for a contact form loosely following Lalith Polepeddi's tutorial. I have used this tutorial before with slight adjustments, but this time the inputs will not validate no matter what I try.
if form.validate() in my routes.py always returns false. I uploaded the (entire venv to github with only the offending code)https://github.com/1988mazdab2000/wtfwtf.git
forms.py file:
class ContactForm(Form):
name = TextField("Name", [validators.Required("Please enter your name.")])
email = TextField("Email", [validators.Required("Please enter your email address."), validators.Email("Please enter your email address.")])
subject = TextField("Subject", [validators.Required("Please enter a subject.")])
message = TextAreaField("Message", [validators.Required("Please enter a message.")])
submit = SubmitField("Send")
my routes.py file:
from flask import render_template, request, flash
from forms import ContactForm
from flask_mail import Message, Mail
mail = Mail()
#app.route('/')
def home():
return render_template('home.html')
#app.route('/about')
def about():
return render_template('about.html')
#app.route('/contact', methods=['GET', 'POST'])
def contact():
form = ContactForm()
if request.method == 'POST':
if form.validate() == False:
flash('All fields are required.')
return render_template('contact.html', form=form)
else:
msg = Message(form.subject.data, sender='contact#example.com', recipients=['your_email#example.com'])
msg.body = """
From: %s <%s>
%s
""" % (form.name.data, form.email.data, form.message.data)
mail.send(msg)
return render_template('contact.html', success=True)
elif request.method == 'GET':
return render_template('contact.html', form=form)
any help with this would be greatly appreciated. I have used identical code to do this in the last three months and I'm stuck.
I've tried using different validators and started with a fresh install of raspbian on two different Pis.
I'd like for the form validators to work properly.
As #VillageMonkey said, use validate_on_submit. More can be found in official documentation.
Here is an example of using form validation using Flask-WTF. In this example, the login form requires a valid email address and a password with at least 6 and at most 35 characters long.
app.py:
from flask import render_template, url_for, request, redirect, flash, Flask
from forms import LoginForm
app = Flask(__name__)
app.secret_key = 'secret key'
#app.route("/login", methods=['GET', 'POST'])
def login():
form = LoginForm()
if request.method == 'POST':
if form.validate_on_submit() == False:
flash('Form validation failed')
return render_template('login.html', form=form)
user_email = form.email.data
user_password = form.password.data
if user_email and user_password:
return "{} - {}".format(user_email, user_password)
return render_template('login.html', form=form)
if __name__ == '__main__':
app.run(debug=True)
forms.py:
from flask_wtf import FlaskForm
from wtforms import StringField, PasswordField, SubmitField, BooleanField
from wtforms.validators import DataRequired, Length, Email, EqualTo
class LoginForm(FlaskForm):
email = StringField('Email', validators=[DataRequired(), Email()])
password = PasswordField('Password', validators=[DataRequired(), Length(min=6, max=35)])
submit = SubmitField('Login')
login.html:
<!DOCTYPE html>
<html>
<head>
<title>Login</title>
</head>
<body>
{% with messages = get_flashed_messages() %}
{% if messages %}
<ul class=flashes>
{% for message in messages %}
<li>{{ message }}</li>
{% endfor %}
</ul>
{% endif %}
{% endwith %}
<form method="POST" action="">
{{ form.csrf_token }}
<div>
{{ form.email.label }} {{ form.email }}
{% if form.email.errors %}
<ul style="color: red;">
{% for error in form.email.errors %}
<li>{{ error }}</li>
{% endfor %}
</ul>
{% endif %}
</div>
<div>
{{ form.password.label }} {{ form.password }}
{% if form.password.errors %}
<ul style="color: red;">
{% for error in form.password.errors %}
<li>{{ error }}</li>
{% endfor %}
</ul>
{% endif %}
</div>
<div>
{{ form.submit }}
</div>
</form>
</body>
</html>
Directory structure:
.
├── app.py
├── forms.py
└── templates
└── login.html
requirements.txt:
Click==7.0
Flask==1.0.2
Flask-WTF==0.14.2
itsdangerous==1.1.0
Jinja2==2.10
MarkupSafe==1.1.1
Werkzeug==0.15.0
WTForms==2.2.1
Output:
Get request of login route:
Post request of login route (failed validation):
Post request of login route (after successful validation):
In the template use {{ form.hidden_tag() }} for csrf protection.
<form action="{{ url_for('contact') }}" method="post">
{{ form.hidden_tag() }}
</form>

how to edit the user profile

Hi guys I am new to Django.
I wants that when I login to my account there is a edit button which shows me a form of some fields which I can edit.
I am confused how the data is saved to the same user profile.
So can anybody tell me how is that possible.Can show me it with one example
With my profile.html I can see my profile and on click on edit button I can edit my profile
{% extends 'base.html' %}
{% block content %}
<p>User_id: {{ drinker.user_id }}
<p>Name: {{ drinker.name }}</p>
<p>Birthday: {{ drinker.birthday }}</p>
<p>first_name: {{ user.first_name }}</p>
<p>Users: {{ user.username }}</p>
<p>Edit Profile
{% endblock %}
Edit function
def Edit(request):
if not request.user.is_authenticated():
return HttpResponseRedirect('/login/')
drinker = request.user.get_profile()
context = {'drinker':drinker}
return render_to_response('edit.html', context, context_instance=RequestContext(request))
**Edit.html**
{% extends "base.html" %}
{% block extrahead %}
<script src="//ajax.googleapis.com/ajax/libs/jquery/1.8.0/jquery.min.js" type="text/javascript"></script>
<script src="//ajax.googleapis.com/ajax/libs/jqueryui/1.8.23/jquery-ui.min.js" type="text/javascript"></script>
<script>
$(function() {
$( "#birth" ).datepicker();
});
</script>
{% endblock %}
{% block content %}
<form action="/edit1/" method="post">
{% csrf_token %}
<div class="register_div">
<p><label for="name">Name:</label></p>
<p><input type="text" value="{{ drinker.name }}"></p>
</div>
<div class="register_div">
<p><label for="birthday">Birthday: {{ drinker.birthday }} </label></p>
<p>Choose new date of birth</p>
<p><input type="text" value="" id="birth"></p>
</div>
<p><input type="submit" value="submit" /></p>
</form>
{% endblock %}
On edit1 edit request function works
def EditRequest(request):
#if request.method == 'POST':
#form = UserProfileForm(request.POST, instance=user)
#if request.user.is_authenticated():
#return render_to_response('hgdhg')
if request.method == 'POST':
form = EditForm(request.POST)
if form.is_valid():
user=User.objects.create_user(usere_id=form.cleaned_data['user_id'])
#user.save()
drinker=user.get_profile()
drinker.name=form.cleaned_data['name']
drinker.birthday=form.cleaned_data['birthday']
drinker.save()
return HttpResponseRedirect('/profile/')
else:
return HttpResponseRedirect('/f/')
else:
return render_to_response('f')#,{'form':form} , context_instance=RequestContext(request))
this editrequest doesn't work ?
Here are the steps you need to execute to edit a user's profile:
Find out which user is logged in (read up on user authentication)
Check if the user has a profile or not; use the normal django query mechanism for that.
If the user has a profile; populate a ModelForm with the instance of the profile (see this page in the manual)
Display the form to the end user just like any other form.
When the user submits changes, do the normal form validation and save the object to the database.
Here is some code that does steps 1-4:
from django.shortcuts import render, redirect
from django.contrib.auth.decorators import login_required
from myapp.models import UserProfile
from myapp.forms import UserProfileForm
#login_required
def edit_profile(request):
try:
user_profile = UserProfile.objects.get(user=request.user)
except UserProfile.DoesNotExist:
# this user has no profile
return redirect('/error')
user_profile_form = UserProfileForm(instance=user_profile)
return render(request,'profile_edit.html',{'form':user_profile_form})
The UserProfileForm class:
from django import forms
from myapp.models import UserProfile
class UserProfileForm(forms.ModelForm):
class Meta:
model = UserProfile
pass the instance of user along your model form
user = User.objects.get(user_name = username)
form = Registrationform(instance=user)
and render this form to your template
Example i did before:
#login_required
def lexuseditform(request,userpk):
if Adult.objects.filter(user=request.user).exists():
adult = Adult.objects.get(user=request.user) # load existing Adult
else:
adult = Adult(user=request.user) # create new Adult
if request.method == 'POST': # If the form has been submitted...
form = AdultForm(request.POST,instance=adult) # A form bound to the POST data
if form.is_valid(): # All validation rules pass
form.save()
redirect_url = reverse('lexusedited',kwargs={'userpk': request.user.pk})
return HttpResponseRedirect(redirect_url) # Redirect after POST
else:
form = AdultForm(instance=adult) # An unbound form
return render(request,'lexus/lexuseditform.html', {'form': form})
#login_required
def lexusedited(request,userpk):
return render(request,'lexus/lexusedited.html')
Hope this helps...