”工欲善其事,必先利其器。“—孔子《论语.录灵公》
首页 > 编程 > Python 和 Django 中的 CRUD 操作 - 第 2 部分

Python 和 Django 中的 CRUD 操作 - 第 2 部分

发布于2024-07-29
浏览:663

在上一篇文章中,我们介绍了设置 Django 项目的基础知识并创建了练习模型,我们将其以列表的形式显示在前端。在本文中,我们将深入探讨执行 CRUD 操作。对于那些不熟悉的人来说,CRUD 代表创建、读取、更新和删除 — 本质上是您可以对数据执行的四个基本操作。

现在我们已经在应用文件夹中设置了 API,我们只需扩展索引视图来处理创建、更新和删除请求。

表格

让我们设置一个允许用户创建练习的表单。我们将再次使用 HTML 模板来实现此目的。首先,在 app/templates 文件夹中创建一个名为 add_exercise.html 的新模板。

{% csrf_token %}

接下来,在我们的 index.html 模板中,我们将使用以下方法包含 add_exercise.html 模板:

{% extends "base.html" %} {% block content %}
    

Exercises

{% include 'add_exercise.html' %} ... {% endblock %}

我们在这里利用 include 标签,它可以提高 HTML 模板的可组合性,使我们的代码更易于维护和理解。如果您在浏览器中刷新页面,您应该会看到该表单出现在屏幕上。

Add Exercise

在我们的 HTML 中,我们使用

标记,其方法属性设置为 POST,操作属性指向 /,这与我们用来获取练习列表的端点相同。

在此上下文中,csrf_token 是由随机生成的秘密值表示的安全功能。它有助于保护我们提交的表单免受伪造攻击,这就是 CSRF 的意思——跨站请求伪造。为每个用户会话生成一个唯一的令牌,第三方站点无法访问该令牌,从而防止发生未经授权的更改。

我们的表单包含两个输入字段:一个用于标题,另一个用于日期,遵循我们的练习模型的架构。提交表单后,标题和日期的值将通过 POST 请求发送到 / 端点,然后由 app/views.py 中的索引视图进行处理。

该模型

在 Django 中,我们可以通过添加与 CRUD 操作相对应的特定方法来增强我们的 Exercise 模型(本质上是一个 Python 类)。在 app/models.py 文件中,我们将包含以下内容:

class Exercise(models.Model):
    ...

    def create(request):
        title = request.POST.get('title')
        date = request.POST.get('date')

        exercise = Exercise.objects.create(title=title, date=date)

        return exercise

我们可以从 POST 请求访问标题和日期,如上面的代码所示。然后,我们可以利用Django内置的ORM来创建一个新的练习并返回创建的实例。

我们将利用用于检索练习的相同索引视图,对其进行扩展以检查请求方法是否为 POST。如果是这样,我们将把请求对象传递给我们之前定义的类方法。创建练习后,我们会将用户重定向回主页或执行页面刷新,确保新添加的练习出现在屏幕上。

from django.http import HttpResponseRedirect

from app import models

...

def index(request):
    if request.method == 'POST':
        models.Exercise.create(request)
        return redirect('/')

    exercises = (
        models.Exercise.objects.all().order_by("created_at")
    )
    return render(request, "index.html", context={'exercises': exercises})

现在尝试创建一个新练习,您应该会看到它出现在列表底部。

更新练习

在向练习中添加更新功能之前,让我们先重构一下代码。我们将把练习移至他们自己的模板,名为exercise.html。

Exercises

{% include 'add_exercise.html' %}
    {% for exercise in exercises %}
  • {% include 'exercise.html' %}
  • {% endfor %}

在 app/templates 文件夹中为 exercise.html 创建一个模板,我们将向其中添加以下 HTML:

{% csrf_token %}

我们再次对列表中的每个练习使用

标签,并为 exercise.id 添加隐藏输入,该输入将用于更新练习。返回浏览器并刷新页面;您应该会看到列表中每个练习的表格,每个输入都预先填充了相应的练习数据。

CRUD Operations In Python & Django - Part 2

请注意,我们没有使用 PUT 作为表单方法;相反,我们使用 POST。这是因为视图处理程序只能解析通过 GET 和 POST 请求发送的数据,没有对 PUT 和 DELETE 的内置支持。当我们在 Exercise 类中创建 create 类方法时,您可能已经注意到我们使用了 request.POST.get('title')。虽然这适用于 POST 请求,但请求对象中没有可用的 PUT 或 DELETE 方法。

但是我们如何区分 POST 和 PUT 请求呢?如果您检查我们之前创建的表单,您会注意到我们为提交按钮分配了一个名称属性。我们可以像访问标题和日期一样访问此属性,使用 request.POST.get('update').

让我们更新创建练习表单以包含相同的更改。

...

在我们的练习视图中,我们将进行以下更改以区分请求。

def index(request):
    if request.method == 'POST':
        create = 'create' in request.POST
        update = 'update' in request.POST

        if create == True:
            models.Exercise.create(request)
        elif update == True:
            models.Exercise.update(request)

        return redirect('/')

    exercises = (
        models.Exercise.objects.all().order_by("created_at")
    )
    return render(request, "index.html", context={'exercises': exercises})

我们检查按钮名称并相应地将请求转发到适当的练习方法。

让我们向 app/models.py 中的 Exercise 模型添加更新类方法。

def update(request):
    id = request.POST.get('id')
    title = request.POST.get('title')
    date = request.POST.get('date')

    exercise = Exercise.objects.filter(pk=id).update(title=title, date=date)

    return exercise

要更新数据库中的行,我们可以使用 Exercise 模型上提供的更新方法。然而,在更新之前,我们需要确保我们更新的是正确的练习。为此,我们按主键 id 过滤练习,并仅更新该特定练习。

删除练习

同样,我们将在exercise.html模板中的每个练习旁边添加一个删除按钮。

...

我们将把delete设置为name属性的值,并在views.py中,我们将扩展if...elif语句来处理删除操作。

def index(request):
    if request.method == 'POST':
        create = 'create' in request.POST
        update = 'update' in request.POST
        delete = 'delete' in request.POST

        if create == True:
            models.Exercise.create(request)
        elif update == True:
            models.Exercise.update(request)
        elif delete == True:
            models.Exercise.delete(request)

        return redirect('/')

    exercises = (
        models.Exercise.objects.all().order_by("created_at")
    )
    return render(request, "index.html", context={'exercises': exercises})

在练习模型中,我们将添加类方法delete。

def delete(request):
    id = request.POST.get('id')
    is_deleted = Exercise.objects.filter(pk=id).delete()

    if is_deleted == 1:
        return True

    return False

通过此添加,我们已在 Python 和 Django 应用程序中成功实现了 CRUD 操作。

要点

  1. Django 视图处理程序不支持 PUT 和 DELETE 请求,因为它们不解析这些 HTTP 方法的查询参数或请求正文。因此,我们必须依赖 POST 请求,并通过在请求正文中传递附加字段来区分它们。
  2. 注意到我正在向我从中获取练习的同一路线发出 POST 请求。这很重要,因为如果您要创建像 /api/exercises 这样的端点来处理请求,则需要手动管理重定向。否则,请求后
    标记的行为是将用户重定向到action属性中指定的端点。因此,您需要手动将用户重定向回所需页面,或者在我们的示例中,将用户保持在同一页面上。
from django.http import HttpResponseRedirect

def index(request):
    ...

    return redirect('/')
    # or
    return HttpResponseRedirect(request.META['HTTP_REFERER'])

总之,通过有效管理我们的 POST 请求并确保正确的重定向,我们可以在 Django 应用程序中实现 CRUD 操作的同时创建无缝的用户体验。

