django 类视图

时间:2025-04-20 09:30:32

django 类视图

from django.urls import reverse_lazy
from django.views.generic import (
    TemplateView, ListView, DetailView,
    CreateView, UpdateView, DeleteView
)
from .models import MyModel

# 1) 仅渲染模板,不依赖模型
class HomePageView(TemplateView):
    template_name = "myapp/base.html"


# 2) 列表视图
class MyModelListView(ListView):
    model = MyModel
    template_name = "myapp/object_list.html"     # 指定模板
    context_object_name = "object_list"          # 在模板中使用的上下文变量
    paginate_by = 10                             # 如果需要分页

# 3) 详情视图
class MyModelDetailView(DetailView):
    model = MyModel
    template_name = "myapp/object_detail.html"
    context_object_name = "object"


# 4) 新建视图
class MyModelCreateView(CreateView):
    model = MyModel
    fields = ["title", "content"]               # 自动生成表单字段
    template_name = "myapp/object_form.html"
    success_url = reverse_lazy("myapp:list")     # 成功后跳转

# 5) 更新视图
class MyModelUpdateView(UpdateView):
    model = MyModel
    fields = ["title", "content"]
    template_name = "myapp/object_form.html"
    success_url = reverse_lazy("myapp:list")

# 6) 删除视图
class MyModelDeleteView(DeleteView):
    model = MyModel
    template_name = "myapp/object_confirm_delete.html"
    success_url = reverse_lazy("myapp:list")

路由配置

from django.urls import path
from .views import (
    HomePageView, MyModelListView, MyModelDetailView,
    MyModelCreateView, MyModelUpdateView, MyModelDeleteView
)

app_name = "myapp"

urlpatterns = [
    path("", HomePageView.as_view(), name="home"),
    path("objects/", MyModelListView.as_view(), name="list"),
    path("objects/add/", MyModelCreateView.as_view(), name="add"),
    path("objects/<int:pk>/", MyModelDetailView.as_view(), name="detail"),
    path("objects/<int:pk>/edit/", MyModelUpdateView.as_view(), name="edit"),
    path("objects/<int:pk>/delete/", MyModelDeleteView.as_view(), name="delete"),
]

base.html

<!DOCTYPE html>
<html lang="zh-CN">
<head>
  <meta charset="UTF-8">
  <title>{% block title %}MyApp{% endblock %}</title>
  <link rel="stylesheet" href="{% static 'css/bootstrap.min.css' %}">
</head>
<body>
  <nav>
    <a href="{% url 'myapp:home' %}">首页</a> |
    <a href="{% url 'myapp:list' %}">列表</a> |
    <a href="{% url 'myapp:add' %}">新建</a>
  </nav>
  <hr>
  <div class="container">
    {% block content %}{% endblock %}
  </div>
</body>
</html>

列表页(object_list.html)

{% extends "myapp/base.html" %}
{% block title %}对象列表{% endblock %}

{% block content %}
  <h1>对象列表</h1>
  <ul>
    {% for obj in object_list %}
      <li>
        <a href="{% url 'myapp:detail' obj.pk %}">{{ obj.title }}</a>
        &mdash; {{ obj.created_at|date:"Y-m-d H:i" }}
      </li>
    {% empty %}
      <li>暂无数据</li>
    {% endfor %}
  </ul>

  {# 分页导航 #}
  {% if is_paginated %}
    <div class="pagination">
      {% if page_obj.has_previous %}
        <a href="?page={{ page_obj.previous_page_number }}">« 上一页</a>
      {% endif %}
      <span>第 {{ page_obj.number }} 页,共 {{ page_obj.paginator.num_pages }} 页</span>
      {% if page_obj.has_next %}
        <a href="?page={{ page_obj.next_page_number }}">下一页 »</a>
      {% endif %}
    </div>
  {% endif %}
{% endblock %}

详情页(object_detail.html)

{% extends "myapp/base.html" %}
{% block title %}对象详情{% endblock %}

{% block content %}
  <h1>{{ object.title }}</h1>
  <p>{{ object.content }}</p>
  <p><small>创建于:{{ object.created_at|date:"Y-m-d H:i" }}</small></p>
  <p>
    <a href="{% url 'myapp:edit' object.pk %}">编辑</a> |
    <a href="{% url 'myapp:delete' object.pk %}">删除</a> |
    <a href="{% url 'myapp:list' %}">返回列表</a>
  </p>
{% endblock %}

表单页(object_form.html)

{% extends "myapp/base.html" %}
{% block title %}{{ view.action }} 对象{% endblock %}
{% block content %}
  <h1>{{ view.action }} 对象</h1>
  <form method="post">
    {% csrf_token %}
    {{ form.as_p }}
    <button type="submit">{{ view.action }}</button>
  </form>
  <a href="{% url 'myapp:list' %}">取消</a>
{% endblock %}