Django - загрузка файла в облако (Azure blob storage) с индикатором прогресса
Я следую руководству this, чтобы добавить индикатор выполнения при загрузке файла в Django, используя ajax.
Когда я загружаю файл в папку, используя опцию upload_to
, все работает нормально.
Но когда я загружаю файл в Azure, используя опцию storage
- он не работает.
Т.е. когда это моя модель:
class UploadFile(models.Model):
title = models.CharField(max_length=50)
file=models.FileField(upload_to='files/media/pre')
Работает идеально, но когда это моя модель:
from myAzure import AzureMediaStorage as AMS
class UploadFile(models.Model):
title = models.CharField(max_length=50)
file = models.FileField(storage=AMS)
Застревает и не продвигается. (AMS определяется в myAzure.py по):
from storages.backends.azure_storage import AzureStorage
class AzureMediaStorage(AzureStorage):
account_name = '<myAccountName>'
account_key = '<myAccountKey>'
azure_container = 'media'
expiration_secs = None
Как я могу заставить его работать?
Я могу предложить попробовать обходной путь - хранить файл локально, а затем загрузить его в Azure.
Не уверен, что это сработает, но, по крайней мере, вы можете попробовать и сказать, если поможет:
class UploadFile(models.Model):
title = models.CharField(max_length=50)
file = models.FileField(upload_to='files/media/pre', null=True, blank=False)
remote_file = models.FileField(storage=AMS, null=True, blank=True, default=None)
def save(self, *args, **kwargs):
if self.file:
self.remote_file = self.file
super().save(*args, **kwargs) # in theory - this should trigger upload of remote_file
self.file = None
super().save(*args, **kwargs)
Когда человек загружает файл в определенное место, для отслеживания текущего состояния загрузки либо добавляется обертка вокруг объекта Python, либо место загрузки предоставляет обратный вызов для мониторинга.
Поскольку библиотека Azure не предоставляет такой обратный вызов, можно создать обертку для объекта или использовать уже существующую.
Есть библиотека, предложенная Alastair McCormack под названием tqdm с такой оберткой, которую можно использовать.
Как показывает Джордж Джон, можно сделать что-то вроде этого
size = os.stat(fname).st_size
with tqdm.wrapattr(open(fname, 'rb'), "read", total=size) as data:
blob_client.upload_blob(data)