版本声明 本文转载于:https://dev.to/prvnbist/crud-operations-in-python-django-part-2-4fad?1如有侵犯,请联系[email protected]删除
最新教程 更多>
  • Item 避免使用其他类型更合适的字符串
    Item 避免使用其他类型更合适的字符串
    1。避免使用字符串替代其他数据类型: 字符串旨在表示文本,但经常被误用来表示数字、枚举或聚合结构。 如果数据本质上是数字,请使用 int、float 或 BigInteger 等类型,而不是 String。 String age = "30"; // incorreto int age = 30;...
    编程 发布于2024-11-02
  • 如何使用sync.WaitGroup防止Go并发死锁?
    如何使用sync.WaitGroup防止Go并发死锁?
    解决 Goroutines 死锁在这种情况下,您在 Go 并发代码中遇到了死锁错误。让我们深入研究这个问题并提供一个有效的解决方案。该错误是由于生产者和消费者的行为不匹配而发生的。在生产者函数中实现的生产者在有限的时间内在通道 ch 上发送值。然而,存在于主函数中的消费者无限期地运行,无休止地尝试从...
    编程 发布于2024-11-02
  • 如何处理文本文件中的 Unicode 文本:无错误编写的完整指南
    如何处理文本文件中的 Unicode 文本:无错误编写的完整指南
    文本文件中的 Unicode 文本:无错写作综合指南从 Google 文档中提取的编码数据可能具有挑战性,尤其是当遇到需要转换为 HTML 使用的非 ASCII 符号时。本指南提供了处理 Unicode 文本并防止编码错误的解决方案。最初,在数据检索期间将所有内容转换为 Unicode 并将其写入文...
    编程 发布于2024-11-02
  • EchoAPI 与 Insomnia:结合实例进行综合比较
    EchoAPI 与 Insomnia:结合实例进行综合比较
    作为一名全栈开发人员,我知道拥有一流的工具来调试、测试和记录 API 是多么重要。 EchoAPI 和 Insomnia 是两个出色的选项,每个选项都有自己独特的特性和功能。让我带您了解这些工具,比较它们的功能和优点,给您一些实际示例,并帮助您决定何时使用 EchoAPI 或 Insomnia。 ...
    编程 发布于2024-11-02
  • 出发时间和持续时间|编程教程
    出发时间和持续时间|编程教程
    介绍 本实验旨在测试您对 Go 的时间和持续时间支持的理解。 时间 下面的代码包含如何在 Go 中使用时间和持续时间的示例。但是,代码的某些部分丢失了。您的任务是完成代码,使其按预期工作。 Go编程语言基础知识。 熟悉 Go 的时间和持续时间支持。 $ go run...
    编程 发布于2024-11-02
  • 起重面试问答
    起重面试问答
    1. JavaScript 中什么是提升? 答案: 提升是执行上下文创建阶段为变量和函数分配内存的过程。在此过程中,为变量分配了内存,并为变量分配了值 undefined。对于函数,整个函数定义存储在内存中的特定地址,并且对其的引用放置在该特定执行上下文中的堆栈上。 ...
    编程 发布于2024-11-02
  • 了解 JavaScript 中的文档对象模型 (DOM)
    了解 JavaScript 中的文档对象模型 (DOM)
    你好,神奇的 JavaScript 开发者? 浏览器提供了一个称为文档对象模型 (DOM) 的编程接口,它允许脚本(特别是 JavaScript)与网页布局进行交互。网页的文档对象模型 (DOM) 是一种分层树状结构,它将页面的组件排列成对象,由浏览器在加载时创建。借助此范例,文档...
    编程 发布于2024-11-02
  • 开始使用 SPRING BATCH 进行编程
    开始使用 SPRING BATCH 进行编程
    Introduction Dans vos projets personnels ou professionnels, Il vous arrive de faire des traitements sur de gros volumes de données. Le traite...
    编程 发布于2024-11-02
  • 使用 CSS 让您的 Github 个人资料脱颖而出
    使用 CSS 让您的 Github 个人资料脱颖而出
    以前,自定义 Github 个人资料的唯一方法是更新图片或更改名称。这意味着每个 Github 配置文件看起来都一样,自定义它或脱颖而出的选项很少。 从那时起,您可以选择使用 Markdown 创建自定义部分。您可以包括您的简历、您的兴趣和爱好,让您的个人资料反映您的身份。这是任何人在访问您的个人资...
    编程 发布于2024-11-02
  • TypeScript 实用程序类型:增强代码可重用性
    TypeScript 实用程序类型:增强代码可重用性
    TypeScript 提供内置实用程序类型,允许开发人员有效地转换和重用类型,使您的代码更加灵活和 DRY。在本文中,我们将探讨关键实用程序类型,例如 Partial、Pick、Omit 和 Record,以帮助您将 TypeScript 技能提升到新的水平。 Partial:使所有属性可选 部分实...
    编程 发布于2024-11-02
  • 电报 window.open(url, &#_blank&#);在ios上工作很奇怪
    电报 window.open(url, &#_blank&#);在ios上工作很奇怪
    我正在制作一个电报机器人,我想添加将一些信息从小型应用程序转发到聊天的选项。我决定使用 window.open(url, '_blank');在我在 iPhone 上尝试之前它一直运行良好。我没有转发,而是分享(这是一件大事,我正好需要转发一条消息)。我有一些如何处理它的想法,但它们...
    编程 发布于2024-11-02
  • 谁是前端开发人员?
    谁是前端开发人员?
    当今互联网上每个网站或平台的用户界面部分都是前端开发人员工作的结果。他们参与创建用户友好的界面,确保网站的外观和功能。但到底谁是前端开发人员呢?我简单解释一下。 用户看到的部分是前端 打开网站时首先看到的是网页界面:颜色、按钮、文字、动画。这都是由前端开发人员创建的。前端是网站或应用...
    编程 发布于2024-11-02
  • 如何使用保留的 CSS 样式将 HTML 内容另存为 PDF?
    如何使用保留的 CSS 样式将 HTML 内容另存为 PDF?
    使用 CSS 将 HTML 内容保存为 PDF在 Web 开发中,即使将内容导出为不同格式,保持视觉美观也至关重要。当尝试将 HTML 元素另存为 PDF 时,这可能会带来挑战,因为 CSS 样式可能会在转换过程中丢失。对于必须在保存的 PDF 中保留 CSS 的情况,请考虑使用以下方法:创建新窗口...
    编程 发布于2024-11-02
  • 为什么使用 Print_r() 时要向 DateTime 对象添加幻像属性?
    为什么使用 Print_r() 时要向 DateTime 对象添加幻像属性?
    Print_r() 更改 DateTime 对象Print_r() 向 DateTime 对象添加属性,从而在调试期间启用自省。此行为是 PHP 5.3 中引入的内部功能的副作用,它将幻像公共属性分配给转储到文本的实例。要避免这些属性引起的错误,请改用反射。然而,不建议寻找这些属性,因为它们没有在类...
    编程 发布于2024-11-02
  • C 语言的数据结构和算法:适合初学者的方法
    C 语言的数据结构和算法:适合初学者的方法
    在 C 语言中,数据结构和算法用于组织、存储和操作数据。数据结构:数组:有序集合,使用索引访问元素链表:通过指针链接元素,支持动态长度栈:先进后出 (FILO) 原则队列:先进先出 (FIFO) 原则树:分级组织数据算法:排序:按特定顺序排序元素搜索:在集合中查找元素图形:处理节点和边之间的关系实战...
    编程 发布于2024-11-02

免责声明: 提供的所有资源部分来自互联网,如果有侵犯您的版权或其他权益,请说明详细缘由并提供版权或权益证明然后发到邮箱:[email protected] 我们会第一时间内为您处理。

Copyright© 2022 湘ICP备2022001581号-3