Django абсолютный URL не работает в HTML-шаблон - PullRequest
0 голосов
/ 07 января 2019

Прежде чем опубликовать этот вопрос, я попробовал несколько решений, но без вены, возможно, потому что у меня мало опыта в django и веб-разработке. Я хочу показать название курса в навигационном меню. Тем не менее, он показывает пустые места. Используя Django 2.1.4, модель выглядит следующим образом:

class Course(model.Model):
    title = models.CharField(max_length=128)
    description = RichTextUploadingField(default='No description available.')

    def __str__(self):
        return self.title

    def get_absolute_url(self):
        return reverse('course-detail', kwargs={'pk': self.pk})

Редактировать: добавление модели урока

Модель урока имеет много-много связей с курсом. Это выглядит следующим образом:

class Lesson(models.Model):
    title = models.CharField(max_length=512)
    content = RichTextUploadingField()
    course = models.ManyToManyField(Course)

    def __str__(self):
        return self.title

    def get_absolute_url(self):
        return reverse('lesson-detail', kwargs={'pk': self.pk})

views.py содержит следующие представления

class CourseListView(ListView):
    model = Course
    template_name = 'courses/courses.html'
    context_object_name = 'courses'
    paginate_by = 10


class CourseDetailView(DetailView):
    model = Course
    template_name = 'courses/course-detail.html'

class LessonDetailView(DetailView):
    model = Lesson
    template_name = 'courses/lesson-details.html'

В URL-адресах указывается следующее:

path('', CourseListView.as_view(), name = 'course-list'),

path('course/<int:pk>/', CourseDetailView.as_view(), name = 'course-detail'),

path('lesson/<int:pk>/', LessonDetailView.as_view(), name = 'lesson-detail'),

В html-шаблон lesson-detail включена следующая нивелирование панировочных сухарей:

<!-- ##### Breadcumb Area Start ##### -->
<div class="breadcumb-area">
    <!-- Breadcumb -->
    <nav aria-label="breadcrumb">
        <ol class="breadcrumb">
            <li class="breadcrumb-item"><a href="{% url 'home' %}">Home</a></li>
            <li class="breadcrumb-item"><a href="{% url 'course-list' %}">Courses</a></li>
            <li class="breadcrumb-item"><a href="{{ course.get_absolute_url }}">{{course.title}}</a></li> {% comment%} This doesn't work {%endcomment%}
            <li class="breadcrumb-item active" aria-current="page">{{ lesson.title }}</li>
            <li></li>
        </ol>
    </nav>
</div>

Как я могу заставить это работать? Название курса «музыка», желаемый результат выглядит как HOME / COURSES / MUSIC / FLUTE. Я хочу иметь возможность включить URL-адрес курса в нескольких местах на веб-сайте, в том числе бегущий текст

Ваша помощь высоко ценится!

1 Ответ

0 голосов
/ 07 января 2019

LessonDetailView не имеет никакой сверхдержавы, он не может предположить, что вы хотите иметь Course экземпляр в контексте вашего шаблона или какой именно вы хотите. В результате шаблон не может разрешить имя course и действительно выдает пустую строку.

Хорошая новость заключается в том, что при условии, что ваша Lesson модель (которую вы забыли опубликовать) имеет ForeignKey на Course, то есть:

class Lesson(models.Model):
    course = models.ForeignKey(Course, ....)
    # etc

тогда вы можете получить связанный экземпляр курса из экземпляра lesson, то есть:

<li class="breadcrumb-item">
  {% with course=lesson.course %}
  <a href="{{ course.get_absolute_url }}">{{course.title}}</a></li>
  {% endwith %}
</li> 

EDIT:

Может быть потому, что модель имеет много-много отношений и требует другого решения

Ну да, действительно. И прежде чем углубляться в детали реализации, просто спросите себя, как узнать, какой из связанных курсов следует выбрать, если у вас есть только идентификатор урока? Ответ: вы не можете. IOW, вы должны сделать идентификатор курса частью шаблона url для вида урока:

path('lesson/<int:course_id>/<int:pk>/', LessonDetailView.as_view(), name = 'lesson-detail'),

затем обновите ваше представление так, чтобы оно получало идентификатор курса, извлекало курс из БД и вставляло его в контексте (nb: непроверенный код, поэтому он может не работать из коробки - но у вас есть очень полная документация, чтобы помочь вам):

class LessonDetailView(DetailView):
    model = Lesson
    template_name = 'courses/lesson-details.html'

    def get_context_data(self, **kwargs):
        context = super().get_context_data(**kwargs)
        course = self.object.courses.get(pk=kwargs["course_id"])
        context["course"] = course
        return context

И, конечно же, сбросьте ваш шаблон до первоначальной версии.

РЕДАКТИРОВАТЬ 2:

Я забыл, что это сломается Lesson.get_absolute_url(), так как вы зависите от знания текущего курса, что невозможно в этом контексте. Решение состоит в том, чтобы просто удалить этот метод из модели Lesson (на самом деле Модель не должна ничего знать о URL) и заменить все вызовы на lesson.get_absolute_url() либо вызовом django.core.urlresolvers.reverse (в коде Python), либо брат {% url %} тег шаблона (в шаблонах).

...