2

I'm trying to get to grips with class based views.

I have urls.py as follows:

urlpatterns = patterns('homework.views',

(r'^index/$', 'index'),
url(r'^(?P<sub_slug>\w+)/$', NavListView.as_view(), name='nav'),
url(r'^(?P<sub_slug>\w+)/(?P<class_grp_slug>\w+)/$', SubNavListView.as_view(), name='subnav'),

url(r'^admin/doc/', include('django.contrib.admindocs.urls')),
url(r'^admin/', include(admin.site.urls)),)

I have my views.py:

# Subject navigation
class NavListView(ListView):
    template_name = 'templates/home.html'

    def get_queryset(self):
        self.subject = Subject.objects.all()
        return self.subject

    def get_context_data(self, **kwargs):
        context = super(NavListView, self).get_context_data(**kwargs)
        context['subjects'] = self.subject
        return context

# Class group navigation
class SubNavListView(NavListView):

    def get_queryset(self):
        self.group = Group.objects.filter(subject__name__iexact=self.kwargs['sub_slug'])
        return self.group

    def get_context_data(self, **kwargs):
        context = super(NavListView, self).get_context_data(**kwargs)
        context['groups'] = self.group
        return context

In my 'templates/home.html' I have:

{% extends 'templates/base.html' %}
{% load url from future %}

{% block nav-menu-items %}
<ul class="nav">
    {% for sub in subjects %}
    <li class=""><a href="{% url 'nav' sub_slug %}">{{ sub }}</a></li>
    {% endfor %}
    <li class="active"><a href="#">Add Subject</a></li>
</ul>
{% endblock nav-menu-items %}

{% block class_groups_nav %}
<div class="tabbable">
  <ul class="nav nav-tabs">
    {% for group in groups %}
    <li>
      <a data-toggle="tab" href="{% url 'subnav' sub_slug class_grp_slug %}">{{ group }}</a>
    </li>
    {% endfor %}
    <li><a href="#">Add</a></li>
  </ul>
{% endblock class_groups_nav %}

I'm trying to achieve a 'nav' of subjects, then a 'subnav' below showing a tab for each class group for the subject selected in the navigation above.

I've tried different ways of doing this such as making Subject.objects.all() available as context processors. I have also attempted to subclass NavListView so I can inherit the previous context, making them available in SubNavListView.

At the moment, I'm getting a NoReverseMatch error where the url named 'nav' is not passing the sub_slug and so I can't use it in the url in the template.

Any thoughts on getting this working?

Many thanks,

1 Answer 1

1

Assuming your Subject model has field named slug in it, you need to update your code to

<li class=""><a href="{% url 'nav' sub.slug %}">{{ sub }}</a></li>

ie. pass an appropriate parameter to {%url ... %}. Change sub.slug to whatever field name you want to refer to.

If you want to, you can also do {% url 'nav' sub_slug=sub.slug %}.

You are trying to pass sub_slug, but which is not defined in the template context, and result in empty string. So nav url will not get any parameter.

I see similar problem in your other {%url ...%} tags in the template.

Sign up to request clarification or add additional context in comments.

2 Comments

Thanks for your answer. So, are the named parts of the url <sub_slug> and <class_grp_slug>, passed as *args to the function, but not into the context when the template is rendered?
@puffin, yes, {% url ...%} expects name of url and value that needs to be passed to view (if any defined in url pattern) not the variable name.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.