#python #django #amazon-web-services #amazon-s3
#python #django #amazon-веб-сервисы #amazon-s3
Вопрос:
Я создал приложение django, в котором хранятся заметки о разных семестрах и филиалах, и я хочу отобразить изображение профиля отправителя сообщения прямо рядом с его именем на главной странице моего сайта. Я использую свои staticfiles непосредственно из корзины S3
Заметки, которые загружают пользователи, хранятся в заметках / моделях.py в то время как профиль пользователя и его изображение профиля хранятся в users/models.py
То, что я хочу сделать, это home.html
(ниже) использовать что-то вроде, {% static post.uploader.profile.image.url %}
но внезапно это не работает.
Settings.py
AWS_ACCESS_KEY_ID='XXXXXXXXXXXXXXXXXX'
AWS_SECRET_ACCESS_KEY='XXXXXXXXXXXXXXXXXXXXXXXXXXX'
AWS_STORAGE_BUCKET_NAME='django-XXXXX'
AWS_S3_REGION_NAME = "ap-south-1"
AWS_S3_SIGNATURE_VERSION = "s3v4"
AWS_S3_FILE_OVERWRITE = False
AWS_DEFAULT_ACL = None
# s3 static settings
AWS_LOCATION = 'staticfiles'
AWS_S3_CUSTOM_DOMAIN = f'{AWS_STORAGE_BUCKET_NAME}.s3.amazonaws.com'
STATIC_URL = f'https://{AWS_S3_CUSTOM_DOMAIN}/{AWS_LOCATION}/'
STATICFILES_STORAGE = 'storages.backends.s3boto3.S3Boto3Storage'
# s3 public media settings
PUBLIC_MEDIA_LOCATION = 'media'
MEDIA_URL = f'https://{AWS_S3_CUSTOM_DOMAIN}/{PUBLIC_MEDIA_LOCATION}/'
DEFAULT_FILE_STORAGE = 'django_project.storage_backends.PublicMediaStorage'
# s3 private media settings
PRIVATE_MEDIA_LOCATION = 'private'
PRIVATE_FILE_STORAGE = 'django_project.storage_backends.PrivateMediaStorage'
DEFAULT_FILE_STORAGE = 'storages.backends.s3boto3.S3Boto3Storage'
notes/models.py
class Notes_Model(models.Model):
"""Store notes of different branches and semesters."""
uploader = models.CharField(max_length=200)
title = models.CharField(max_length=200)
date_posted = models.DateTimeField(auto_now_add=True)
description = models.TextField(max_length=2500)
branch_choice = models.CharField(max_length=50, choices=branch_choices, default='cse')
file_semester = models.IntegerField(choices=semester_choice)
file = models.FileField()
syllabus = models.TextField(max_length=200, default='No Syllabus Availibe Yet')
def __str__(self):
return self.title
def get_absolute_url(self):
return reverse("notes-detail", kwargs={"pk": self.pk})
users/models.py
from django.db import models
from django.contrib.auth.models import User
from PIL import Image
class Profile(models.Model):
user = models.OneToOneField(User, on_delete=models.CASCADE)
image = models.ImageField(default='default.svg', upload_to='profile-pics')
def __str__(self):
return (f'{self.user.username} Profile')
def save(self):
super.save()
img = Image.open(self.image.path)
if img.height > 300 or img.width > 300:
output_size = (300, 300)
img.thumbnail(output_size)
img.save(self.image.path)
home.html
{% extends "base.html" %}
{% block content %}
{% load static %}
<div>
{% for post in posts %}
<article class="media content-section">
<img class="rounded-circle article-img" <!--this src is posing the issue -->src="{% static post.uploader.profile.image.url %}" width="60" height="60" style="margin-right: 30px">
<div class="media-body">
<p class="mr-2 text-capitalize">{{ post.uploader }}</p>
<small class="text-muted font-italic">{{ post.date_posted }}</small>
<div class="article-metadata">
</div>
<h2><a class="article-title text-info text-capitalize" href="{% url 'notes-detail' post.id %}">{{ post.title }}</a></h2>
<p class="article-content">{{ post.content }}</p>
</div>
</article>
{% endfor %}
</div>
xml из корзины aws s3 сообщает, что ключа нет, но он присутствует в корзине.
<Error>
<Code>NoSuchKey</Code>
<Message>The specified key does not exist.</Message>
<Key>staticfiles/</Key>
<RequestId>960CD372E7128E16</RequestId>
<HostId>
90tvY TT6FkefEheQXtuOLv5T8fCvJsDzIOBpam8inz4GGdhpb9QXrkToDCl/3yN 69tJoUUYQo=
</HostId>
</Error>
Возвращаемый URL-адрес: https://django-xxxxxxx.s3.amazonaws.com/staticfiles /
тогда как это должно быть
Ожидаемый возвращаемый URL-адрес: https://django-xxxxxx.s3.amazonaws.com/staticfiles/profile.jpg
Ответ №1:
Вы используете {% static %}
templatetag для чего-то, что не является статическим файлом. Это медиафайл. Значением post.uploader.profile.image.url
должен быть фактический URL-адрес изображения в качестве медиа-ресурса. Передача этого URL {% static %}
-адреса пытается найти URL-адрес как имя статического ресурса, поэтому вы получаете NoSuchKey
ошибку.
Комментарии:
1. хорошо, я согласен, что это медиафайл, но для разных пользователей, даже если при использовании
{{ post.uploader.profile.image.url }}
which снова не работает.2. Что означает «не работает»? Есть ли изображение, загруженное для этого профиля, то есть изображения нет
None
? Существует ли значение поdefault.svg
умолчанию? Правильно ли настроена корзина для медиафайлов?3. не работает означает, что изображение не загружается из корзины S3 на интерфейс моего веб-сайта. Причина проблемы, по-видимому
<img src=" {{ post.uploader.profile.image.url }}">
, в том, что я, например, не могу указать правильный путь вimg
. Есть ли у вас какое-либо представление об этом? и да, корзина S3 настроена правильно.4. Еще одна вещь:
DEFAULT_FILE_STORAGE
определяется дважды. Второй вариант выигрывает, поэтому похоже, что у вас неправильно настроены сегменты, поскольку вы не используетеPublicMediaStorage
класс, а вместо этого используете (я полагаю) базовый классS3Boto3Storage
.