Django get user timezone in template - python

I'm saving date in UTC. I wan't to change that date to automatic user timezone.
my settings
USE_TZ = True
my template
{% for sale in sales %}
date : {{sale.date}}
{% endfor %}
I tried django-tz-detect
https://github.com/adamcharnock/django-tz-detect
but I can't implement that correctly.
Please suggest a good way to solve this issue.

I got a solution from here
I created a view function
#login_required
#ajax_required
#require_GET
def set_user_timezone(request):
timezone = request.GET.get('timezone')
request.session["set_user_timezone"] = timezone
response_data = {}
response_data['status'] = 'true'
response_data['message'] = 'user timezone set successfully.'
return HttpResponse(json.dumps(response_data), mimetype='application/javascript')
context
if "set_user_timezone" in request.session:
user_session_ok = True
user_time_zone = request.session['set_user_timezone']
else:
user_session_ok = False
user_time_zone = "Asia/Kolkata"
in my base template
{% if not user_session_ok %}
<script type="text/javascript" src="{% static 'js/jstz.js' %}"></script>
<script>
$(document).ready(function(){
var timezone = jstz.determine();
var timezone_name = timezone.name();
$.ajax({
url : '/set-user-timezone/',
action : "GET",
data : {
timezone : timezone_name
},
success : function(data){
},
error : function(data){
}
})
});
</script>
{% endif %}
my sales template
{% for sale in sales %}
{% load tz %}
date : {{ sale.sale_date|timezone:user_time_zone }}
{% endfor %}
I don't know this is the correct method. but this solution works for me.

Related

Getting None value in views.py from Ajax

I am trying to get the id of a model object of django from the template using ajax. But I cannot get the exact value of data in the views.py.I am getting a None value for id in views. Where I have done wrong? Here is my code
Views.py:
def is_ajax(request):
return request.META.get('HTTP_X_REQUESTED_WITH') == 'XMLHttpRequest'
def home(request):
return render(request, 'home/home.html')
def index(request):
# If you have passed any data through the 'data' property
#you can get it here, according to the method used.
##if is_ajax(request=request):
id = request.GET.get('data')
msg = testing.objects.exclude(id = id).first()
# Note that we are passing the 'ajax_comments.html' template.
#return render(request, 'practice.html', {'text': msg, 'id':id})
##else:
##msg = testing.objects.last()
return render(request, 'practice.html', {'text': msg, 'id': id} )
#comments = Comment.objects.all.first()
#return render(request, 'practice.html', {'comments': comments})
Template:
{% extends 'base.html'%}
{%block head %} {%endblock%}
{%block navbar %} {% endblock %}
{%block navsmall %} {% endblock %}
{% block header%}
{% endblock %}
{% block firstgrid%}
{%endblock%}
{%block secondgrid%}
<div id = 'myTest'>
{{text.text}} <br> {{id}}
<button class = "asd" value="{{text.td}}">Button</button>
</div>
<script>
$(".asd").click(function(e){
e.preventDefault();
var id = $(this).val();
$.ajax({
method: 'GET', // defaults to GET. Set POST if you like, but be aware of the CSRF token submission too!
url: "{% url 'practice' %}", // submit to the same url
data: {'data': id}, // pass here any data to the server. You can omit it.
success: function(data) {
// This function will run when server returns data
$('#my-Test').replaceWith(data);
alert('ok');
console.log(id);
},
error: (error) => {
console.log('error');
}
});
});
</script>
{%endblock%}
{%block footer%}
{%endblock%}
In views I am getting None value in id

how to update selected value of the dropdown list to the database

