Search code examples
pythondjangourlslug

how to use slug to form urls


my models.py file looks like this

from django.db import models
from django.template.defaultfilters import slugify

class Entertainmentblog(models.Model):

    slug = models.SlugField(max_length=100)
    body = models.TextField()
    posted = models.DateTimeField('date published')
    img_url0 = models.CharField(max_length=100)
    img_alt0 =  models.CharField(max_length=100)
    title1 = models.CharField(max_length=100)
    title2 = models.CharField(max_length=100)


    def save(self):
        super(Entertainmentblog, self).save()
        self.slug = '%i-%s' % ( self.id, slugify(self.slug) )
        super(Entertainmentblog, self).save()

And my app urls.py file looks like this

from django.conf.urls import patterns, url
from entertainment import views
urlpatterns = patterns('',
    url(r'^$', views.ListView.as_view(), name='index'),
    url(r'^(?P<slug>[^\.]+),(?P<id>\d+)/$', views.DetailView.as_view(), name='article'),
)

But this gives an error.

Exception Value: Reverse for 'article' with arguments '(u'what-is-happening',)' and keyword arguments '{}' not found. 1 pattern(s) tried: [u'entertainment/(?P[^\.]+),(?P\d+)/$']

My view.py file

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 entertainment.models import Entertainmentblog
class ListView(generic.ListView, slug, id):
   template_name = 'entertainment/index.html'
   context_object_name = 'latest_article_list'

def get_queryset(self):

    return Entertainmentblog.objects.order_by('-posted')[:25]

class DetailView(generic.DetailView):
   model = Entertainmentblog
   template_name = 'entertainment/article.html'     

How do I correct this?


Solution

  • Oh, there is serious problems with your views:

    First:

    class ListView(generic.ListView, slug, id)
    

    should be

    class ListView(generic.ListView)
    

    see python inheritance.

    Second:

    slug and id must be class members of your view so you can redefine you view like this:

    class ListView(generic.ListView):
       template_name = 'entertainment/index.html'
       context_object_name = 'latest_article_list'
       slug = None
       id = None
    
    def get_queryset(self):
    
        return Entertainmentblog.objects.order_by('-posted')[:25]
    

    Third:

    Youre naming a derivate class as its parent. I don't know the implications of doing this, but surely, isn't a good practice.

    Finally:

    The error you're getting is becouse the view returned by views.DetailView.as_view() (remember DetailView is your derived class) don't receives the arguments you are passing through url. Check your url, I can see in the error that is complaining about and argument (u'what-is-happening',) but there is no id. It should be something like, for example, (u'what-is-happening', '4')