Django ModelForm ImageField 上傳注意事項
分類
說明
分享使用 ModelForm 上傳 ImageField 儲存到模型時,需要設定什麼。
models.py
示範新增 Article 模型,內含 cover_image ImageField 欄位。
upload_to
需自己設定儲存路徑。
models.py
from django.db.models import Model
class Article(Model):
"""文章"""
# 封面圖片
cover_image = ImageField(upload_to="your_image_path", blank=True)
forms.py
示範表單上傳 Article 模型,包含 cover_image
圖像欄位。
注意 from my_app.models import Article
,填入你的 models 位置和名稱。
forms.py
from django.forms import ModelForm
from my_app.models import Article
class ArticleForm(ModelForm):
"""文章表單"""
class Meta:
model = Article
fields = ["cover_image"]
labels = {
"cover_image": "封面照片",
}
view.py
article_id
是從網址取得的 id,一開始會先檢查 id 是否有文章,接著檢查 HTTP 請求是 GET 還是 POST,GET 的話只需帶入空表單給前端渲染就好,如果是 POST 就檢查表單是否有效,無效的話就必須傳給前端修改,有效才寫入到資料庫。
view.py
"""文章編輯"""
from django.http import HttpRequest
from django.http import HttpResponse
from django.shortcuts import redirect
from django.shortcuts import render
from my_app.forms import ArticleForm
from my_app.models import Article
def article_edit(request: HttpRequest, article_id: int) -> HttpResponse:
"""文章編輯
Args:
request (HttpRequest): Http 請求
Returns:
HttpResponse: Http 回應
"""
try:
article: Article = Article.objects.get(id=article_id)
except Article.DoesNotExist:
return redirect("index")
if request.method == "GET":
# 空表單
article_form = ArticleForm(instance=article)
return render(
request,
"my_app/article_edit.html",
{
"article_form": article_form,
"article_id": article_id,
},
)
if request.method == "POST":
# 表單包含使用者輸入的資料
article_form = ArticleForm(request.POST, request.FILES, instance=article)
# 表單無效
if not article_form.is_valid():
return render(
request,
"my_app/article_edit.html",
{
"article_form": article_form,
"article_id": article_id,
},
)
article_form.save()
# 成功寫入重新導向網址
return redirect("your_url")
# 未知的特殊狀況
return redirect("your_url")
注意 ArticleForm(request.POST, request.FILES, instance=article)
這行,第1個參數是請求的資料,這個比較常見,需注意第2個參數是檔案,如果沒帶入第2個參數,就沒辦法取得圖片檔案。
HTML
這裡假設 url 處理文章表單的名稱是 article_edit
。
article_form
和 article_id
是從 view 設定的變數。
article_edit.html
<form action="{% url 'article_edit' article_id %}"
enctype="multipart/form-data"
method="post"
name="article_edit">
{% csrf_token %}
{{ article_form.as_p }}
<button type="submit" class="btn btn-primary">儲存</button>
</form>
需注意 form 表單屬性要加上 enctype="multipart/form-data"
。
url
示範 article edit url
path('article_edit/<int:article_id>', view.article_edit, name='article_edit')
一杯咖啡的力量,勝過千言萬語的感謝。
支持我一杯咖啡,讓我繼續創作優質內容,與您分享更多知識與樂趣!