I got values of dropdown list which is expense.id and expense_type. In database I look for expense object which has id==expense.id sent by ajax in order to update its type (expense_type). So I need to send both expense.id and expense.type to sever using ajax. I dont know how to perform in jQuery as well as html. Below is my code I got error which is "Not Found: /polls/17/project_detail/ajax/update_form/"
<form action="/ajax/update_form/" method="POST" id="selection-form">
{% csrf_token %}
<select id="select_dropdown">
{% for expense in expenses %}
{% if project.id and expense.city %}
<option value="{{expense.id}}" selected="selected">{{expense.expense_type}}</option>
{% else %}
<option value="{{expense.id}}">{{expense.expense_type}}</option>
{% endif %}
{% endfor %}
</select>
<td><input type="submit" value="Save"></td>
</form>
=====js====
$('#selection-form').on('submit', function(event) {
event.preventDefault();
console.log("form_submitted");
create_post();
});
function create_post(){
console.log("update fucntion is working!");
var value = $("#select_dropdown").find(":selected").val();
var text = $("#select_dropdown option:selected").text();
$.ajax({
//url: "{% url 'update_form' %}",
url: "ajax/update_form/",
method: "POST",
data: {
"value": value,
"text": text,
//"pro_expense": pro_expense,
//"id": valueSelected,
csrfmiddlewaretoken: '{{ csrf_token }}',
},
//dataType: "json",
success: function(data){
console.log(data);
},
error: function(error_data){
console.log("error")
console.log(error_data)
}
});
return false;
};
====views.py=====
#csrf_exempt
def update_form(request):
if request.method == "POST" and request.is_ajax():
value = request.POST.get('value')
text = request.POST.get('text')
expense = Expense.objects.get(pk = value)
expense.expense_type = text
expense.save()
return HttpResponse({"result": "success"}, content_type="application/json")
===urls.py===
url(r'^(?P<project_id>[0-9]+)/project_detail/$', views.project_detail, name='project_detail'),
url(r'^ajax/update_form/$', views.update_form, name = 'update_form'),
error is "Not Found: /polls/17/project_detail/ajax/update_form/". please help. Any help will be highly appreciated!!

How to hide button/form with django templates?

I want to hide form if user already pushed on the button. I tried to use a bit of JS code, it works well, but after refreshing page, button on form stay valid. It not a huge surprise for me)) I want hide form using Django templates, but it is not so easy as I thought.
my html :
<div class="who_come">
<p>Who come : </p>
{% for u in who_come %}
{%if u.visiter.username != request.user.username %}
<form class="form-inline" role="form" method="post" id="joinToEventForm">
{% csrf_token %}
<p align="left"><b ><button type="submit">I want join</button></b></p></b></p>
</form>
{% endif %}
{% endfor %}
<div id="who_come_links">
{% for u in who_come reversed %}
<p>{{u.visiter.username}}</p>
{% endfor %}
</div>
<script>
$('#joinToEventForm').submit(function() {
$(this).find("button[type='submit']").prop('disabled',true);
});
</script>
<script>
$('#joinToEventForm').on('submit', function(event){
event.preventDefault();
console.log("form submitted!") // sanity check
$.ajax({
type:'POST',
data:{
action: 'joinEvent',
csrfmiddlewaretoken:'{{ csrf_token }}'
},
success : function (data) {
//console.log(data);
var usernames = JSON.parse(data);
var html_str = '';
for (var i=0; i < usernames.length; i++) {
html_str += '<p>' + usernames[i] + '</p>';
}
$('#who_come_links').html(html_str);
}
});
});
</script>
</div>
my model :
class WhoComeOnEvent(models.Model):
visiter = models.ForeignKey(User, related_name='WhoComeOnEvent')
which_event = models.ForeignKey(Topic, related_name='WhoComeOnEvent')
in this place :
<p>Who come : </p>
{% for u in who_come %}
{%if u.visiter.username != request.user.username %}
<form class="form-inline" role="form" method="post" id="joinToEventForm">
{% csrf_token %}
<p align="left"><b ><button type="submit">I want join</button></b></p></b></p>
</form>
{% endif %}
{% endfor %}
i tried to check who already joined to event and if user that do request same that user in database table, then hide form. But this code doesn't work. It hide form no matter if user exist in db table or not. Second part is that has no connection to current event. Suppose django template that hide form in my case will work. It will check only row in table but it will ignore current it event or it different event (not sure, but i'm afraid of it).
my view :
def p(request, pk):
user = request.user
topic = get_object_or_404(Topic, pk=pk)
post = get_object_or_404(Post, pk=pk)
comment = Comments.objects.filter(pk=pk)
who_come = WhoComeOnEvent.objects.filter(which_event=topic.id)
if request.is_ajax() and request.POST.get('action') == 'joinEvent':
who_come_obj = WhoComeOnEvent.objects.create(
visiter=user,
which_event=post.topic
)
visitors_usernames = []
for w in who_come:
visitors_usernames.append(w.visiter.username)
return HttpResponse(json.dumps(visitors_usernames))
if request.method == 'POST':
form = CustomCommentForm(request.POST)
if form.is_valid():
comment = form.save(commit=False)
comment.post = post
comment.creator = user
comment = Comments.objects.create(
body=form.cleaned_data.get('body'),
creator=user,
post=post
)
return HttpResponseRedirect(request.META.get('HTTP_REFERER'))
# return render(request, 'post.html', {'post': post, 'topic': topic, 'comment': comment,
# 'form': form, 'who_come': who_come})
else:
form = CustomCommentForm()
return render(request, 'post.html', {'post': post, 'topic': topic, 'comment': comment,
'form': form, 'who_come': who_come})
Solution:
I found more elegant solution, just adding .distinct('visitor') to my who_come queryset.
If someone will read it question and found my solution helpful, notice, that objects still creating to the databese and it doesn't unique!

