這是我的自定義圖片上傳功能
def upload_image(file, dir_name, filename):
try:
target_path = '/static/images/' dir_name '/' filename
path = storage.save(target_path, file)
return storage.url(path)
except Exception as e:
print(e)
這是我的模型
class MenuOptions(models.Model):
name = models.CharField(max_length=500, null=False)
description = models.CharField(max_length=500, null=True)
image_url = models.ImageField(upload_to=upload_image())
def __str__(self):
return f'{self.name}'
我想使用我的 upload_image 函式上傳影像,如您所見,它采用 3 個引數檔案、dir_name 和 file_name。如何在我的 model.ImageField() 中傳遞這些引數另外,我想將 image_url 存盤到我的資料庫中,如 upload_image 函式回傳的那樣,它將檔案存盤在 DB 中還是 URL 中?
uj5u.com熱心網友回復:
首先,您應該傳遞upload_image,而不是呼叫upload_image():
image_url = models.ImageField(upload_to=upload_image)
第二件事,使用傳遞的值upload_to自動呼叫。因此不需要Storage.save()呼叫內部。應該只回傳應該保存檔案的路徑。upload_image()upload_image
函式upload_to應該有 2 個引數,instance并且filename.
參考
uj5u.com熱心網友回復:
這是我存盤檔案的解決方案。
您只需實作以下功能并在模型中使用它。
import os
import uuid
from django.utils.deconstruct import deconstructible
@deconstructible
class MediaFileNameHash(object):
def __init__(self, base_dir, path):
self.address = base_dir "/" path
self.path = path
if not os.path.exists(self.address):
os.makedirs(self.address, exist_ok=True)
def __call__(self, _, filename):
# @note It's up to the validators to check if it's the correct file type in name or if one even exist.
filename = os.path.splitext(filename)
return self.path '/' filename[0] "@" str(uuid.uuid4()) filename[1]
例如:
class MenuOptions(models.Model):
name = models.CharField(max_length=500, null=False)
description = models.CharField(max_length=500, null=True)
image_url = models.ImageField(
upload_to=MediaFileNameHash("/media/", "files"),
verbose_name=_("Address")
)
uj5u.com熱心網友回復:
另外要傳遞函式名稱,您首先需要在模型中撰寫一個函式來處理這樣的路徑!
# In you models.py
# will automatically save your image to your custom view
def get_upload_image_filepath(self, filename):
return 'Images/' str(self.pk) '/default.png'
class MenuOptions(models.Model):
name = models.CharField(max_length=500, null=False)
description = models.CharField(max_length=500, null=True)
image_url = models.ImageField(upload_to=get_upload_image_filepath)
def __str__(self):
return f'{self.name}'
好吧,我只是要指導你如何處理這種情況,你可以重構你的代碼,因為它會在同樣的意義上作業。這是我關于如何撰寫自定義視圖的解決方案:
# this would be at the top of your view
import base64
import os
TEMP_UPLOAD_IMAGE_NAME = "default.png"
def save_temp_upload_image_from_base64String(imageString, user):
INCORRECT_PADDING_EXCEPTION = "Incorrect padding"
try:
if not os.path.exists(settings.TEMP):
os.mkdir(settings.TEMP)
if not os.path.exists(settings.TEMP "/" str(user.pk)):
os.mkdir(settings.TEMP "/" str(user.pk))
url = os.path.join(settings.TEMP "/" str(user.pk),TEMP_UPLOAD_IMAGE_NAME)
storage = FileSystemStorage(location=url)
image = base64.b64decode(imageString)
with storage.open('', 'wb ') as destination:
destination.write(image)
destination.close()
return url
except Exception as e:
print("exception: " str(e))
# workaround for an issue I found
if str(e) == INCORRECT_PADDING_EXCEPTION:
imageString = "=" * ((4 - len(imageString) % 4) % 4)
return save_temp_upload_image_from_base64String(imageString, user)
return None
轉載請註明出處,本文鏈接:https://www.uj5u.com/qukuanlian/420712.html
標籤:
