Display user's posts in their profile on django - python

I have been trying to make the profile page of a user have the user's posts but everytime I run my code nothing shows up only the user's username and user's email. I've tried multiple ways to make it work but somehow it doesn't. I think the profile.html has the error in it.
views.py
def profile(request, pk=None):
if pk:
post_owner = get_object_or_404(User, pk=pk)
user_posts=Post.objects.filter(posti=request.user)
else:
post_owner = request.user
user_posts=Post.objects.filter(posti=request.user)
return render(request, 'profile.html', {'post_owner': post_owner, 'user_posts': user_posts})
models.py
class Post(models.Model):
text = models.CharField(max_length=200)
posti = models.ImageField(upload_to='media/images', null=True, blank="True")
user = models.ForeignKey(User, related_name='imageuser', on_delete=models.CASCADE, default=2)
profile.html
<div class="content-section">
<div class="media">
<img class="rounded-circle account-img" src="{{ user.profile.image.url }}">
<div class="media-body">
<h2 class="account-heading">{{ post_owner.username }}</h2>
<p class="text-secondary">{{ post_owner.email }}</p>
</div>
{% for Post in user_posts %}
<li class="list-group-item">{{ Post.text }}
{{ Post.user }}
{% if Post.posti %}
<img src="{{ image.posti.url }}" alt="image here" style="max-width: 300px; max-height: 300px">
{% endif %}
{% if Post.user == user %}
<div class="float-right">
<form action="delete_image/{{ image.id }}/" action="post">
<button type="submit" class="btn btn-outline-danger btn-sm">Delete</button>
</form>
</div>
{% endif %}
</li>
{% endfor %}
</div>
</div>

The problem here is with the line:
user_posts=Post.objects.filter(posti=request.user)
To get the posts from the logged in user you will need to use this:
user_posts=Post.objects.filter(user=request.user)
and to get the posts from the selected user you will need to do this:
user_posts=Post.objects.filter(user_id=pk)
I hope this helps :)

You are querying the wrong column:
user_posts=Post.objects.filter(posti=request.user)
posti is an ImageField. You actually want to query the user field:
user_posts=Post.objects.filter(user=request.user)
That being said, you don't need any of these queries in your view. You can simply make use of your related_name, i.e.:
{% for Post in post_owner.imageuser.all %}

Related

Unable to render images in caraousel from database in django?

