Django视图详解

发布于:2025-04-09 ⋅ 阅读:(30) ⋅ 点赞:(0)

前言

欢迎来到我的博客

个人主页:北岭敲键盘的荒漠猫-CSDN博客


一、Django视图是什么?

视图(View) 是Django处理HTTP请求的核心组件。它接收一个HttpRequest对象,处理业务逻辑,并返回一个HttpResponse对象(如网页、JSON数据、重定向等)。

1. 视图的两种写法
  • 函数视图(FBV,Function-Based Views) :用Python函数实现。

    from django.http import HttpResponse
    
    def hello(request):
        return HttpResponse("Hello World!")
    
  • 类视图(CBV,Class-Based Views) :用类的方法处理请求(更结构化,适合复用)。

    from django.views import View
    from django.http import HttpResponse
    
    class HelloView(View):
        def get(self, request):
            return HttpResponse("GET请求示例")
        
        def post(self, request):
            return HttpResponse("POST请求示例")
    

二、编写第一个视图:详细步骤

1. 创建视图函数

views.py中定义一个处理请求的函数:

# myapp/views.py
from django.http import HttpResponse

def home_page(request):
    return HttpResponse("<h1>欢迎来到我的网站!</h1>")
2. 配置URL路由

urls.py中将URL路径映射到视图:

# myproject/urls.py
from django.urls import path
from myapp import views

urlpatterns = [
    path('', views.home_page, name='home'),  # 根路径指向home_page视图
]
3. 运行开发服务器
python manage.py runserver

