Как показать файлы в шаблонах django из базы данных?

Я пытаюсь отобразить файлы в шаблонах django. Из базы данных они успешно отображаются. Я не понимаю, почему он не отображается из шаблонов. Здесь я делюсь своими кодами на данный момент.

#models.py
class Answer(models.Model):
    description = models.TextField(blank=True, null=True)
    question_id = models.ForeignKey(
        Question, blank=False, on_delete=models.CASCADE)
    created_by = models.ForeignKey(User, blank=False, on_delete=models.CASCADE)

    def __str__(self):
        return self.question_id.description


class AnswerFile(models.Model):
    answer = models.ForeignKey(
        Answer, on_delete=models.CASCADE, related_name='files', null=True, blank=True)
    file = models.FileField(
        'files', upload_to=path_and_rename, max_length=500, null=True, blank=True)

    def __str__(self):
        return str(self.answer)

Поскольку мне нужно несколько файлов, я создал другую модель файла с внешним ключом

#forms.py
class AnswerForm(ModelForm):
    # question_id = forms.IntegerField(required=True)

    class Meta:
        model = Answer
        fields = ['description']
        widgets = {
            'description': forms.Textarea(attrs={"class": "form-control", "id": "exampleFormControlTextarea1", "rows": 5, "placeholder": "Add a reply"}),
        }


class AnswerFileForm(AnswerForm):  # extending Answerform
    file = forms.FileField(
        widget=forms.ClearableFileInput(attrs={'multiple': True}), required=False)

    class Meta(AnswerForm.Meta):
        fields = AnswerForm.Meta.fields + ['file', ]

    def clean(self):
        cleaned_data = super(AnswerFileForm, self).clean()
        file = cleaned_data.get("file")
        description = cleaned_data.get("description")
        if not file and not description:
            raise forms.ValidationError("This is a required field.")
        return cleaned_data

в формах я также стараюсь держаться подальше и все прекрасно работает в views.py

#views.py
    def question_details(request, pk):
        question = Question.objects.filter(id=pk).first()
    
        # answers list
        answers = Answer.objects.filter(question_id=pk).order_by('-id')
        # end answers list
    
        answerForm = AnswerFileForm()
        # start of the answer submission
        if request.method == "POST":
            answerForm = AnswerFileForm(
                request.POST or None, request.FILES or None)
            files = request.FILES.getlist('file')
            if answerForm.is_valid():
                question = Question.objects.filter(id=pk).first()
                if question:
                    answer = answerForm.save(commit=False)
                    answer.created_by = request.user
                    answer.question_id = question
                    answer.save()
                    if files:  # check if user has uploaded some files
                        for file in files:
                            AnswerFile.objects.create(answer=answer, file=file)
                    
                    return redirect("fsingle_question", question.pk)
    
        context = {
            "page_title": "Question Details",
            "question": question,
            "answerForm": answerForm,
            "answers": answers
        }
        return render(request, 'ask_question/question_details.html', context)

вот шаблон на данный момент

    <div class="ms-5">
      <div class="">{{ answer.description }}</div>
      <img src="{{ answer.files }}" width="120" />
    </div>

enter image description here на изображении видно, что поле описания отображается отлично, но для файлов я пробовал несколько способов.

хотя из базы данных все работает отлично enter image description here enter image description here

Если кто-то может помочь мне, это будет очень признательно.

Заранее спасибо.

Для решения этой проблемы попробуйте следующее.
обратите внимание .url что очень важно при показе поля FileField/ImageField.

{% for answer in answers %}
        <div class="ms-5">
          <div class="">{{ answer.description }}</div>
          {% for file in answer.answerfile_set.all %}
          <img src="{{ file.file.url }}" width="120" />
         {% endfor %}
        </div>
{% endfor %}

Вы захотите изучить QuerySet API здесь Django Docs, и выяснить, что вам больше подходит select_related или prefetch_related, которые оба по-разному используют отношения внешних ключей.

Использование select_related:

AnswerFile.objects.all().select_related("answer__question_id").filter(answer__question_id__id = pk)
Вернуться на верх