ValueError: The 'cover' attribute has no file associated with it - django

I uploaded image from admin panel and it get stored in media/img.I want to display posted image in my index.html but i get this ValueError: The 'cover' attribute has no file associated with it.I think I am making mistake in url or view ..I am new to django.
# app urls.py
urlpatterns = [
path('', views.PostList.as_view(), name='home'),
path('<slug:slug>/', views.post_detail, name='post_detail'),
]
# project urls.py
urlpatterns = [
path("admin/", admin.site.urls),
path("", include("blog.urls"), name="blog-urls"),
path("summernote/", include("django_summernote.urls")),
]
# views.py
class PostList(generic.ListView):
queryset = Post.objects.filter(status=1).order_by('-created_on')
template_name = 'index.html'
paginate_by = 3
# models.py
class Post(models.Model):
cover = models.ImageField(upload_to='image/', default='')
title = models.CharField(max_length=200, unique=True)
slug = models.SlugField(max_length=200, unique=True)
author = models.ForeignKey(
User, on_delete=models.CASCADE, related_name="blog_posts"
)
updated_on = models.DateTimeField(auto_now=True)
content = models.TextField()
created_on = models.DateTimeField(auto_now_add=True)
status = models.IntegerField(choices=STATUS, default=0)
<!-- index.html -->
<img src={{ post.cover.url }} alt="{{ post.title }}" width="160px" height="220px">

List view output is a queryset, means a list of instances, so you have to loop through it.
{% for post in object_list %}{% if post.cover %}
<img src={{ post.cover.url }} alt="{{ post.title }}" width="160px" height="220px">{% endif %}
{% endfor %}
also change the include url to
path("", include("blog.urls"))
without name, if you want you can add a namespace

Related

NoReverseMatch at /products/ "adding products to the basket"

I am fairly new and working on a project and want to just add products to the basket
I have struggled with this for a few days and just don't know what to do to make it work.
can anybody help me or refer me to some page that can help me?
Thank You
NoReverseMatch at /products/
Reverse for 'addtobasket' with arguments '('Python Tutorial',)' not found. 1 pattern(s) tried: ['productapp/\.\./basket/$']
models:
class Products(models.Model):
products_name = models.CharField(max_length=30)
pub_date = models.DateTimeField(auto_now=True)
price = models.CharField(max_length=10)
note = models.CharField(max_length=200)
inventory = models.IntegerField(default=1)
product_pic = models.ImageField(upload_to ='images/', default='images/broken/broken.png')
def __str__(self):
if (self.inventory<=0):
return self.products_name + ' (Out of Stock)'
return self.products_name
class Basket(models.Model):
products = models.ForeignKey(Products, on_delete=models.CASCADE)
pub_date = models.DateTimeField(auto_now=True)
amount = models.IntegerField(default=1)
def __str__(self):
return str(self.products)
urls:
app_name = 'productapp'
urlpatterns = [
path('products/', views.products, name='products'),
path('basket/', views.basket, name ='basket'),
path('', views.home, name='home'),
path('../basket/', views.addtobasket, name='addtobasket'),
]
views:
def products(request):
products_list = Products.objects.order_by('-pub_date')
context = {'products_list': products_list}
return render(request, 'productapp/products.html', context)
def basket(request):
basket_list = Basket.objects.order_by('-pub_date')
context = {'basket_list': basket_list}
return render(request, 'productapp/basket.html', context)
def addtobasket(request, name):
basket = Basket.objects.all()
product = Products.objects.get(products_name=name)
basket.products.add(product)
return HttpResponseRedirect(reverse("basket"))
html:
<body>
<section>
{% block content %}
{% if products_list %}
{% for product in products_list %}
<div>
<div>
<p>{{product.products_name}}</p>
<p>{{product.price}}</p>
Add to Basket
</div>
</div>]
{% endfor %}
{% else %}
<p>No products avalable at this moment.</p>
{% endif %}
{% endblock %}
</section>
</body>
A path with ../ makes not much sense, since that means the url should contain the dots.
Furthermore you should specify the URL parameter in the path:
app_name = 'productapp'
urlpatterns = [
path('products/', views.products, name='products'),
path('basket/', views.basket, name ='basket'),
path('', views.home, name='home'),
path('basket/add/<str:name>/', views.addtobasket, name='addtobasket'),
]
Adding an item to the basket should not work with a GET request, since the HTTP protocol specifies that GET requests should not have side-effects. You will need to work with a POST request, for example by implementing a mini-form with method="post", or through an AJAX post request.

