0

I am following "django by example" and i met the problem but i don't know what causes it.

The following is the error page:


NoReverseMatch at /blog/ Reverse for 'post_detail' with arguments '('', '', '')' not found. 1 pattern(s) tried: ['blog/(?P\d{4})/(?P\d{2})/(?P\d{2})/(?P[-\w]+)/$']

Request Method: GET

Request URL: http://127.0.0.1:8000/blog/

Django Version: 1.11

Exception Type: NoReverseMatch

Exception Value: Reverse for 'post_detail' with arguments '('', '', '')' not found. 1 pattern(s) tried: ['blog/(?P\d{4})/(?P\d{2})/(?P\d{2})/(?P[-\w]+)/$']

Exception Location: E:\workspace\pycharm\djangobyexample\mysite\env\lib\site-packages\django\urls\resolvers.py in _reverse_with_prefix, line 497

Python Executable: E:\workspace\pycharm\djangobyexample\mysite\env\Scripts\python.exe

Python Version: 3.5.2

Python Path: ['E:\workspace\pycharm\djangobyexample\mysite', 'E:\workspace\pycharm\djangobyexample\mysite\env\Scripts\python35.zip', 'E:\workspace\pycharm\djangobyexample\mysite\env\DLLs', 'E:\workspace\pycharm\djangobyexample\mysite\env\lib', 'E:\workspace\pycharm\djangobyexample\mysite\env\Scripts', 'c:\users\richard\appdata\local\programs\python\python35\Lib', 'c:\users\richard\appdata\local\programs\python\python35\DLLs', 'E:\workspace\pycharm\djangobyexample\mysite\env', 'E:\workspace\pycharm\djangobyexample\mysite\env\lib\site-packages']



Main URLConfiguration

urlpatterns = [
    url(r'^admin/', admin.site.urls),
    url(r'^blog/', include('blog.urls', namespace='blog', app_name='blog')),
]

blog/url.py

from django.conf.urls import url
from . import views

urlpatterns = [
    # post views
    # url(r'^$', views.post_list, name='post_list'),
    url(r'^$', views.PostListView.as_view(), name='post_list'),
    url(r'^(?P<year>\d{4})/(?P<month>\d{2})/(?P<day>\d{2})/(?P<post>[-\w]+)/$',
        views.post_detail,
        name='post_detail'),
    #url(r'^(?P<post_id>\d+)/share/$', views.post_share, name='post_share'),
]

views.py

from django.shortcuts import render, get_object_or_404
from .models import Post
from django.core.paginator import Paginator, EmptyPage, PageNotAnInteger
from django.views.generic import ListView
from .forms import EmailPostForm
from django.core.mail import send_mail


# Create your views here.

class PostListView(ListView):
    queryset = Post.published.all()
    context_object_name = 'posts'
    paginate_by = 3
    template_name = 'blog/post/list.html'



def post_detail(request, year, month, day, post):
    post = get_object_or_404(Post, slug=post,
                             status='published',
                             publish__year=year,
                             publish__month=month,
                             publish__day=day)
    return render(request, 'blog/post/detail.html', {'post': post})

models.py

from django.db import models
from django.utils import timezone
from django.contrib.auth.models import User
from django.core.urlresolvers import reverse


class PublishedManager(models.Manager):
    def get_query(self):
        return super(PublishedManager, self).get_query().filter(status='published')


class Post(models.Model):
    STATUS_CHOICES = {
        ('draft', 'Draft'),
        ('published', 'Published'),
    }
    title = models.CharField(max_length=250, primary_key=True)
    slug = models.SlugField(max_length=250, unique_for_date='publish')
    author = models.ForeignKey(User, related_name='blog_post')
    body = models.TextField()
    publish = models.DateTimeField(default=timezone.now)
    created = models.DateTimeField(auto_now_add=True)
    updated = models.DateTimeField(auto_now=True)
    status = models.CharField(max_length=10, choices=STATUS_CHOICES, default='draft')

    class Meta:
        # Telling django to sort results by the publish field in descending order by default when we query the database
        ordering = ('-publish',)

    def __str__(self):
        return self.title

    objects = models.Manager()
    published = PublishedManager()

    def get_absolute_url(self):
        return reverse('blog:post_detail', args=[self.publish.year,
                                                 self.publish.strftime('%m'),
                                                 self.publish.strftime('%d'),
                                                 self.slug])

detail.html

{% extends "blog/base.html" %}

{% block title %}{{ post.title }}{% endblock %}

{% block content %}
    <h1>{{ post.title }}</h1>
    <p class="date">
        Published {{ post.publish }} by {{ post.author }}
    </p>
    {{ post.body|linebreaks }}

{% endblock %}

list.html

{% extends "blog/base.html" %}

{% block title %}My Blog{% endblock %}

{% block content %}
    <h1>My Blog</h1>
    {% for post in posts %}
        <h2>

            <a href="{{ post.get_absolute_url }}">
                {{ post.title }}
            </a>
        </h2>
        <p class="date">
            Published {{ post.publish }} by {{ post.author }}
        </p>
        {{ post.body|truncatewords:30|linebreaks }}
    {% endfor %}
    {% include "pagination.html " with page=page_obj %}
{% endblock %}

base.html

{% load staticfiles %}

<html>
<head>
    <meta charset="UTF-8">
    <title>{% block title %}{% endblock %}</title>

</head>
<body>
    <div id="content">
        {% block content %}
        {% endblock %}
        </div>
        <div id="sidebar">
            <h2>My blog</h2>
            <p>This is my blog.</p>
        </div>
</body>
</html>
Richard
  • 25
  • 1
  • 8

1 Answers1

2

This line is giving you the error, because the arguments are invalid.

<!-- <a href="{% url 'blog:post_detail' post.year post.month post.day %}">-->

The post does not have year, month and day attributes -- they are attributes of post.publish.

You are already using {{ post.get_absolute_url }} on the next line of the template to get the url. Since the url tag line is inside an html comment <!-- -->, the easiest fix is to simply delete the line.

Alasdair
  • 298,606
  • 55
  • 578
  • 516
  • Thanks for you reply, and i have alreay tried but it does not work. – Richard Apr 26 '17 at 14:39
  • If you remove that line then you should not get that error, unless you have `{% url 'blog:post_detail' ... %}` somewhere else in your template that you haven't shown us. – Alasdair Apr 26 '17 at 14:42
  • Thank you, i had checked my code again and there is no any other use of {% url 'blog:post_detail' ... %} or "xx.get_absolute_url". How should i do now .... – Richard Apr 26 '17 at 14:48
  • Try restarting your server to make sure that you're not running old code. If you don't have `{% url 'post_detail' ... %}`, `{% url 'blog:post_detail' ... %}`, `reverse('post_detail", ...)`, or `reverse('blog:post_detail", ...)` anywhere else in your code then you should not get that error message, so I can't help you solve it. – Alasdair Apr 26 '17 at 14:51
  • 1
    an important thing to learn from this is the fact that HTML comments will not prevent django from executing it's template code. so if you really need to comment something, you're better off using {% comment %} {% endcomment %} or {# 'this is your one line comment' #} – Brian H. Apr 26 '17 at 15:21