Django file field не сохраняет файл в папку s3 bucket при обновлении
Я загружаю файл в s3 bucket по следующему пути:
bucket/folder/{custom_id}/file
У меня есть приведенный ниже метод, который я вызываю в Model. В методе DRF Post файл корректно сохраняется в s3, и я могу получить путь в GET. Но когда я пытаюсь загрузить новые файлы в методе PUT, имя файла сохраняется в db, но файл не сохраняется в ведро s3.
пользовательский путь загрузки
def upload_path_handler(instance, filename):
return f'{FILES_FOLDER}/{id}/{filename}'
In Models.py
cc_file = models.FileField(
db_column='CCFilename', blank=True, null=True, upload_to=upload_path_handler
)
Этот метод работает в POST API вызове DRF. Как мне сохранить новый файл в s3, если файл изменяется при обновлении поля
Что можно попробовать...
1. Убедитесь, что у вас установлены правильные разрешения и политика S3. Получите доступ к 'Policy' через вкладку permissions в консоли AWS S3 для вашего конкретного ведра.
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "Statement1",
"Effect": "Allow",
"Principal": "*",
"Action": "s3:GetObject",
"Resource": "arn:aws:s3:::<your_bucket_name>/*"
},
{
"Sid": "Statement2",
"Effect": "Allow",
"Principal": "*",
"Action": "s3:PutObject",
"Resource": "arn:aws:s3:::<your_bucket_name>/images/"
}
]
}
2. Установите WhiteNoiseMiddleware & django-storages в окружении вашего проекта.
pip install whitenoise
pip install django-storages
3. Добавить следующее к MIDDLEWARE=
в settings.py
'whitenoise.middleware.WhiteNoiseMiddleware',
4. Следующие дополнения в settings.py
необходимы для корректной обработки URL из S3. Обработка выполняется django middleware & django-storages автоматически
STATICFILES_LOCATION = 'static'
MEDIAFILES_LOCATION = 'media'
AWS_S3_CUSTOM_DOMAIN = '%s.s3.amazonaws.com' % os.environ['BUCKET_NAME']
AWS_ACCESS_KEY_ID = os.environ['AWS_KEY']
AWS_SECRET_ACCESS_KEY = os.environ['AWS_ACC_KEY']
AWS_STORAGE_BUCKET_NAME = os.environ['BUCKET_NAME']
AWS_S3_FILE_OVERWRITE = False
AWS_DEFAULT_ACL = None
DEFAULT_FILE_STORAGE = 'storages.backends.s3boto3.S3Boto3Storage'
STATICFILES_STORAGE = 'storages.backends.s3boto3.S3StaticStorage'
MEDIA_ROOT = os.path.join (BASE_DIR, 'static/images/')
STATIC_ROOT = os.path.join (BASE_DIR, 'static')
STATIC_URL = "https://%s/%s/" % (AWS_S3_CUSTOM_DOMAIN, STATICFILES_LOCATION)
MEDIA_URL = "https://%s/%s/" % (AWS_S3_CUSTOM_DOMAIN, MEDIAFILES_LOCATION)
5. Для прицельной загрузки в точную папку S3 Bucket. (Дополнительно)
В файле setting.py установите корень медиа:
MEDIA_ROOT = os.path.join (BASE_DIR, 'static/images/')
В models.py используйте ImageFiled
и добавьте upload_to=
принимает имя папки и создает ее с первой загрузкой!:
image_variable = models.ImageField(null=True, default="{default_filename)", upload_to='uploads/')
Ссылка: django-storages , whiteNoiseMiddelware, S3 Access Troubleshooting