Passing data with CreateView in django - python

I am getting the error:
NOT NULL constraint failed: films_comment.film_id
On the comments page there is a form field called body for the comment itself, I also need it to store this comment against the user and the film.
Models:
from django.db import models
from django.urls import reverse
class Film(models.Model):
title = models.CharField(max_length=200)
director = models.CharField(max_length=200)
description = models.CharField(max_length=200)
pub_date = models.DateField('date published')
def get_absolute_url(self):
return reverse('films:detail', kwargs={'pk' : self.pk})
class Comment(models.Model):
# user = models.ForeignKey(User, on_delete=models.CASCADE)
user = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE)
film = models.ForeignKey(Film, on_delete=models.CASCADE)
body = models.CharField(max_length=200)
Views:
from django.views import generic
from .models import Film, Comment
from django.views.generic.edit import CreateView, UpdateView, DeleteView
class IndexView(generic.ListView):
# model = Film
template_name = 'films/index.html'
# context_object_name = 'object_list'
def get_queryset(self):
return Film.objects.all()
class DetailView(generic.DetailView):
model = Film
template_name = 'films/detail.html'
class CommentCreate(CreateView):
model = Comment
fields = ['body']
Urls:
app_name = 'films'
urlpatterns = [
path('', views.IndexView.as_view(), name='index'),
# path('<int:film_id>/comment', views.add_comment, name='add_comment'),
path('<int:pk>', views.DetailView.as_view(), name='detail'),
path('<int:film_id>/comment/', views.CommentCreate.as_view(), name='add_comment'),
]
Link on details page for adding a comment:
Leave a comment
comment_form.py:
<form action="" method="post">
{% csrf_token %}
{% include 'films/form-template.html' %}
<button type="submit">Submit</button>
</form>
Form template:
{% for field in form %}
{{field.errors}}
<label>{{ field.label_tag }}</label>
{{ field }}
{% endfor %}
forms.py
from django import forms
from .models import Comment
class CommentForm(forms.ModelForm):
class Meta:
model = Comment
fields = ('body',)

You need to override view's form_valid method to update new comment instance with current user and film:
class CommentCreate(CreateView):
model = Comment
fields = ['body']
def form_valid(self, form):
film = Film.objects.get(pk=self.kwargs['film_id'])
form.instance.user = self.request.user
form.instance.film = film
return super(CommentCreate, self).form_valid(form)
To fix "No URL redirect to" you can add get_absolute_url() method to the Comment model:
def get_absolute_url(self):
return reverse('detail', kwargs={'pk': self.film.pk})

Related

models.py order of the models gives NameError: name 'Category/Post' is not defined