Failing To Display Media File Django

I have created a model called Product that takes in an ImageField that will be upload on a function I created:
class Product(models.Model):
title = models.CharField(max_length=120)
description = models.TextField()
price = models.DecimalField(decimal_places=2, max_digits=10, default=39.99)
image = models.ImageField(upload_to=upload_image_path, null= True, blank=True)
def __str__(self):
return self.title
return self.image
def __unicode__(self):
return self.title
I have also created my MEDIA_ROOT and STATIC_ROOT below is code from main urls however I also defined this two on the settings.py:
if settings.DEBUG:
urlpatterns = urlpatterns + static(settings.STATIC_URL, document_root=settings.STATIC_ROOT)
urlpatterns = urlpatterns + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
So I am able to upload Image from the admin and it uploads properly to the media_root that I created.
When I try calling/displaying the image it render nothing I do not know where I could have made a mistake
{% load static %}
{{ object.title }} <br/>
{{ object.description }} <br/>
{{ object.image.url }}<br/>
<img src="{{ object.image.url }}" class='img-fluid'/>
but the {{ object.image.url }} actually gives me the exact path of the Image which should make sense for the the picture to rendered.
This is the the result output that I was telling about, that I'm getting the image url but I can not display the Image
<img src="/media/{{ object.image }}" alt='xyz'>

Django Class Based Views not rendering variables in Template

