Passing session data to templates without customizing views - python

I'm working on adding subscriptions using django-registration. Right now, I'm trying to create a Paypal form on the registration_complete page.
I have created a session variable as follows:
def user_created(sender, user, request, **kwargs):
form = RegistrationFormEx(data=request.POST)
new_user = User.objects.get(username=request.POST['username'])
digest=hmac.new(str(request.POST['username'])+str(request.POST['password1']), str(request.POST['password1']),hashlib.sha1).hexdigest()
new_profile = UserProfile(user=new_user,api_key=digest)
new_profile.save()
#now add other fields including password hash as well
uid = new_profile.id
#Add username to session to pass it via Paypal later
request.session['username']=request.POST['username']
merchant_profile = MerchantProfile(user_id=uid,
create_time=datetime.datetime.now(),
modified_time=datetime.datetime.now(),
payment_card_id=uid,
current_state=1,
name=request.POST['name'],
)
merchant_profile.save()
return new_user
user_registered.connect(user_created)
My template for the Paypal form is is as follows:
{% extends "base.html" %}
{% load i18n %}
{% block content %}
<p>
{% trans "You are now registered. Activation email sent." %}
<form action="https://www.sandbox.paypal.com/cgi-bin/webscr" method="post">
<input type="hidden" name="cmd" value="_xclick">
<input type="hidden" name="business" value="sumit_1349250468_per#sample.com">
<input type="hidden" name="item_name" value="registration charge {{ request.session.username }}">
<input type="hidden" name="item_number" value="1">
<input type="hidden" name="amount" value="9.00">
<input type="hidden" name="no_shipping" value="0">
<input type="hidden" name="no_note" value="1">
<input type="hidden" name="currency_code" value="USD">
<input type="hidden" name="lc" value="AU">
<input type="hidden" name="bn" value="PP-BuyNowBF">
<input type="image" src="https://www.paypal.com/en_AU/i/btn/btn_buynow_LG.gif" border="0" name="submit" alt="PayPal - The safer, easier way to pay online.">
<img alt="" border="0" src="https://www.paypal.com/en_AU/i/scr/pixel.gif" width="1" height="1">
<input type="hidden" name="return" value="http://url/payment_result?response=success">
<input type="hidden" name="cancel_return" value="http://url/sorry">
</form>
</p>
{% endblock %}
Without changing any views, how can I print the value for request.session.username in this template?

In settings.py, TEMPLATE_CONTEXT_PROCESSORS should include django.core.context_processors.request - This makes the request variable available to your templates.
Although, a word of warning: When the user activates his email and signs in after returning, the session variable will probably have changed.

Related

Password change field reset password django

I created a password reset system through email using django, but when I am at the password page, if I enter the password and confirmation right, it doesn't do anything just reloads the page and seems to throw in error in form.errors, but it shows this field is required (error) even though I filled it out.
In addition, how do you make it so only one email can be assigned to a user. So when registering or changing your info, the same email can't be used with two accounts.
Here is the code to my password reset page:
{% extends 'base.html' %}
{% block head %}
<link href="\static\accounts\css\forms.css" rel="stylesheet">
<script src="\static\registration\js\emailvariable.js"></script>
{% endblock %}
{% block body %}
{% if validlink %}
<h3 style="text-align: center">Change password</h3>
<form id="login-form" method="post">
{% csrf_token %}
<input placeholder="Password" id="id_password" name="password"
type="password" class="form-control">
<input placeholder="Confirm Password" id="id_password2" name="password2"
type="password" class="form-control">
<div style="text-align:center;">
<button type="submit" class="btn btn-outline-dark centerbutton">Change password</button>
</div>
{% if form.errors %}
<p class=" label label-danger">
<div style="text-align: center">
{{ error | escape }}
</div>
</p>
{% endif %}
</form>
{% else %}
<p>
The password reset link was invalid, possibly because it has already been used.
Please request a new password reset.
</p>
{% endif %}
{% endblock %}
I am not sure about your first question, but I can answer the 2nd.
class SignUpForm(UserCreationForm):
def clean_email(self):
email = self.cleaned_data.get('email')
username = self.cleaned_data.get('username')
if email and User.objects.filter(email=email).exclude(username=username).exists():
raise forms.ValidationError(u'Email addresses must be unique.')
return email
Put something like that in the forms.py where you have the registration form.
for the email portion of your question:
views.py
email = self.cleaned_data.get('email')
foo = User.objects.filter(email=email)
if foo:
return error
else:
***carry forth with saving the new user***
the 'if foo' will see if a user exists in the db with the email address given. If so, return error. If not carry forth with code.
I solved the form problem.
You need to change:
<input placeholder="Password" id="id_password" name="password" type="password" class="form-control">
<input placeholder="Confirm Password" id="id_password2" name="password2" type="password" class="form-control">
To this:
<input placeholder="Password" name="new_password1" required id="id_new_password1" type="password" class="form-control">
<input placeholder="Confirm Password" name="new_password2" required id="id_new_password2"
type="password" class="form-control">
What is happening is that your name entries are wrong, which causes the form to fail validation in general in the default password reset view and get returned with a generic error.
Just swap those out and the form should work fine.

