Django:使用命名网址而不是ID

时间:2016-09-18 04:45:49

标签: python django

所以我正在制作一个涉及闪存卡的学习应用程序。用户可以制作主题并将包含卡片的卡片放入其中。因此,例如,在生物学科目中,将会有一个称为“单元一”的甲板,并且该甲板上将装满卡片。甲板的URL理想情况下看起来像

localhost:8000/subjects/Biology/unit-one/

这是我的代码

views.py

class IndexView(generic.ListView):
  template_name = 'card/index.html'
  context_object_name = 'subjects'

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

class SubjectView(DetailView):
  model = Subject
  slug_field = "subject"
  template_name = 'card/subject.html'

class DeckView(DetailView):
  model = Deck
  template_name = 'card/deck.html'

  def get_object(self, subjects, deck):
      subject_obj = Subject.objects.filter(subject_name=subjects).first()
      obj = Deck.objects.filter(subject=subject_obj, deck_name=deck).first()
      return obj

  def get(self, request, subjects, deck):
      self.object = self.get_object(subjects, deck)
      context = self.get_context_data(object=self.object)
      return self.render_to_response(context)

models.py

class Subject(models.Model):
  subject_name = models.CharField(max_length=100)
  description = models.TextField()

  def __str__(self):
      return self.subject_name

  def get_absolute_url(self):
      return reverse('card:index')

class Deck(models.Model):
  deck_name = models.CharField(max_length=100)
  subject = models.ForeignKey(Subject, on_delete=models.CASCADE)

  def __str__(self):
      return self.deck_name

class Card(models.Model):
  term = models.CharField(max_length=100)
  definition = models.TextField()
  deck = models.ForeignKey(Deck, on_delete=models.CASCADE)

  def __str__(self):
      return self.term

urls.py

url(r'^subjects/(?P<subject>[\w ]+)/$', views.SubjectView.as_view(), name='subject'),
url(r'^subjects/(?P<subject>[\w ]+)/(?P<deck>[\w ]+)/$', views.DeckView.as_view(), name='deck'),

的index.html

<li><a href="{% url 'card:subject' subject.subject_name %}">

subject.html

<ul>
  {% for deck in subject.deck_set.all %}
  <li><a href="{% url 'card:deck' deck.deck_name %}">{{deck.deck_name}}</a></li>
  {% endfor %}
</ul>

但是,我收到了这个错误。

Generic detail view SubjectView must be called with either an object pk or a slug.

索引页面显示正常,但是当我点击某个主题时,我收到了该错误。我该如何解决这个问题?

2 个答案:

答案 0 :(得分:1)

只是一个假设。请尝试将Char更改为Slug

class Subject(models.Model):
  subject_name = models.SlugField(max_length=100)
  description = models.TextField()

另外

slug_field = "subject_name"

答案 1 :(得分:0)

您是否尝试过设置SubjectView.slug_url_kwarg