How to retrieve value from checkbox defined in django template

I have created a menu with three options(home,change password and logout). In home I am displaying all the books stored in the database. Now I want to filter the contents based on categories of the books using checkbox. By default all the books are shown upon filtering the category only the books of that category should be shown.But for me it is showing all the books even after clicking on all the checkbox (checkbox contains the categories).I think there is some problem in my template file.
urls.py,
url(r'^welcome_user/$',views.welcome_user, name='welcome_user'),
Models.py,
class Add_cat(models.Model):
category = models.CharField("Name",max_length=25,unique=True)
def __unicode__(self):
return u'{0}'.format(self.category)
class Add_prod(models.Model):
book = models.CharField("Book Name",max_length=40)
author = models.CharField("Author",max_length=30)
price = models.PositiveIntegerField("Price")
image = models.ImageField(upload_to='images',null=True)
cat = models.ForeignKey(Add_cat,on_delete=models.CASCADE)
Template file,
{% block content %}
{% load staticfiles %}
<head>
<link rel="stylesheet" href="{% static 'style.css' %}">
</head>
<body>
<div class="box">
<div class="sideNav">
<form action="{% url 'welcome_user' %}">
<p id=id3>Categories</p>
<hr>
{% for i in products %}
<input type="checkbox" name="cat_name" value="{{i.cat}}">{{i.cat}}<br>
{% endfor %}
<button type="submit">Submit</button>
</form>
</div>
<div>
{% for i in products %}
<div style="display:inline-block;margin:30px">
<img src="{{i.image.url}}" alt="No Image" width=196px height=196px>
<p id=id4>Rs.{{i.price}}</p>
</div>
{% endfor %}
</div>
</div>
</body>
{% endblock %}
Views.py,
#login_required
def welcome_user(request):
if 'cat_name' in request.GET:
filter_category = request.GET.getlist('cat_name')
my_products = Add_prod.objects.filter(cat__in=filter_category)
context = { "products":my_products}
else:
my_products = Add_prod.objects.all()
context = { "products":my_products}
return render(request,"welcome-user.html",context)
To check whether checbox value is in sent form you should go with following condition
if 'cat_name' in request.GET:
#checkbox has been checked
else:
#it is not checked
Remember that in operator return boolean so you can also do
filter_category = 'cat_name' in request.GET
To get value you just need to get values of 'cat_name' key like:
value = request.GET['cat_name']
after checking whether it is in GET parameters or not
I think all you need to do is add __in to your filter:
#login_required
def welcome_user(request):
filter_category = request.GET.getlist('cat_name')
categories = Add_cat.objects.all()
if filter_category: # I couldn’t decipher the structure of an `Add_cat`, so I left off the `in` check since it would not work for lists
print filter_category
my_products = Add_prod.objects.filter(cat__in=filter_category) # the template implies that this field is `cat` and not `category`
context = { "products":my_products}
else:
my_products = Add_prod.objects.all()
context = { "products":my_products}
return render(request,"welcome-user.html",context)
Checkboxes work a little bit different from other form inputs, so if you examine a post sent from a form that includes a checkbox,
if the checkbox is checked, your queryset will look like:
the value will be 'on'
So, you have to check
if request.POST.get('cb1')=='on':
"item is selected"
else:
"item is not selected"
Try this below code
Add_prod.objects.filter(cat__in=filter_category)
#login_required
def welcome_user(request):
filter_category = request.GET.getlist('cat_name')
if filter_category:
my_products = Add_prod.objects.filter(cat__in=filter_category)
context = { "products":my_products}
else:
my_products = Add_prod.objects.all()
context = { "products":my_products}
return render(request,"welcome-user.html",context)
Template file
Remove quotes(') from {% url 'welcome_user' %}
<form method='get' action="{% url welcome_user %}">
UPDATE
Add quotes between views.welcome_user
urls.py
url(r'^welcome_user/$','views.welcome_user', name='welcome_user'),

(django) strftime format does not work properly, different timezone, order

This is about comments of a bulletin. When someone writes a comment and push 'submit', ajax send data to pushComment() of views.py, save the data, and return to the ajax. So user can see the comment without refreshing the page.
The Problem is, the data format.
I used strftime(format) but it works with some problems.
TIMEZONE is not applied with new comments. my server TIMEZONE is 'asia/seoul' but new comments shows TIMEZONE as UTC. (only for new comments)
Format order is changed. my format is 'date to time' but time comes sonner than date.
here's my code.
views.py
def pushComment(request):
pk = request.POST.get('writing_id', 1)
ac = ArticleComments(
user = User.objects.get(username=request.user.username),
article = FreeBoards.objects.get(id=pk),
comments = request.POST.get('comments', 'Nothing'),
# target = 0,
pub_date = datetime.now().replace(microsecond=0),
like = 0,
)
ac.save()
com_cnt = ArticleComments.objects.filter(article=pk).count()
FreeBoards.objects.filter(id=pk).update(comments = com_cnt)
user = MyUser.objects.get(nickname=request.user.myuser)
data = {
'writing_id': pk,
'user': user.nickname,
'comments': ac.comments,
# 'target': ac.target,
'pub_date': str(ac.pub_date.strftime('%y-%m-%d %H:%M:%S %Z')), # why TIMEZONE is UTC ?????
'like': ac.like,
'com_cnt': com_cnt,
}
return HttpResponse(simplejson.dumps(data), content_type="application/json")
template
<form role="form" class="form-inline" id="form-com-id" name="commentform" onsubmit="return false;" action="." method="POST">{% csrf_token %}
<div class="form-group">
<div class="col-xs-11">
<input type="text" class="form-control" id="id-comment" name="comname" placeholder="Leave your comment.">
</div>
</div>
<div class="form-group">
<div class="col-xs-1">
<button type="submit" class="btn btn-default" id="btn-comment-submit" OnClick="javascript:commentCheck();">Submit</button>
</div>
</div>
</form>
<br><br>
<div class="comments-group">
<div id="com-start" class="panel-heading">자유로운 댓글</div>
{% if comment_list %}
{% for c in comment_list %}
<div class="col-xs-12 col-sm-6 col-md-4">
<div class="{% cycle 'box1' 'box2' 'box3' 'box4' 'box5' %}">
<div class="boxbox">
<div class="com-user">
<p>작성자: {{c.user.myuser}}
<button onclick=deleteCom()>×</button>
</p>
</div>
<div class="com-content ellipsis">
<p>{{c.comments}}</p>
</div>
<div class="com-date"
<p>{{c.pub_date}}</p>
</div>
</div>
</div>
</div>
{% endfor %}
{% endif %}
</div>
javascript
$('#form-com-id').submit(function() {
var com = $('#id-comment').val();
if(com){
$.ajax({
url : "/sle/freeboards/pushComment/",
type : "POST",
data : {
writing_id : '{{writing_id}}',
comments : com,
csrfmiddlewaretoken: '{{csrf_token}}',
},
dataType : "json",
success:function(data){
$('#id-comment').val('');
/* create elements and class matching */
var divcomgrp = document.getElementsByClassName('comments-group');
var divgrid = document.createElement("div");
divgrid.className = 'col-xs-12 col-sm-6 col-md-4';
var divbox = document.createElement('div');
if(data.com_cnt % 5 == 0) {
divbox.className = 'box5';
} else if (data.com_cnt % 5 == 1) {
divbox.className = 'box1';
} else if (data.com_cnt % 5 == 2) {
divbox.className = 'box2';
} else if (data.com_cnt % 5 == 3) {
divbox.className = 'box3';
} else if (data.com_cnt % 5 == 4) {
divbox.className = 'box4';
}
// quotient = data.com_cnt / 5;
var divcontainer = document.createElement("div");
divcontainer.className = 'boxbox';
var divuser = document.createElement("div");
divuser.className = 'com-user';
var divcont = document.createElement("div");
divcont.className = 'com-content';
var divdate = document.createElement("div");
divdate.className = 'com-date';
/* create paragraphs */
var puser = document.createElement('p');
var textnode = document.createTextNode(data.user);
puser.appendChild(textnode);
var butdel = document.createElement('button');
butdel.innerHTML = '&times';
butdel.onclick = deleteCom;
puser.appendChild(butdel);
var pcomments = document.createElement('p');
var textnode2 = document.createTextNode(data.comments);
pcomments.appendChild(textnode2);
var pdate = document.createElement('p');
var textnode3 = document.createTextNode(data.pub_date);
pdate.appendChild(textnode3);
/* appending children */
divuser.appendChild(puser);
divcont.appendChild(pcomments);
divdate.appendChild(pdate);
divcontainer.appendChild(divuser);
divcontainer.appendChild(divcont);
divcontainer.appendChild(divdate);
divbox.appendChild(divcontainer);
divgrid.appendChild(divbox);
divcomgrp[0].appendChild(divgrid);
},
failure: function(data){
alert('fail!!');
},
});
}
});
settings.py
TIME_ZONE = 'Asia/Seoul'
result
I cannot upload images... so I'll write it.
the original date format from comments.html : Feb.25,2015,11:31 a.m
ajax comments(temporary for new comments) : UTC 02:31:53 15-02-25
(both comments were written at 11:31, I wrote a comment and refresh, then add another comment right after.)
(if i refresh the page, the 2nd one disappear and all date format printed as 1st one.)
I don't know why the format i inputted does not work.
p.s)
...and one more, What should I do to print 'datetimefield' without time?
Need the DateTimeField for database but in a certain page i want to show just date, not time.
You need to set a timezone-aware datetime as the pub_date when you create a new ArticleComments instance.
from django.utils import timezone
ac = ArticleComments.objects.create(
...
pub_date = timezone.now().replace(microsecond=0),
...
)
Secondly, correct me if I am wrong but I think you should convert ac. pub_date to local time first prior to formatting it to a string:
from django.utils import timezone
data = {
...
'pub_date': timezone.localtime(ac.pub_date).strftime('%y-%m-%d %H:%M:%S %Z')),
...
}
For your last question about converting a datetime object to date without time, you can call .date() method on that datetime.
>>> from django.utils.timezone import now
>>> today_as_date = now().date()
>>> today_as_date_str = today_as_date.strftime('%Y-%m-%d')
For more information, you might want to take a look at the timezone documentation in Django and pytz library.

Categories

Resources