访问 [http://127.0.0.1:8000](http://127.0.0.1:8000) 即可看到页面。


三、深入理解请求(HttpRequest)和响应(HttpResponse)

1. HttpRequest对象:包含请求的所有信息
  • 常用属性

    • request.method:请求方法(GET、POST等)
    • request.GET:GET请求的参数(字典形式)
    • request.POST:POST请求的表单数据
    • request.FILES:上传的文件
    • request.user:当前登录用户(需启用认证中间件)
  • 示例:处理GET请求参数

    def greet(request):
        name = request.GET.get('name', '游客')  # 获取name参数,默认值'游客'
        return HttpResponse(f"你好,{name}!")
    

 

2. HttpResponse对象:返回内容给浏览器
  • 常见用法

    • 返回文本:HttpResponse("文本内容")
    • 返回HTML:HttpResponse("<h1>标题</h1>")
    • 返回JSON:JsonResponse({'data': 'xxx'})
    • 重定向:HttpResponseRedirect('/new-url/')
  • 示例:返回JSON数据

    from django.http import JsonResponse
    
    def json_example(request):
        data = {'status': 'success', 'message': '请求成功'}
        return JsonResponse(data)
    


    四、函数视图(FBV)的完整流程

    1. 处理GET和POST请求
    def contact(request):
        if request.method == 'POST':
            # 处理表单提交
            name = request.POST.get('name')
            email = request.POST.get('email')
            print(f"收到来自{name} ({email}) 的消息")
            return HttpResponseRedirect('/thanks/')  # 重定向到感谢页面
        else:
            # 显示空表单
            return render(request, 'contact.html')
    
    2. 渲染模板(Template)

    使用render()函数将数据传递到HTML模板:

    from django.shortcuts import render
    
    def article_list(request):
        articles = Article.objects.all()  # 假设Article是模型
        return render(request, 'articles/list.html', {'articles': articles})
    

    模板文件 articles/list.html

    {% for article in articles %}
        <h2>{{ article.title }}</h2>
        <p>{{ article.content }}</p>
    {% endfor %}
    

    五、类视图(CBV)的用法详解

    1. 基本结构
    from django.views import View
    from django.http import HttpResponse
    
    class MyView(View):
        def get(self, request):
            # 处理GET请求
            return HttpResponse("GET请求")
    
        def post(self, request):
            # 处理POST请求
            return HttpResponse("POST请求")
    
    2. 在URL中使用类视图
    # urls.py
    urlpatterns = [
        path('myview/', MyView.as_view(), name='my-view'),
    ]
    
    3. 类视图的优势:复用与扩展
    • 继承内置通用视图(如ListView, DetailView
    • 重写方法自定义行为:
      class ArticleListView(ListView):
          model = Article  # 关联模型
          template_name = 'articles/list.html'  # 指定模板
          context_object_name = 'article_list'  # 模板中使用的变量名
      
          def get_queryset(self):
              # 过滤已发布的文章
              return Article.objects.filter(status='published')
      

    六、通用视图(Generic Views)快速入门

    Django内置了处理常见场景的类视图,极大简化代码。

    概念:

    通用视图(Generic Views)是Django为解决Web开发中重复模式设计的"快捷工具包",它能让你用极简代码实现以下常见功能:

    • 显示对象列表(如商品列表、文章列表)
    • 展示单个对象详情(如用户详情页)
    • 处理表单创建/修改对象(如新建订单)
    • 日期归档页面(如按月份展示文章)
    • 删除对象前的确认操作

    传统函数视图需要手动处理数据库查询、模板渲染等细节,而通用视图通过"约定优于配置"原则自动完成这些基础工作

    1. ListView:显示对象列表
    from django.views.generic import ListView
    
    class BookListView(ListView):
        model = Book  # 自动获取所有Book对象
        template_name = 'books/book_list.html'  # 默认模板:books/book_list.html
        context_object_name = 'books'  # 模板中变量名(默认object_list)
    
    2. DetailView:显示单个对象详情
    from django.views.generic import DetailView
    
    class BookDetailView(DetailView):
        model = Book
        # 默认模板:books/book_detail.html
        # 通过URL中的pk或slug获取对象(如 /books/1/)
    
    3. 表单处理:CreateView/UpdateView
    from django.views.generic.edit import CreateView
    from django.urls import reverse_lazy
    
    class BookCreateView(CreateView):
        model = Book
        fields = ['title', 'author', 'price']  # 表单字段
        template_name = 'books/book_form.html'
        success_url = reverse_lazy('book-list')  # 提交成功后跳转的URL
    

    七、实际场景案例

    1. 用户登录视图
    from django.contrib.auth import authenticate, login
    from django.shortcuts import render, redirect
    
    def login_view(request):
        if request.method == 'POST':
            username = request.POST['username']
            password = request.POST['password']
            user = authenticate(request, username=username, password=password)
            if user is not None:
                login(request, user)
                return redirect('home')
            else:
                return render(request, 'login.html', {'error': '用户名或密码错误'})
        return render(request, 'login.html')
    
    2. 文件上传
    def upload_file(request):
        if request.method == 'POST' and request.FILES['file']:
            uploaded_file = request.FILES['file']
            # 保存文件到服务器
            with open(f'uploads/{uploaded_file.name}', 'wb+') as destination:
                for chunk in uploaded_file.chunks():
                    destination.write(chunk)
            return HttpResponse("文件上传成功!")
        return render(request, 'upload.html')
    

    八、常见问题与调试技巧

    1. 404错误处理
    • 使用get_object_or_404替代get
      from django.shortcuts import get_object_or_404
      
      def book_detail(request, pk):
          book = get_object_or_404(Book, pk=pk)
          return render(request, 'books/detail.html', {'book': book})
      
    2. 调试视图
    • 打印请求信息
      def debug_view(request):
          print("请求方法:", request.method)
          print("GET参数:", request.GET)
          print("用户:", request.user)
          return HttpResponse("查看控制台输出")
      
    3. 单元测试
    from django.test import TestCase, Client
    
    class ViewTests(TestCase):
        def test_home_page(self):
            client = Client()
            response = client.get('/')
            self.assertEqual(response.status_code, 200)
            self.assertContains(response, "欢迎")
    

    九、最佳实践总结

    1. 选择合适的视图类型

      • 简单逻辑用函数视图(FBV)
      • 复杂或重复逻辑用类视图(CBV)
    2. 保持视图简洁

      • 业务逻辑抽离到单独模块(如utils.py
      • 使用通用视图减少重复代码
    3. 安全注意事项

      • 始终验证用户输入
      • 使用@login_required限制敏感操作
      • 启用CSRF保护(表单中加{% csrf_token %}
    4. 性能优化

      • 使用select_relatedprefetch_related优化数据库查询
      • 缓存频繁访问的视图(如使用@cache_page装饰器)


    网站公告

    今日签到

    点亮在社区的每一天
    去签到