I'm pretty new to Django and already have read a lot about class-based views before coming here. I'm trying to build a one page website, with dynamic blocks that can be written from the Django admin. My problem is that I cannot manage to render variables from my database in my template. Here's what I wrote:
models.py
from django.db import models
from tinymce.models import HTMLField
class MyResume(models.Model):
subline = models.CharField(max_length=200)
content = HTMLField()
class Meta:
verbose_name = "My Resume"
verbose_name_plural = "My Resume"
def __str__(self):
return "My Resume"
class AboutMe(models.Model):
subline = models.CharField(max_length=200)
content = HTMLField()
cover_img = models.ImageField(upload_to="about_me")
class Meta:
verbose_name = "About me"
verbose_name_plural = "About me"
def __str__(self):
return "About me"
class Experience(models.Model):
subline = models.CharField(max_length=200)
pres_content = models.TextField()
exp_content = HTMLField()
date_exp = models.IntegerField()
class Meta:
verbose_name = "Experience"
verbose_name_plural = "Experiences"
def __str__(self):
return "Experience"
class ProjectPost(models.Model):
title = models.CharField(max_length=200)
technology = models.CharField(max_length=100)
subline = models.CharField(max_length=200)
content = HTMLField()
project_post_cover = models.ImageField(upload_to="projectpost_cover")
class Meta:
verbose_name = "Project Post"
verbose_name_plural = "Project Posts"
def __str__(self):
return self.title
class BlogPost(models.Model):
title = models.CharField(max_length=200)
overview = models.TextField()
timestamp = models.DateTimeField(auto_now_add=True)
content = HTMLField()
blogpost_thumbnail = models.ImageField(upload_to="blogpost_thumbnail")
class Meta:
verbose_name = "Blog Post"
verbose_name_plural = "Blog Posts"
def __str__(self):
return self.title
class Contact(models.Model):
subline = models.CharField(max_length=200)
presentation_content = HTMLField()
def __str__(self):
return "Contact section text"
views.py
from django.shortcuts import render
from django.views.generic.base import TemplateView
from .models import *
class IndexTemplateView(TemplateView):
template_name = 'index.html'
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs) # first, call super get context data
context['myresume'] = MyResume.objects.all()
context['aboutme'] = AboutMe.objects.all()
context['experience'] = Experience.objects.all()
context['projectpost'] = ProjectPost.objects.all()
context['blogpost'] = BlogPost.objects.all()
context['contact'] = Contact.objects.all()
return context
core.urls.py:
from django.urls import path
from .views import IndexTemplateView
urlpatterns = [
path('', IndexTemplateView.as_view()),
]
appname.urls.py:
from django.contrib import admin
from django.urls import include, path
from django.conf.urls import url
from django.conf import settings
from django.conf.urls.static import static
urlpatterns = [
path('admin/', admin.site.urls),
url(r'^tinymce/', include('tinymce.urls')),
path('', include('core.urls')),
]+ static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
and a snippet from my index.html template:
{% extends 'base.html' %}
{% load static %}
{% block content %}
(...)
<!-- ==================== ABOUT ==================== -->
<section id="about" class="section">
<h2 class="title">ABOUT</h2>
<div class="section-des">
{{ aboutme.subline }}
</div>
<div class="content-670">
<p>
{{ aboutme.content }}
</p>
</div>
<img class="about-img block-right" data-jarallax-element="0 -40" src="{{ aboutme.cover_img.url }}" alt="">
(...)
{% endblock content %}
All of the variables you've added to your template context are querysets, not objects. But you're trying to read them as individual objects in your template, which is why it doesn't work. You have two options:
Iterate over each queryset in your template:
{% for item in aboutme %}
<h2 class="title">ABOUT</h2>
{{ item.subline }}
{{ item.content }}
{% endfor %}
If you only want to display one of each model, then you need to fix your context method to only return one object, e.g.,
context['aboutme'] = AboutMe.objects.first()
Where here you're just returning the first AboutMe object in the database. If you do this, then your existing template logic will work. How you determine which object to return depends on what your data looks like.
{% for obj in myresume %}
<p>{{ obj.subline }}</p>
{% endfor %}
{% for obj in aboutme %}
<p>{{ obj.subline }}</p>
{% endfor %}
you can call your objects in this way in your templates. Also modify str function in models to get the dynamic content.
class MyResume(models.Model):
subline = models.CharField(max_length=200)
content = HTMLField()
class Meta:
verbose_name = "My Resume"
verbose_name_plural = "My Resume"
def __str__(self):
return self.sublime

Django does not see the static files images