I am trying to render images from my database to carousel in Django. I have a model which contains url fields to store images url but when I use them in (template.html) my carousel img src, it only renders 1st image but not others even though I have three images url stored in database. To understand it better here is my code.
models.py
from django.db import models
# Create your models here.
class CaraouselData(models.Model):
title = models.CharField(max_length=100, null=False)
description = models.TextField(max_length=200, null=True)
image = models.URLField(null = False, default=True)
def __str__(self):
return self.title
views.py
def home(request):
caraousel_data = CaraouselData.objects.all()
return render(request, 'index.html', context={
'caraousel_data': caraousel_data,
})
template.js
{% block content %}
{# Caraousel Data Section#}
<div class="container-fluid p-0">
<div id="carouselExampleCaptions" class="carousel slide" data-bs-ride="carousel">
<div class="carousel-indicators">
<button type="button" data-bs-target="#carouselExampleCaptions" data-bs-slide-to="0" class="active" aria-current="true" aria-label="Slide 1"></button>
<button type="button" data-bs-target="#carouselExampleCaptions" data-bs-slide-to="1" aria-label="Slide 2"></button>
<button type="button" data-bs-target="#carouselExampleCaptions" data-bs-slide-to="2" aria-label="Slide 3"></button>
</div>
{# images fetching from models #}
<div class="carousel-inner">
{% for item in caraousel_data %}
<div class="carousel-item {% if forloop.counter0 == 0 %} active" {% endif %}>
<img src="{{ item.image }}" width="600" height="670" class="d-block w-100" alt="...">
<div class="carousel-caption d-none d-md-block">
<h5>{{ item.title }}</h5>
<p>{{ item.description }}</p>
</div>
</div>
{% endfor %}
{% endblock %}
I think you have not installed the pillow library.🤔
To handle images you must install them first.

How to capture values in checked checkboxes using Django

I am creating a web application that will serve as a grocery store. The way I set it up is so the customer can come onto the website, click on the items that they would like to purchase, and then click a submit button to purchase those items. The problem I am running into is having a views.py function to take the information of which products were selected and subtracting 1 from the quantity of the database. When I say print(products) in my views.py, it returns "[]" in my terminal. This means that the values in my checked checkboxes are not being captured. Can anyone help me solve this?
"""models.py"""
class Post(models.Model):
title = models.CharField(max_length=100)
Price = models.DecimalField(max_digits=4, decimal_places=2,default=1)
Sale = models.DecimalField(max_digits=4, decimal_places=2,default=1)
quantity = models.IntegerField(default=1)
author = models.ForeignKey(User, on_delete=models.CASCADE)
category = TreeForeignKey('Category',null=True,blank=True, on_delete=models.CASCADE)
def __str__(self):
return self.title
def get_absolute_url(self):
return reverse('post-detail', kwargs={'pk': self.pk})
views.py
class PostListView(ListView):
model = Post
template_name = 'blog/home.html' # <app>/<model>_<viewtype>.html
context_object_name = 'posts'
def inventory(request):
products = request.POST.getlist('products')
a = Post.objects.filter(title=products).update(
quantity=F('quantity')-1
)
return redirect('blog-home')
urls.py
path('user/<str:username>', UserPostListView.as_view(), name='user-posts'),
path('inventory', views.inventory, name='inventory'),
home.html
{% extends "blog/base.html" %}
{% block content %}
{% for post in posts %}
{% if post.quantity > 0 %}
<input type="checkbox" name="products" id="product_{{ post.id }}" value="{{ post.id }}">
<article class="media content-section">
<div class="media-body">
<div class="article-metadata">
<a class="mr-2" href="{% url 'user-posts' post.author.username %}">{{ post.category }}</a>
</div>
<h2><a class="article-title" href="{% url 'post-detail' post.id %}">{{ post.title }}</a></h2>
<p class="article-content"> Price: ${{ post.Price }}</p>
<p class="article-content"> Sale: ${{ post.Sale }}</p>
Inventory count: {{ post.quantity }}
</input>
</div>
</article>
{% else %}
<article class="media content-section">
<div class="media-body">
<div class="article-metadata">
<a class="mr-2" href="{% url 'user-posts' post.author.username %}">{{ post.category }}</a>
</div>
<h2><a class="article-title" href="{% url 'post-detail' post.id %}">{{ post.title }}</a></h2>
<p class="article-content"> Price: ${{ post.Price }}</p>
<p class="article-content"> Sale: ${{ post.Sale }}</p>
Inventory count: {{ post.quantity }}
<p>Out Of Stock!</p>
</div>
</article>
{% endif %}
{% endfor %}
<button type="submit" name="Purchase" >Confirm Purchase</button>
{% endblock content %}
My goal is to click on the checkboxes, and when the customer clicks the button on the bottom of home.html, it triggers the inventory function to subtract "1" from the quantity.
You have to create a form in your HTML to handle this POST request.
Then handle this in your view with if request.method == 'POST' followed by the getlist() and the update function. also, i think you need to add a for loop to your queryset because there could be more than one product. hope this helps!
def inventory(request):
if request.method == 'POST':
products = request.POST.getlist('products')
for product in products:
a = Post.objects.filter(title=product).update(
quantity=F('quantity')-1
)
return redirect('blog-home')

auth.user.none and <QuerySet []> in ManyToManyField rendering

I try to display numbers of Users who liked some image on my website written in Django.
The Image model looks like this below:
class Image(models.Model):
(***)
users_like = models.ManyToManyField(settings.AUTH_USER_MODEL,
related_name='images_liked',
blank=True)
When I use in my template:
{{image.users_like.all}}
I get :
QuerySet [],
when I use in templates
{{image.users_like}}
I get
auth.User.None.
It's weird because in my admin page I have information that someone liked this photo.
Below my view function:
def image_detail(request, id, slug):
image = get_object_or_404(Image, id=id, slug=slug)
return render(request,
'images/image/detail.html',
{'section': 'images',
'image': image})
EDIT
My admin page, in Users like section display usernames of user who already liked the photo. PrtSc below:
FULL BLOCK
<h1>{{ image.title }}</h1>
`<p>{{image.users_like.all}}</p>
{% load thumbnail %}
{% thumbnail image.image "300" as im %}
<a href="{{ image.image.url }}">
<img src="{{ im.url }}" class="image-detail">
</a>
{% endthumbnail %}
{% with total_likes=image.users_like.count users_like=image.users_like.all %}
<div class="image-info">
<div>
<span class="count">
<span class="total">{{ total_likes }}</span>
like{{ total_likes|pluralize }}
</span>
<a href="#" data-id="{{ image.id }}" data-action="{% if request.user in users_like %}un{% endif %}like" class="like button">
{% if request.user not in users_like %}
Like
{% else %}
Unlike
{% endif %}
</a>
</div>
{{ image.description|linebreaks }}
</div>
<div class="image-likes">
{% for user in image.users_like.all %}
<div>
<img src="{{ user.profile.photo.url }}">
<p>{{ user.first_name }}</p>
</div>
{% empty %}
Nobody likes this image yet.
{% endfor %}
</div>
{% endwith %}
Answer in the comments above. QuerySet was empty when called. After adding users to image.users_like the problem disappeared. Thank you solarissmoke.

Django Field is showing up in one view but not the other

I'm just starting out with Django and I have a problem where, when I added a field to my model (JobPost which inherits from models.Model) and it migrated successfully I can see and interact with the new field when I create a job post, but not when I view the JobPost (which is displayed using crispy forms using the {{ form|crispy }} tag.
I have added the field name to my fields = [''] in my views.py
models.py
class JobPost(models.Model):
#constants
CLEARANCE_LEVELS=[(...),]
author = models.ForeignKey(User, on_delete=models.CASCADE)
title = models.CharField(max_length=100)
content = models.TextField()
clearance_required = models.CharField(max_length=50, choices=CLEARANCE_LEVELS, default='None')
date_posted = models.DateTimeField(default=timezone.now)
views.py
class JobDetailView(DetailView):
model = JobPost
class JobCreateView(LoginRequiredMixin, CreateView):
model = JobPost
fields = ['title', 'content', 'clearance_required']
# form_valid checks if the user is logged in
def form_valid(self, form):
form.instance.author = self.request.user
return super().form_valid(form)
jobpost_form.html
{% load crispy_forms_tags %}
{% block content %}
<div class="content-section">
<form method="POST">
{% csrf_token %} <!--Used to prevent some XSS Attacks (Cross-site request forgery) -->
<fieldset class="form-group">
<legend class="border-bottom mb-4">Create Job Post</legend>
{{ form|crispy }}
</fieldset>
<div class="form-group">
<button class="btn btn-outline-info" type="submit">Submit</button>
</div>
</form>
</div>
{% endblock content %}
jobpost_detail.html
{% block content %}
<article class="media content-section">
<img class="rounded-circle article-img" src="{{ object.author.profile.image.url }}">
<div class="media-body">
<div class="mb-2 article-metadata">
<a class="mr-1" href="{% url 'profile' %}">{{ object.author }}</a> <!-- BROKEN LINK: SIMPLY TAKES TO CURRENTLY LOGGED IN USER-->
<small class="text-muted">{{ object.date_posted|date:"F d, Y" }}</small>
{% if object.author != user %}
<a class="btn btn-secondary btn-sm float-right" href="{% url 'user-jobs' object.author.username %}">See all jobs the user applied to</a>
{% endif %}
<div>
{% if object.author == user %}
<a class="btn btn-secondary btn-sm mt-1 mb-1 float-right" href="{% url 'user-jobs' object.author.username %}">See all jobs the user applied to</a>
<a class="btn btn-secondary btn-sm mt-1 mb-1" href="{% url 'job-update' object.id %}">Update Job Posting</a>
<a class="btn btn-danger btn-sm mt-1 mb-1" href="{% url 'job-delete' object.id %}">Delete</a>
{% endif %}
</div>
</div>
<div class="mt-1">
<h2 class="article-title">{{ object.title }}</h2>
<p class="article-content">{{ object.content }}</p>
</div>
</div>
</article>
{% endblock content %}
So when I view it in my browser, I see the "clearance_required" field when I create a job post. But when I just view the job post, it only shows the title and description, not the new clearance_required field. I don't know how I can get it to display.
Here's a picture of the issue:
Notice how the clearance field is missing in the second picture
Do you actually output in object.clearance_required in jobpost_detail.html, because I cannot see it?
And by the way, if you output it, you should use object.get_clearance_required_display, because it is a field with choices.

How to correct logic in comments View?

I build comments functional for post but has bug. When someone comment post, another user see correct comment body, but incorrect image and
def p(request, pk):
user = request.user
#user_that_text_comment = User.objects.filter(pk=pk)
topic = get_object_or_404(Topic, pk=pk)
post = get_object_or_404(Post, pk=pk)
comment = Comments.objects.filter(pk=pk)
if request.method == 'POST':
form = CustomCommentForm(request.POST)
if form.is_valid():
comment = form.save(commit=False)
comment.post = post
comment.creator = user
comment.save()
comment = Comments.objects.create(
body=form.cleaned_data.get('body'),
creator=user,
)
return render(request, 'post.html', {'post': post, 'topic': topic, 'comment': comment, 'form': form})
else:
form = CustomCommentForm()
return render(request, 'post.html', {'post': post, 'topic': topic, 'comment': comment, 'form': form})
I builded comment function for post but it has bug. When someone comment post, another user see correct comment body, but incorrect image and name.
i know why i has this problem(i suppose), it happend because i use user=request.user. Notice on string that i comment on 3 line. I was think that will help me,but it isn't. I use primary key in my url. url(r'^boards/(?P<pk>\d+)/$', views.board_topics, name='board_topics'), and when i use primary key in filter it return to me user that has same pk as post pk. I need that it return to me username and picture of user that create this comment.
Html template:
<div class="detailBox">
<div class="titleBox">
<label>{{topic.subject}}</label>
<!--<button type="button" class="close" aria-hidden="true">×</button>-->
</div>
<div class="commentBox">
<img src="{{ MEDIA_URL }}{{ topic.image.url }}" alt="">
<p class="taskDescription">{{ post.message|safe|linebreaks}}</p>
</div>
<div class="actionBox">
<ul class="commentList">
{% for comment in post.comment.all %}
<li>
<div class="commenterImage">
{% if user.profile.profile_img %}
<img src="{{ MEDIA_URL }}{{ user.profile.profile_img.url }}" >
{{ user.username }}
{% else %}
<img src="https://image.freepik.com/free-vector/no-translate-detected_1053-593.jpg">
{{ user.username }}
{% endif %}
</div>
<div class="commentText">
<p class="">{{ comment.body }}</p> <span class="date sub-text">{{comment.created_at}}</span>
</div>
</li>
{% endfor %}
</ul>
<form class="form-inline" role="form" method="post">
{% csrf_token%}
{{form}}
<button type="submit" class="btn btn-default">Add</button>
</form>
</div>
</div>{% endblock %}
You should add the comment prefix and relate to the creator to the variables inside the comment
<li>
<div class="commenterImage">
{% if comment.creator.profile.profile_img %}
<!-- ^^^^^ -->
<img src="{{ MEDIA_URL }}{{ comment.creator.profile.profile_img.url }}" >
<!-- ^^^^^ -->
{{ comment.creator.username }}
<!-- ^^^^^ -->
{% else %}
<img src="https://image.freepik.com/free-vector/no-translate-detected_1053-593.jpg">
{{ user.username }}
{% endif %}
</div>
<div class="commentText">
<p class="">{{ comment.body }}</p> <span class="date sub-text">{{comment.created_at}}</span>
</div>
</li>

Categories