Django 分類頁畫面顯示功能指南
更新日期: 2024 年 12 月 24 日
本文為 Django 分類功能系列教學,第 10 篇:
在 Django 項目中,為了實現按分類篩選服務的功能,我們可以利用分類路由和視圖,來處理未篩選和篩選分類的邏輯。
本指南將帶您逐步完成路由、視圖、模板的設計與實現,並介紹完整的架構邏輯,讓新手也能輕鬆上手。
功能概述
目標功能
- 未篩選服務:
- URL:
categories/
- 顯示所有服務,無需區分分類。
- URL:
- 篩選特定分類:
- URL:
categories/<int:category_id>/
- 根據分類顯示特定的服務。
- URL:
這樣的設計能夠靈活地管理分類篩選,同時保持簡潔的路由結構。
路由設計
categories/urls.py
from django.urls import path
from . import views
app_name = "categories"
urlpatterns = [
path("", views.all_services, name="all_services"), # 顯示所有服務
path("<int:category_id>/", views.services_by_category, name="services_by_category"), # 按分類篩選服務
]
路由解析
all_services
:處理顯示所有服務的請求。services_by_category
:根據分類 ID 來篩選對應的服務,分類 ID 為整數類型。
視圖實現
未篩選服務
在 views.py
中新增以下代碼:
from django.shortcuts import render
from services.models import Service
def all_services(request):
services = Service.objects.all() # 獲取所有服務
return render(request, "categories/all_services.html", {"services": services})
邏輯說明
Service.objects.all()
:從資料庫中獲取所有服務數據。render
:將數據傳遞給模板進行渲染,生成未篩選的服務頁面。
篩選特定分類
在 views.py
中新增以下代碼:
from django.shortcuts import render, get_object_or_404
from services.models import Service, Category
def services_by_category(request, category_id):
category = get_object_or_404(Category, id=category_id) # 確保分類存在
services = Service.objects.filter(category=category) # 篩選該分類的服務
return render(request, "categories/services_by_category.html", {
"category": category,
"services": services,
})
邏輯說明
get_object_or_404
:檢查分類是否存在,若不存在則返回 404 頁面。Service.objects.filter(category=category)
:根據分類篩選對應的服務數據。render
:將分類和服務數據傳遞給模板,生成篩選後的服務頁面。
模板設計
未篩選服務模板
文件路徑:categories/templates/categories/all_services.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>所有服務</title>
</head>
<body>
<h1>所有服務</h1>
<ul>
{% for service in services %}
<li>
<a href="{% url 'categories:service_by_category' service.category.id %}">
{{ service.name }} - 分類: {{ service.category.name }}
</a>
</li>
{% endfor %}
</ul>
</body>
</html>
模板解析
{% for service in services %}
:迴圈顯示所有服務。service.category.name
:顯示服務對應的分類名稱。{% url 'categories:service_by_category' service.category.id %}
:導連到個別分類頁
篩選分類模板
文件路徑:categories/templates/categories/services_by_category.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>{{ category.name }} 的服務</title>
</head>
<body>
<h1>{{ category.name }} 的服務</h1>
<ul>
{% for service in services %}
<li>{{ service.name }}</li>
{% endfor %}
</ul>
<a href="{% url 'categories:all_services' %}">返回所有服務</a>
</body>
</html>
模板解析
category.name
:顯示當前分類的名稱作為標題。{% for service in services %}
:顯示當前分類下的所有服務。- 返回鏈接:提供返回未篩選頁面的按鈕或鏈接。
完整功能測試
測試用例
- 未篩選頁面 (
categories/
)- 行為:顯示所有服務及其分類。
- 測試:確認所有服務都正確顯示,分類名稱準確。
- 篩選分類頁面 (
categories/<int:category_id>/
)- 行為:顯示特定分類下的服務。
- 測試:確認只有該分類的服務被顯示,其他分類的服務不應出現。
架構優勢
獨立的分類功能
- 將分類邏輯集中在
categories
app 中,與其他應用邏輯分離,方便維護。
清晰的路由規劃
categories/
顯示所有服務,categories/<int:category_id>/
提供篩選功能,語義清晰,結構簡單。
易於擴展
- 若未來需要新增分類篩選的附加功能,例如多層次分類或篩選條件,現有結構能輕鬆適配。
結論
透過上述步驟,您可以成功實現分類篩選的基本功能,並確保代碼結構清晰、易於維護和擴展。
這樣的設計方式不僅符合 Django 的最佳實踐,也為未來功能開發奠定了堅實的基礎。