I'm new to Django so this is probably a dumb question but,
when I put the class Category model above the class Post model I get an
NameError: name 'Post' is not defined error.
but when I try to put class Category model underneath the Post model (as in the code here) I get
categories = models.ManyToManyField(Category)
NameError: name 'Category' is not defined error.
models.py
class Post(models.Model):
title = models.CharField(max_length=100)
content = models.TextField()
date_posted = models.DateTimeField(default=timezone.now)
author = models.ForeignKey(User, on_delete=models.CASCADE) #if is deleted than delete their posts
location = models.CharField(max_length=100, default="")
tags = TaggableManager()
likes = models.ManyToManyField(User, related_name='blog_posts')
categories = models.ManyToManyField(Category)
def total_likes(self):
return self.likes.count()
def __str__(self):
return self.title
def get_absolute_url(self):
return reverse('post-detail', kwargs={'pk': self.pk})
class Category(models.Model):
post = models.ForeignKey(Post, related_name="categories")
name = models.CharField(max_length=20)
def __str__(self):
return self.name
admin.py
from django.contrib import admin
from .models import Post, Comment, Category #, Konum
# Register your models here.
admin.site.register(Post)
admin.site.register(Comment)
admin.site.register(Category)
#admin.site.register(Konum)
some of the code
<form method="GET" action=".">
<div class="form-group col-md-4">
<label for="category">Category</label>
<select id="category" class="form-control" name="category">
<option selected>Choose...</option>
{% for cat in categories %}
<option value="{{ cat }}">{{ cat }}</option>
{% endfor %}
</select>
</div>
<button type="submit" class="btn btn-primary">Search</button>
</form>
views.py
def home(request):
context = {
"posts": Post.objects.all()
}
return render(request, 'blog/home.html', context)
#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------
#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------
#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------
#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------
#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------
#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------#--------------------------------------------------------------------------------------------------------------------------------------
#--------------------------------------------------------------------------------------------------------------------------------------
def filter(request):
qs = Post.objects.all()
categories = Category.objects.all()
id_exact_query = request.GET.get('id_exact')
title_or_author_query = request.GET.get('title_or_author')
category = request.GET.get('category')
if is_valid_queryparam(category) and category != 'Choose...':
qs = qs.filter(categories__name=category)
context = {
'posts': qs,
'categories': Category.objects.all()
}
return render(request, 'blog/home.html', context)
class PostListView(ListView):
model = Post
template_name = 'blog/home.html'
context_object_name = 'posts'
ordering = ['-date_posted']
paginate_by = 199
class UserPostListView(ListView):
model = Post
template_name = 'blog/user_posts.html'
context_object_name = 'posts'
paginate_by = 199
def get_queryset(self):
return Post.objects.filter(author = user).order_by('-date_posted')
urls.py
from django.urls import path, re_path
from .import views
from .views import PostListView, PostDetailView, PostCreateView, PostUpdateView, PostDeleteView, UserPostListView, TagIndexView, LikeView #, LocationPostListView
urlpatterns = [
path('', PostListView.as_view(), name="blog-home"), #has a empty strting bc its already processed blog part in main urls
path('user/<str:username>', UserPostListView.as_view(), name="user-posts"),
#--------------------------------------------------------------------------------------------------------------------------------------
#path('location/<str:loc>', LocationPostListView.as_view(), name="location-posts"),
#--------------------------------------------------------------------------------------------------------------------------------------
path('post/<int:pk>/', PostDetailView.as_view(), name='post-detail'),#pk means primary key like post 1 post 2 etc
path('post/new/', PostCreateView.as_view(), name='post-create'),
path('post/<int:pk>/update/', PostUpdateView.as_view(), name='post-update'),
path('post/<int:pk>/delete/', PostDeleteView.as_view(), name='post-delete'),
path('about/', views.about, name="blog-about"),
#--------------------------------------------------------------------------------------------------------------------------------------
path('tag/<slug:slug>/', TagIndexView.as_view(), name='tagged'),
path('like/<int:pk>', LikeView, name='like_post'),
#--------------------------------------------------------------------------------------------------------------------------------------
]
You can use a string literal to specify the model name of a model that still needs to be defined, so you can use ManyToManyField('Category') or ForeignKey('Post', on_delete=models.CASCADE) for example to refer to models not yet defined:
from django.conf import settings
class Post(models.Model):
title = models.CharField(max_length=100)
content = models.TextField()
date_posted = models.DateTimeField(default=timezone.now)
author = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE)
location = models.CharField(max_length=100, default="")
tags = TaggableManager()
likes = models.ManyToManyField(settings.AUTH_USER_MODELS, related_name='liked_posts')
categories = models.ManyToManyField('Category')
It however does not seem to make much sense that a Category has a ForeignKey to a post: that would mean that a Category links to exactly one Post record?
You can for example use a ListView with:
class PostListView(ListView):
model = Post
template_name = 'blog/home.html'
context_object_name = 'posts'
ordering = ['-date_posted']
paginate_by = 199
def get_queryset(self):
qs = super().get_queryset()
if self.request.GET.get('category'):
return qs.filter(categories__name=self.request.GET['category'])
return qs
def get_context_data(self, *args, **kwargs):
context = super().get_queryset(*args, **kwargs)
context['categories'] = Category.objects.all()
return context
Note: It is normally better to make use of the settings.AUTH_USER_MODEL [Django-doc] to refer to the user model, than to use the User model [Django-doc] directly. For more information you can see the referencing the User model section of the documentation.

How to use Django url template tag with variable as url path

I encountered a No Reverse Match Error in trying to render a template. Can you explain what this No Reverse Match Error mean for easier understanding and how to solve the error?
models.py
from django.contrib.sites.models import Site
from django.contrib.gis.db import models
from django.utils.crypto import get_random_string
from django.contrib.gis.geos import GEOSGeometry,Point
from django.contrib.auth.models import AbstractUser
from django.shortcuts import render
# Create your models here.
class User(AbstractUser):
pass
geos_pnt=Point(4314498.56, 1003834.600,srid=3857)
#pnt=GEOSGeometry('POINT(4314498.56, 1003834.600)').wkt
class Apartment(models.Model):
SUBCITY_CHOICES = (
('ADK', 'Addis Ketema'), ('AKLTY', 'Akaki-Kality'), ('ARD', 'Arada'), ('BL', 'Bole'), ('GL', 'Gulele'),
('KLF', 'Kolfe-Keranio'), ('LDTA', 'Ledeta'), ('NFS', 'Nefas Silk'), ('YK', 'Yeka'))
apt_id = models.CharField(str(SUBCITY_CHOICES)+"-"+get_random_string(length=4), max_length=8,primary_key=True)
location = models.PointField(default=geos_pnt,extent=(4282586.10,996190.90,4346411.02,1011478.31),
blank=True, null=True, srid=3857, help_text="Point(longitude latitude)")
no_bedrooms= models.IntegerField(null=True)
apt_area = models.IntegerField(default=0, null=True)
apt_cost = models.IntegerField(default=0, null=True)
apt_subcity = models.CharField(default='Nefas Silk',max_length=100, choices=SUBCITY_CHOICES,null=True)
register_date = models.DateTimeField('Register Date',auto_now_add=True,null=True)
slug = models.SlugField(unique=True)
objects = models.Manager()
sites =models.ManyToManyField(Site)
#change points from apt_rent_db to kml
def pointkml(self):
points = Apartment.objects.kml()
return render("placemarks.kml", {'places': points})
def get_absolute_url(self):
return reverse('apartment_create', kwargs={'pk': self.pk, 'apt_id': self.apt_id.pk})
def save(self, *args, **kwargs):
#self.Latitude = self..y
#self.Longitude = self.location.x
self.slug = slugify(self.apt_id)
super(Apartment, self).save(*args, **kwargs)
class Meta:
# order of drop-down list items
verbose_name = ("Apartment")
verbose_name_plural = ("Apartments")
ordering = ('apt_cost',)
app_label = 'rent_app'
def __unicode__(self):
return self.apt_id
urls.py:
from django.urls import path
from . import views
app_name = 'rent_app'
urlpatterns = [
path('', views.IndexView.as_view(), name='index'),
path('apartment_create/<slug:apt_id>)', views.ApartmentCreate.as_view(), name='apartment_create'),
path('apartments/<int:pk>/', views.ApartmentUpdate.as_view(), name='apartment_update'),
path('apartments/<int:pk>/delete/', views.ApartmentDelete.as_view(), name='apartment_delete'),
]
views.py:
from django.urls import reverse_lazy
from django.views import generic
from django.views.generic.edit import CreateView, DeleteView, UpdateView
from .models import Apartment
from .forms import ApartmentCreateForm
class IndexView(generic.ListView):
template_name = 'djnago_leaflet.html'
context_object_name = 'latest_apartments_list'
def get_queryset(self):
"""Return the last five published apartments."""
return Apartment.objects.order_by('-register_date')[:5]
class ApartmentCreate(CreateView):
template_name = 'rent_app/apartment-create-success.html'
form_class = ApartmentCreateForm
fields = ['apt_id','location','apt_area','apt_cost']
success_url= reverse_lazy('apartment-create')
class ApartmentUpdate(UpdateView):
model = Apartment
fields = ['apt_id','location','apt_area', 'apt_cost']
template_name='index_leaflet.html'
template_name_suffix='apartments'
class ApartmentDelete(DeleteView):
model = Apartment
template_name = 'index_leaflet.html'
template_name_suffix='apartments'
success_url = reverse_lazy('apartment-list')
the html:
<html>
<head>
{% leaflet_js plugins="forms" %}
{% leaflet_css plugins="forms" %}
</head>
<body>
{% leaflet_map "map" callback="window.map_init_basic" %}
<h2>Edit Apartment ID {{ Apartment.apt_id }}</h2>
<h2>Edit Apartment Location {{ Apartment.location }}</h2>
<form action="{% url 'rent_app:apartment_create' apt_id %}" method="post">
{% csrf_token %}
{{ form }}
<input type="submit"/>
</form>
</body>
</html>
I think there are a number of issues in your code.
First regarding the error you are seeing. In your urls you have defined a pattern with the name 'apartment_create' which expects a slug as a parameter. However, apt_id in your template is an empty field. So django cannot find a pattern with the name 'apartment_create' and a valid slug. To solve this change the url pattern to
path('apartment_create/', views.ApartmentCreate.as_view(), name='apartment_create')
And in your template either take out the apt_id from your action in the form (or take out the action all together.
However, in your ApartmenCreate view you are missing the model parameter. In addition the fields and the form parameter are redundant. And are you sure the template_name parameter in that view is correct?
In your model the field apt_id looks strange. You are creating a field with some very obscure verbose_name. If you want to have a choice field you have to set the choices parameter of the field, e.g.:
apt_id = models.CharField(choices=SUBCITY_CHOICES, max_length=8, primary_key=True)
Your get_absolute_url is also not correct: First of all there is no valid url matching that pattern and secondly a field (apt_id) does not have a pk.
In your template you have statements like {{ Apartment.apt_id }}. However, Apartment is a class. So in your views add context_object_name='apartment' so you can access the values in your template like so {{ apartment.apt_id }}.
There are probably some other issues which I have overlooked.

Unable to use data of one app in another in Django

I have three apps (Internship, UserProfile and Infrastructure) in my django project. I have made models Profile and StudentProject in UserProfile Model. The StudentProject Model contains two foreign key-> user and Lab (this model is defined in the Infrastructure model). In a template(details.html file) in Infrastructure app, i want to retrieve all StudentProjects who have their foreign key as the lab whose details are currently being shown. I am unable to bring the student projects created here. Please help someone. I have already tried to use filter but it doesn't work!
userprofile/models.py file
from django.conf import settings
from django.db import models
from django.core.urlresolvers import reverse
from infrastructure.models import Lab
class Profile(models.Model):
user = models.OneToOneField(settings.AUTH_USER_MODEL, on_delete=models.CASCADE)
name = models.CharField(max_length=100)
type = models.CharField(max_length=100)
profile_picture = models.FileField()
skills = models.CharField(max_length=1000)
def get_absolute_url(self):
return reverse('userprofile:index')
def __str__(self):
return self.name
class StudentProject(models.Model):
user = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE)
title = models.CharField(max_length=100)
project_picture = models.FileField()
lab = models.ForeignKey(Lab)
mentor = models.CharField(max_length=100)
domain = models.CharField(max_length=100)
description = models.CharField(max_length=1000)
def __str__(self):
return self.title
def get_absolute_url(self):
return reverse('userprofile:index')
infrastructure/models.py file
from django.db import models
from django.core.urlresolvers import reverse
class Lab(models.Model):
name = models.CharField(max_length=100)
department = models.CharField(max_length=100)
description = models.CharField(max_length=1000)
lab_logo = models.FileField()
def get_absolute_url(self):
return reverse('infrastructure:details', kwargs={'pk': self.pk})
def __str__(self):
return self.name
infrastructure/templates/details.html
->This is where i want all student projects of lab to be shown
{% extends 'infrastructure/base.html' %}
{% block body %}
<h1>This is details page</h1>
<img src="{{ lab.lab_logo.url }}" style="width: 300px;">
<h1>{{ lab.name }}</h1>
<h2>{{lab.projects}}</h2>
{% endblock %}
infrastructure/views.py file
from django.core.urlresolvers import reverse_lazy
from django.views import generic
from infrastructure.models import Lab
from django.views.generic.edit import CreateView, UpdateView, DeleteView
class IndexView(generic.ListView):
template_name = 'infrastructure/index.html'
context_object_name = 'all_labs'
def get_queryset(self):
return Lab.objects.all()
class DetailView(generic.DetailView):
model = Lab
template_name = 'infrastructure/details.html'
class LabCreate(generic.CreateView):
model = Lab
fields = ['name', 'department', 'description', 'lab_logo']
class LabUpdate(generic.UpdateView):
model = Lab
fields = ['name', 'department', 'description', 'lab_logo']
class LabDelete(DeleteView):
model = Lab
success_url = reverse_lazy('infrastructure:index')
infrastructure/urls.py file
from django.conf.urls import url
from . import views
app_name = 'infrastructure'
urlpatterns = [
url(r'^$', views.IndexView.as_view(), name='index'),
url(r'^(?P<pk>[0-9]+)/$', views.DetailView.as_view(), name='details'),
url(r'^lab/add/$', views.LabCreate.as_view(), name='lab-add'),
url(r'^lab/(?P<pk>[0-9]+)/$', views.LabUpdate.as_view(), name='lab-update'),
url(r'^lab/(?P<pk>[0-9]+)/delete/$', views.LabDelete.as_view(), name='lab-delete'),
]
userprofile/views.py file
from django.contrib.auth import login, authenticate, logout
from django.http import request
from django.shortcuts import render, redirect, get_object_or_404
from django.urls import reverse_lazy
from .models import Profile, StudentProject
from django.views.generic.edit import CreateView, UpdateView, DeleteView
from .forms import UserForm
from django.views import generic
from django.views.generic import View
class IndexView(generic.TemplateView):
template_name = 'userprofile/index.html'
context_object_name = 'user_profile'
def get_queryset(self):
return request.user.get_profile()
class ProfileCreate(CreateView):
model = Profile
fields = ['user', 'name', 'type', 'profile_picture', 'skills']
class ProfileUpdate(UpdateView):
model = Profile
fields = ['user', 'name', 'type', 'profile_picture', 'skills']
class StudentProjectCreate(CreateView):
model = StudentProject
fields = ['user', 'title', 'project_picture', 'lab', 'mentor', 'domain', 'description']
class StudentProjectUpdate(UpdateView):
model = StudentProject
fields = ['user', 'title', 'project_picture', 'lab', 'mentor', 'domain', 'description']
class StudentProjectDelete(DeleteView):
model = StudentProject
success_url = reverse_lazy('userprofile:index')
def logout_view(request):
logout(request)
return render(request, 'userprofile/logout.html')
# for new user
class UserFormView(View):
form_class = UserForm
template_name= 'internship/registration_form.html'
# display blank form
def get(self, request):
form = self.form_class(None)
return render(request, self.template_name, {'form': form})
# process from data
def post(self, request):
form = self.form_class(request.POST)
if form.is_valid():
user = form.save(commit=False)
# cleaned (normalized) data
username = form.cleaned_data['username']
password = form.cleaned_data['password']
user.set_password(password)
user.save()
# return User object if credentials are correct
user = authenticate(username=username, password=password)
if user is not None:
if user.is_active:
login(request, user)
return redirect('userprofile:profile-add')
return render(request, self.template_name, {'form': form})
userprofile/urls.py file
from django.conf.urls import url, include
from django.contrib.auth import views as auth_views
from userprofile import views
app_name = 'userprofile'
urlpatterns = [
url(r'^$', views.IndexView.as_view(), name='index'),
url(r'^profile/add/$', views.ProfileCreate.as_view(), name='profile-add'),
url(r'^profile/(?P<pk>[0-9]+)/$', views.ProfileUpdate.as_view(), name='profile-update'),
url(r'^logout$', views.logout_view, name='logout_view'),
url(r'^login/$', auth_views.login, {'template_name': 'userprofile/login.html'}),
url(r'^register/$', views.UserFormView.as_view(), name='register'),
url(r'^studentproject/add/$', views.StudentProjectCreate.as_view(), name='student-project-add'),
url(r'^studentproject/(?P<pk>[0-9]+)/$', views.StudentProjectUpdate.as_view(), name='student-project-update'),
url(r'^studentproject/(?P<pk>[0-9]+)/delete/$', views.StudentProjectDelete.as_view(), name='student-project-delete'),
]
Basically, you need to add related_name argument to your declaration of Lab Field in StudentProject Model. That will make children accessible from parent Model further:
class StudentProject(models.Model):
user = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE)
title = models.CharField(max_length=100)
project_picture = models.FileField()
lab = models.ForeignKey(Lab, related_name=projects)
...
And now, in your template, you can easily iterate over your current lab's projects:
{% extends 'infrastructure/base.html' %}
{% block body %}
<h1>This is details page</h1>
<img src="{{ lab.lab_logo.url }}" style="width: 300px;">
<h1>{{ lab.name }}</h1>
{% for project in lab.projects_set.all %}
<h2>{{project.title}}</h2>
{% endfor %}
{% endblock %}

