Search code examples
pythondjangodjango-templatesdjango-urlsslug

Django Template changing html attribute based on slug and current request


When I tried to iterate through a list of post titles to create links in a django template the urls never match the requested path (matching the current web page should alter the formatting on the page for that list item). When I try and change things, Django spits out a 404 error which doesn't let me diagnose the problem or it "works" but not as expected.

the relevant url patterns (in blog app within project):

path('', views.index, name='blog_index'), 
path('<slug:post>', views.blog_post, name='entries')  

the relevant views functions (in blog app within project):

ef index(request):
    try:
        return render(request, 'blog/index.html', {'posts':blog_posts.keys})
    except:
        raise Http404()

def blog_post(request, post):
    try:
        return render(request, 'blog/post.html', {
            'post_title':post,
            'post_content':blog_posts[],
            'posts':blog_posts.keys
            })
    except:
       raise Http404()

the navigation template:

<ul>
   {% for post in posts %}
   {% url "blog:entries" "{{post}}" as blog_entry %}
   <li><a href="/blog/{{post}}" {% if request.path == blog_entry %} class="active"{% endif %}>
   <span class="item">{{post}}</span>
   </a></li>
   {% endfor %}
</ul>

I suspect the {% url "blog:entries" "{{post}}" as blog_entry %} in the template is not resolving correctly as when I replace the href with {% blog_entry %} it causes a 404 error.

I have tried hard coding it in, I have tried different ways of writing the url, I have tried changing the syntax (in case I am doing it incorrectly. I have checked the page source when I have run tests. I have never been able to get the class attribute to be "active" when on the matching page.

EDIT: The links all go to the correct pages, however the IF logic in the template does not work. i.e. None of the changes I have tried make result in reques.path == blog_entry resolving as True.
Also the above code snippets are part of an App within a project and I have included more of the views.py and urls.py file. Currently I have the "blog posts" stored in a dictionary at the top of views.py for testing.


Solution

  • Try this:

    <ul>
       {% for post in posts %}
       {% url "blog:entries" post=post as blog_entry %}
       <li><a href="/blog/{{post}}" {% if request.path == blog_entry %} class="active"{% endif %}>
       <span class="item">{{post}}</span>
       </a></li>
       {% endfor %}
    </ul>