I'm trying to create an online store with Django. I want to add photos of goods, but Django for some reason does not see them. Please help to solve the problem.
Here is a screenshot of error:
here is settings.py
BASE_DIR = os.path.dirname(os.path.abspath(__file__))
STATIC_ROOT = 'staticfiles'
STATICFILES_DIRS = (
os.path.join(BASE_DIR, 'static'),
'../static/products/media/product_images/',
)
models.py
from django.db import models
# Create your models here.
class Product(models.Model):
name = models.CharField(max_length=70, blank=True, null=True, default=None)
price = models.DecimalField(max_digits=10, decimal_places=2, default=0)
description = models.TextField(blank=True, null=True, default=None)
short_description = models.TextField(blank=True, null=True, default=None)
is_active = models.BooleanField(default=True)
created = models.DateTimeField(auto_now_add=True, auto_now=False)
updated = models.DateTimeField(auto_now_add=False, auto_now=True)
def __str__(self):
return "%s, %s" % (self.price ,self.name)
class Meta:
verbose_name = 'Товар'
verbose_name_plural = 'Товары'
class ProductImage(models.Model):
product = models.ForeignKey(Product, blank=True, null=True, default=None, on_delete=models.CASCADE)
image = models.ImageField(upload_to='static/media/product_images/')
is_active = models.BooleanField(default=False)
is_main = models.BooleanField(default=True)
created = models.DateTimeField(auto_now_add=True, auto_now=False)
updated = models.DateTimeField(auto_now_add=False, auto_now=True)
def __str__(self):
return "%s" % self.id
class Meta:
verbose_name = 'Фотография'
verbose_name_plural = 'Фотографии'
main urls.py file
from django.contrib import admin
from django.urls import include, path
from django.conf import settings
from django.conf.urls.static import static
urlpatterns = [
path('admin/', admin.site.urls),
path('', include('online_shop.urls', namespace='online_shop')),
path('', include('products.urls', namespace='products')),
path('', include('orders.urls', namespace='orders')),
]
html template
{% extends 'online_shop/base.html' %}
{% load static %}
{% block content %}
<section>
<div class="top-section">
<img src="{% static 'img/clem.png' %}" class="img-fluid">
</div>
</section>
<section>
<div class="container">
<div class="row">
{% for product_image in product_images %}
<div class="col-lg-3">
<div class="product-item">
<div>
<img src="{{product_image.image}}" alt="" class="img-fluid">
</div>
<h4>{{product_image.product.name}}</h4>
<p>{{product_image.product.description|truncatechars_html:80 }}</p>
<div class="price">
{{product_image.product.price}} ГРН
</div>
<div class="add-to-card">
<button class="btn btn-success">
Добавить в корзину
</button>
</div>
</div>
</div>
{% endfor %}
</div>
</div>
</section>
{% endblock content %}
You may need to do some modifications
settings.py
# prefix used in static files path rendering
STATIC_URL = '/static/'
# store static files once execute python manage.py collectstatic
STATIC_ROOT = os.path.join(BASE_DIR, 'staticfiles/')
# directories where static files are stored in the development environment
STATICFILES_DIRS = [
os.path.join(BASE_DIR, "static"),
]
# prefix used upon uploaded images
MEDIA_URL = '/media/'
# where uploaded images should save
MEDIA_ROOT = os.path.join(BASE_DIR, 'media/')
urls.py
# lets you have the ability to view images even in development environment
if settings.DEBUG:
urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)
update:
Since you use static/media/product_images/ as upload path, the uploaded files will be saved in
project-root-dir/media/static/products/media/product_images
Hope this helps!
you can do this by adding the following snippet to your urls.py
from django.contrib import admin
from django.urls import include, path
from django.conf import settings
from django.conf.urls.static import static
urlpatterns = [
path('admin/', admin.site.urls),
path('', include('online_shop.urls', namespace='online_shop')),
path('', include('products.urls', namespace='products')),
path('', include('orders.urls', namespace='orders')),
] + static(settings.STATIC_URL, document_root=settings.STATIC_ROOT)

Django dynamic filtering by passing slug from template

So I've read this article on dynamic filtering in Django; Dynamic filtering
Though I had something working I needed two similar views, one to show all different categories with their slug as parameter, and a second view to show all posts from all categories without a parameter.
How can I use a single ListView and pass an empty parameter from the template to show all posts from all categories in a list?
Or would this even be possible?
urls.py
urlpatterns = [
path('', views.PostListView.as_view(), name='index'),
path('<slug:slug>/', views.PostbyCategoryListView.as_view(), name="category"),
]
views.py
class PostListView(ListView):
model = Post
template_name = 'index.html'
class PostbyCategoryListView(ListView):
model = Post
template_name = 'index.html'
def get_queryset(self):
self.category = get_object_or_404(Category, slug=self.kwargs['slug'])
return Post.objects.filter(category=self.category)
index.html
...
<h6>Categories</h6>
{% if category_list %}
<ul>
<li class="category-item">
All categories
</li>
{% for category in category_list %}
<li class="category-item">
{{ category.name }}
</li>
{% endfor %}
</ul>
{% else %}
<p>No categories</p>
{% endif %}
...
models.py
class Category(models.Model):
name = models.CharField(max_length=200)
slug = models.CharField(max_length=200)
class Post(models.Model):
category = models.ForeignKey('Category',default=1, on_delete=models.SET_NULL, null=True, related_name="posts")
title = models.CharField(max_length=200)
content = models.TextField(max_length=2000)