How to display Model data in a Django Template

I am new to Django. I am trying to display data from my Project model in my index view, using a template. I tried my best to structure this app similar to the polls app. I'm not sure what I am doing wrong. I am using python 2.7, and django 1.8.6
Here is my url:
from django.conf.urls import url
from . import views
app_name = 'project'
urlpatterns = [
url(r'^$', views.IndexView.as_view(), name='index'),
url(r'^(?P<pk>[0-9]+)/$', views.DetailView.as_view(), name='detail'),
]
Here is my Model:
import datetime
from django.db import models
from django.utils.encoding import python_2_unicode_compatible
from django.contrib.auth.models import User
from django.utils import timezone
#python_2_unicode_compatible # only if you need to support Python 2
class Contractor(models.Model):
#project
name = models.CharField(max_length=50)
address = models.CharField(max_length=100, blank=True)
phone = models.CharField(max_length=14, blank=True)
city = models.CharField(max_length=60, blank=True)
state = models.CharField(max_length=2, blank=True)
created_by = models.ForeignKey(User, related_name='Contractor_created_by')
created_date = models.DateTimeField()
modified_by = models.ForeignKey(User, related_name='Contractor_modified_by')
modified_date = models.DateTimeField()
def __str__(self):
return self.name
#python_2_unicode_compatible # only if you need to support Python 2
class Project(models.Model):
name = models.CharField(max_length=50)
jobNumber = models.CharField(max_length=8)
shopOut = models.DateTimeField(null=True)
shopIn = models.DateTimeField(null=True)
delivery = models.DateTimeField(null=True)
job1 = models.CharField(max_length=50, null=True)
job2 = models.CharField(max_length=50, null=True)
job3 = models.CharField(max_length=50, null=True)
contractor = models.ForeignKey(Contractor, on_delete=models.CASCADE, default=101)
created_by = models.ForeignKey(User, related_name='Project_created_by')
created_date = models.DateTimeField(auto_now_add=True)
modified_by = models.ForeignKey(User, related_name='Project_modified_by')
modified_date = models.DateTimeField(auto_now=True)
def __str__(self):
return self.name
def save(self, *args, **kwargs):
if not self.id:
self.created_by = User.objects.get(id=1)
self.modified_by = User.objects.get(id=1)
super(Project, self).save(*args, **kwargs)
year = datetime.datetime.now().year
self.jobNumber = '{}{:04d}'.format(year, self.id)
self.modified_by = User.objects.get(id=1)
super(Project, self).save(*args, **kwargs)
Here is my View:
from django.shortcuts import get_object_or_404, render
from django.http import HttpResponseRedirect
from django.core.urlresolvers import reverse
from django.views import generic
from django.utils import timezone
from .models import Project
# Create your views here.
class IndexView(generic.ListView):
model = Project
template_name = 'project/index.html'
def get_queryset(self):
return Project.objects
class DetailView(generic.DetailView):
model = Project
Here is my Template:
{% load staticfiles %}
<h1>Projects</h1>
<ul>
{% for projects in project.get_queryset %}
in for loop
<!-- <li>{{ projects.name }}</li> -->
<li>Test</li>
{% endfor %}
</ul>
end of list
When I go to the page I get a h1 Project, an empty ul, and a line that says 'end of list'
In your get_queryset, you should return Project.objects.all().
In your template, you don't need to do project.get_queryset, the get_queryset method is called for you and the values are passed to the template as object_list and <objectname>_list, along with other parameters. In your case, the object is Project so there should be a project_list variable too along with object_list.
You can do:
{% for project in project_list %}
<li>{{ project.name }}</li>
{% endfor %}
Or:
{% for project in object_list %}
<li>{{ project.name }}</li>
{% endfor %}
You can read more about it here: https://docs.djangoproject.com/en/1.9/ref/class-based-views/generic-display/#listview
Your get queryset doesn't return a query set at the minute, currently its just returning a related manager. you should make it return a queryset...
def get_queryset(self):
return Project.objects.all() # added all
You might want to try:
{% for project in object_list %}
<li>{{ project.name }}</li>
{% endfor %}
object_list is the default name of queryset if you use ListView, you can change that by defining context_object_name in your view. Here's django doc about that.