How to fill inputs when editing an article in flask

I have a list of articles.
After I press Edit, I am redirected to another page containing in the url the id of the article that wants to be edited.
Edit
This is where I am redirected:
And I want the inputs to be filled with the title and the body text of the respective article.
This is my backend function:
#app.route('/edit_article/<string:id>', methods=['POST', 'GET'])
def edit_article(id):
conn = mysql.connect()
cursor = conn.cursor()
result = cursor.execute("SELECT * from articles where id=%s", [id])
data = cursor.fetchone()
if result < 0:
flash("Article does not exist!")
cursor.close()
conn.close()
return render_template("edit_article.html", data=data)
How can I use data to fill those inputs? Please help. Thank you.
I will put also the edit_article.html
{% extends 'layout.html' %}
{% block body %}
<div class="container">
<div class="jumbotron">
<h1>Bucket List App</h1>
<form class="form-addArticle">
<label for="inputTitle" class="sr-only">Title</label>
<input type="name" name="inputTitle" id="inputTitle" class="form-control" placeholder="Title" required autofocus>
<label for="inputBody" class="sr-only">Body</label>
<input type="text" name="inputBody" id="inputBody" class="form-control" placeholder="Body" required autofocus>
<button id="btnEditArticle" class="btn btn-lg btn-primary" type="button">Update article</button>
</form>
<p class="text-center" style="color:red" id="message"></p>
</div>
</div>
{% endblock %}
You can just need to add value="{{ ... }}" to your inputs:
<input type="name" value="{{ data[0] }}" name="inputTitle" id="inputTitle" class="form-control" placeholder="Title" required autofocus>
<input type="text" value="{{ data[1] }}" name="inputBody" id="inputBody" class="form-control" placeholder="Body" required autofocus>
But it's recommended to name the values:
name, text = cursor.fetchone()
return render_template("edit_article.html", name=name, text=text)
and then
<input type="name" value="{{ name }}" name="inputTitle" id="inputTitle" class="form-control" placeholder="Title" required autofocus>
<input type="text" value="{{ text }}" name="inputBody" id="inputBody" class="form-control" placeholder="Body" required autofocus>
But I'd personally recommend WTForms module instead of rendering forms manually - it can for example help to validate your inputs properly.

How to get the latest ID from different class in Django