Problems with rendering page on Django framework

I have categories of the news and news and i don't know how to render the page with the list of news that belong to the same category. Hope You will help me with that.
this is my model.py file:
from django.db import models
class Category(models.Model):
class Meta:
verbose_name_plural = u'Categories'
category = models.CharField(max_length=255)
slug = models.CharField(max_length=255)
def __unicode__(self):
return self.category
class News(models.Model):
class Meta:
verbose_name_plural = u'News'
title = models.CharField(max_length=255)
category = models.ForeignKey(u'Category', related_name=u'Category', blank=True, null=True)
pub_date = models.DateTimeField('date published')
slug = models.CharField(max_length=255)
short_content=models.TextField(max_length=2000, blank=True)
content = models.TextField(max_length=10000)
image = models.FileField(u'Images', upload_to='media/img/news', blank=True)
def __unicode__(self):
return self.title
views.py:
from django.shortcuts import render
from django.views.generic import ListView, DetailView
from news.models import News
class NewsListView(ListView):
template_name ='news/list.html'
context_object_name = 'news_list'
def get_queryset(self):
return News.objects.order_by('-pub_date') [:5]
class NewsDetailView(DetailView):
model=News
template_name = 'news/detail.html'
def CategoryNews(request, categoryslug):
category = Category.objects.get(slug=categoryslug)
news = News.objects.filter(category=category)
return render (request, 'news/category_news.html', {'category' : category})
urls.py:
django.conf.urls import patterns, url
from news.views import NewsListView, NewsDetailView
from news import views
urlpatterns = patterns('',
url(r'^$', NewsListView.as_view(), name='list'),
url(r'^(?P<slug>[-_\w]+)/$', NewsDetailView.as_view()),
url(r'^kids-garden/$', views.CategoryNews),
)
Thank You!
On CategoryNews view add news to render context. This will make news items available in templates.
def CategoryNews(request, categoryslug):
category = Category.objects.get(slug=categoryslug)
news = News.objects.filter(category=category)
return render (request, 'news/category_news.html', {'category' : category, 'newsitems': news})
Add named group to category url to make it dynamic.
Rewrite
url(r'^kids-garden/$', views.CategoryNews, name='category'),
to
url(r'^category/(?P<categoryslug>\w+)/$', views.CategoryNews, name='category'),
In category_news.html
{%for news in newsitems%}
{{ news.title }}
{{ news.content }}
# rest values...........
{% endfor %}
I think this should do the job:
views.py
....
from news.models import News, Category
def CategoryNews(request, categoryslug):
category_news = News.objects.filter(category__slug='categoryslug')
return render (request, 'news/category_news.html', {'category_news' : category_news})

Categories

Resources