I saw all the conversations about this issue, but I can't solve it. I am new in this Python-Django programming so if anyone can help me? :)
This is my views.py:
class HistoryProjectCreate(CreateView):
template_name = 'layout/create_proj_history.html'
model = ProjectHistory
project = Project.objects.latest('id')
user = User.id
fields = ['user', 'project', 'user_start_date']
success_url = reverse_lazy('git_project:index')
Var project has to return latest project ID from database, and I have to use it ID in my html form:
<form class="form-horizontal" action="" method="post" enctype="multipart/form-data">
{% csrf_token %}
<label for="user"></label>
<input id="user" type="text" name="user" value="{{ user.id }}" ><br>
<label for="project">Project title: </label>
<input id="project" type="text" name="project" value="{{ project.id }}" ><br>
<!--Here - "project.id" I need latest project ID-->
<label for="user_start_date">Start date: </label>
<input id="user_start_date" type="date" name="user_start_date" value="{{ projectHistory.user_start_date }}" ><br>
<div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<button type="submit" class="btn btn-success">Submit</button>
</div>
</div>
</form>
I am not sure if project = Project.objects.latest('id') is correct statement for getting the latest ID from Project table.
If you want the last Id of project, you need to order by id, and use last() function available on queryset
project = Project.objects.order_by('id').last()
Order_by doc
Last function doc

Submit without refresh - Django

i have a "follow" button on my web-site just like in Twitter. But this button is html-only without any js. I know nothing about js/jquery/ajax. Can anyone help me, what sholud i do to submit this form without page refresh? Thank you.
template 'event.html':
{% if user in event.users.all %}
<form action="/event/{{ event.id }}/" method="GET">
{% csrf_token %}
<input type="hidden" value="{{ event.id }}" name="remove">
<input type="submit" class="btn btn-warning btn-block" value="{% trans "Remove from My Events"%}">
</form>
{% else %}
<form action="/event/{{ event.id }}/" method="GET">
{% csrf_token %}
<input type="hidden" value="{{ event.id }}" name="add">
<input type="submit" class="btn btn-primary btn-block" value="{% trans "Add to My Events"%}">
</form>
{% endif %}
views.py:
def show_event(request, event_id):
event = get_object_or_404(Event, id=event_id)
user = request.user
if request.GET.get('add'):
event.users.add(user)
event.save()
if request.GET.get('remove'):
event.users.remove(user)
event.save()
return render(request, 'events/event.html', {'event':event, 'user':user}
First learn Javascript and Jquery and Ajax to understand more clearly.
http://www.tutorialspoint.com/jquery/
http://www.w3schools.com/jquery/
template 'event.html':
{% if user in event.users.all %}
<form action="/event/{{ event.id }}/" method="GET" id="event">
{% csrf_token %}
<input type="hidden" value="{{ event.id }}" name="remove">
<input type="submit" class="btn btn-warning btn-block" value="{% trans "Remove from My Events"%}">
</form>
{% else %}
<form action="/event/{{ event.id }}/" method="GET">
{% csrf_token %}
<input type="hidden" value="{{ event.id }}" name="add">
<input type="submit" class="btn btn-primary btn-block" value="{% trans "Add to My Events"%}">
</form>
{% endif %}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.0.0-beta1/jquery.min.js"></script>
<script>
$('#event').submit(function(e){
e.preventDefault();
url = $(this).attr('action') # to get url
data = $(this).serialize(); # for sending form data
$.post(url, data, function(response){
# do whatever you want with response(data)
})
})
</script>
It is impossible, Python is a server side language and if you want to process data, you need send the information to the server.
The first time that i did this, i saw this video in YouTube: https://www.youtube.com/watch?v=KgnPSmrQrXI

Django custom form rendering

When i put { form } in some template it renders this:
<tr><th></th><td><input type="text" name="login" maxlength="10" /></td></tr>
<tr><th></th><td><input type="text" name="email" /></td></tr>
<tr><th></th><td><input type="text" name="password" maxlength="10" /></td></tr>
but what if I do not need tr,th,td,p tags? this is what I want.
<input type="text" name="login" placeholder="Имя пользователя"/>
<input type="email" name="email" placeholder="E-mail"/>
<input type="password" name="password" placeholder="Пароль"/>
What you're currently seeing is the output of form.as_table, which gives you the form rendered as tr elements that you insert into a set of tags. You'll want to check out Customizing the form template in the django docs to make them do exactly what you want them to do. That link walk you through it with examples.
To just get the input widgets, iterate through the form and only insert the field itself:
<form action="" method="get">
{% for field in form %}
{{ field }}
{% endfor %}
</form>

Categories

Resources