Python 从0开始 一步步基于Django创建项目(13)将数据关联到用户

在city_infos应用程序中,每个城市信息条目是关联到城市的,所以只需要将城市条目关联到用户即可。

将数据关联到用户,就是把‘顶层’数据关联到用户。

设计思路:

1、修改顶层数据模型,向其中添加‘用户’属性

2、根据模型更新数据库

3、在数据显示部分,根据发起request的用户,显示与该用户匹配的内容

1)在cities页面显示与用户关联的city信息条目

2)在city页面,显示与那些city信息条目关联的具体信息

3)用户不能查看与自己不匹配的edit_entry页面,更不能进行编辑

4、将新主题关联到用户

5、确保主题下的新条目是其隶属的用户添加

步骤如下:

1、修改C:\D\Python\Python310\study\snap_gram\city_infos路径下的models.py文件。

首先在文件中包含django自带的User类。

from django.contrib.auth.models import User

然后修改City类

owner = models.ForeignKey(User,on_delete=models.CASCADE)

给City类添加owner属性,该属性值是User对象的ID,User对象的ID作为外键,与City对象相关联。采用级联删除,即删除对象的同时,删除该对象关联的City。

2、确认有哪些User对象的ID可用

使用django shell查询当前的用户信息。获得两个用户名称,及其ID。

(sg_env) C:\D\Python\Python310\study\snap_gram>python manage.py shell
Python 3.10.11 (tags/v3.10.11:7d4cc5a, Apr  5 2023, 00:38:17) [MSC v.1929 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
(InteractiveConsole)
>>> from django.contrib.auth.models import User
>>> User.objects.all()
<QuerySet [<User: sg_admin>, <User: 12344321>]>
>>> for user in User.objects.all():
...     print(user.username,user.id)
...
sg_admin 3
12344321 4
>>>

3、根据模型,更新数据库,

首先,生成数据库更新文件0002_city_owner。在文件中,要求将City表中,所有条目关联到ID为3的用户,即sg_admin

(sg_env) C:\D\Python\Python310\study\snap_gram>python manage.py makemigrations city_infos
It is impossible to add a non-nullable field 'owner' to city without specifying a default. This is because the database needs something to populate existing rows.
Please select a fix:
 1) Provide a one-off default now (will be set on all existing rows with a null value for this column)
 2) Quit and manually define a default value in models.py.
Select an option: 1
Please enter the default value as valid Python.
The datetime and django.utils.timezone modules are available, so it is possible to provide e.g. timezone.now as a value.
Type 'exit' to exit this prompt
>>> 3
Migrations for 'city_infos':
  city_infos\migrations\0002_city_owner.py
    - Add field owner to city

其次,使用该更新文件,更新数据库。

(sg_env) C:\D\Python\Python310\study\snap_gram>python manage.py migrate
Operations to perform:
  Apply all migrations: admin, auth, city_infos, contenttypes, sessions
Running migrations:
  Applying city_infos.0002_city_owner... OK

4、使用django shell查看city信息,确认数据库修改成功

(sg_env) C:\D\Python\Python310\study\snap_gram>python manage.py shell
Python 3.10.11 (tags/v3.10.11:7d4cc5a, Apr  5 2023, 00:38:17) [MSC v.1929 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
(InteractiveConsole)
>>> from city_infos.models import City
>>> for city in City.objects.all():
...     print(city.name,city.owner)
...
北京 sg_admin
墨尔本 sg_admin
悉尼 sg_admin
>>>

5、修改C:\D\Python\Python310\study\snap_gram\city_infos路径下的views.py文件,修改cities函数。使得登录用户只能查看隶属于自己的city条目。

@login_required
def cities(request):
    #request中包含发起请求的用户信息,核对用户信息与city的owner属性
    #用户信息一致,才能通过filter检查,展现出来
    cities = City.objects.filter(owner=request.user).order_by('date_added')
    context = {'cities':cities}
    return render(request,'city_infos/cities.html',context)

6、使用不同用户登录,查看cities页面

当以用户12344321登录时查看不到任何city信息,如下图所示:

以用户sg_admin登录时,则可查看到city信息,因为已经将这些信息全部关联到该用户。

7、修改C:\D\Python\Python310\study\snap_gram\city_infos路径下的views.py文件,修改city函数。使得登录用户只能查看隶属于自己的entry条目。

如果不做此处的修改,任何已登录的用户都可输入类似于http://localhost:8000/cities/1/的URL,来访问不隶属于自己的city主题的页面。

from django.http import Http404

@login_required
def city(request,city_id):
    city = City.objects.get(id=city_id)
    #核对用户,显示隶属于该用户的信息,否则抛出404错误
    if city.owner != request.user:
        raise Http404
    entries = city.entry_set.order_by('date_added')
    context = {'city':city,
               'entries':entries}
    return render(request,'city_infos/city.html',context)

8、修改C:\D\Python\Python310\study\snap_gram\city_infos路径下的views.py文件,修改edit_entry函数。使得登录用户只能查看隶属于自己的entry条目。

如果不做此处修改,将出现下图的问题。12344321用户查看了不隶属于自己的city的条目,并能够打开和编辑edit_entry页面

修改程序如下:

@login_required
def edit_entry(request,entry_id):
    #request=GET时,返回原有Entry内容,request=POST时,提交新Entry内容
    entry = Entry.objects.get(id=entry_id)  # 找到指定的entry
    city = entry.city
    
    #检查用户匹配
    if city.owner != request.user:
        raise Http404
    
    if request.method != 'POST':#初次请求,使用当前条目填充表单
        form = EntryForm(instance=entry)
    else:#处理POST提交的数据
        form = EntryForm(instance=entry, data=request.POST)
        if form.is_valid():  # Django自动检查提交数据的合法性
            form.save()
            return redirect('city_infos:city',city_id=city.id)  # 页面重定向
    context = {'entry':entry,'city': city, 'form': form}  # 程序不进入if块,或者没有通过有效性验证,都执行该行代码
    return render(request, 'city_infos/edit_entry.html', context)

9、修改C:\D\Python\Python310\study\snap_gram\city_infos路径下的views.py文件,修改new_city函数。将新主题关联到用户。

@login_required
def new_city(request):
    '''Add new City'''
    if request.method != 'POST':#未提交数据时,创建一个新表单,此时request.method=='GET'
        form = CityForm()
    else:#提交数据时
        form = CityForm(data=request.POST)#data是用户刚刚POST的数据,如此则form包含用户提交的数据
        if form.is_valid():#Django自动检查提交数据的合法性
            new_city = form.save(commit=False) #commit=False表示先不写库
            new_city.owner = request.user
            new_city.save() #改完了owner属性,然后写库
            return redirect('city_infos:cities')#页面重定向
    context = {'form':form}#程序不进入if块,或者没有通过有效性验证,都执行该行代码
    return render(request,'city_infos/new_city.html',context)

10、修改C:\D\Python\Python310\study\snap_gram\city_infos路径下的views.py文件,修改new_entry函数。确保新增条目隶属的city,隶属于当前用户。

@login_required
def new_entry(request,city_id):
    '''Add new Entry to specific city'''
    city = City.objects.get(id=city_id)#找到指定的city
    #核实用户
    if city.owner != request.user:
        raise Http404

    if request.method != 'POST':#未提交数据时,创建一个新表单,此时request.method=='GET'
        form = EntryForm()
    else:
        form = EntryForm(data=request.POST)  # data是用户刚刚POST的数据,如此则form包含用户提交的数据
        if form.is_valid():  # Django自动检查提交数据的合法性
            #commit=False的作用:让Django创建一个新条目,赋值给new_entry,但是不保存到数据
            new_entry = form.save(commit=False)
            #通过设定city,将新条目与指定city关联
            new_entry.city = city
            #再将新条目,保存到数据
            new_entry.save()
            return redirect('city_infos:city',city_id=city_id)  # 页面重定向
    context = {'city':city,'form':form}#程序不进入if块,或者没有通过有效性验证,都执行该行代码
    return render(request, 'city_infos/new_entry.html', context)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/495067.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

泛微OA 主表字段更改 修改明细字段的必填或修改属性

1、申请类型&#xff1a;其它类&#xff0c;供应商、规格、金额必填。 2、申请类型&#xff1a;IT设备类&#xff0c;供应商、规格、金额可编辑。 <script>jQuery(document).ready(function(){//绑定主表字段变更事件WfForm.bindFieldChangeEvent("field6669",…

python实战之基础篇

1. 注释 # coding utf-8 # 该注释放到文件第一行, 这个注释告诉python解释器该文件的编码集是UTF-82. 导入语句有三种形式 import <模块名> from <模块名> import <代码元素> from <模块名> import <代码元素> as <代码元素别名>3. 获取…

C语言 大小写字母转换

目录 1.问题描述 1.1描述 1.2输入描述&#xff1a; 1.3输出描述&#xff1a; 1.4示例 1.5备注&#xff1a; 2.代码解读 2.1使用ASCII码值的版本 2.2使用getchar吸收回车的版本 2.3使用函数的版本 3.以下是三种方式的全部代码 4.结语 1.问题描述 1.1描述 实现字母的…

Vue过渡动画,组件动画,元素动画(vue2元素、组件过渡动画)

​简介&#xff1a;Vue的过渡动画允许你定义一个进入和离开的过渡&#xff0c;然后在元素的状态改变时自动应用这些过渡&#xff0c;提升用户体验。它通过 <transition> 标签 这个内置组件&#xff0c;在元素或组件的插入、更新和移除时应用过渡效果&#xff08;也就是动…

什么是 MySQL 回表?

什么是 MySQL 回表&#xff1f; 题目 什么是 MySQL 回表&#xff1f; 推荐解析 回表简介 1&#xff09;索引结构&#xff1a;MySQL 使用 B 树索引结构来加速数据的查找。B 树是一种多叉树&#xff0c;它的叶子节点中存储了完整的数据行&#xff0c;而非叶子节点存储了索引…

第十篇【传奇开心果系列】Python自动化办公库技术点案例示例:深度解读Python自动化操作Excel

传奇开心果博文系列 系列博文目录Python自动化办公库技术点案例示例系列博文目录 前言一、重要作用解说二、Python操作Excel的常用库介绍三、数据处理和分析示例代码四、自动化报表生成示例代码五、数据导入和导出示例代码六、数据可视化示例代码八、数据校验和清洗示例代码九、…

【海贼王之强者之路】经典动漫影视改编火爆剧情回合卡牌手游-Win服务端源码视频架设教程-开放多区-GM后台-安卓苹果IOS双端版本!

【海贼王之强者之路】站长推荐经典动漫影视改编火爆剧情回合卡牌手游-2024年3月27日最新打包Win服务端源码视频架设教程-开放多区-GM后台-安卓苹果IOS双端版本&#xff01;

Dynamo一键清理Revit中未放置的房间和多余的房间

今天我们来解决一个Revit中比较常见的小问题&#xff0c;就是清理未放置的房间和多余的房间。 首先&#xff0c;我们可以先做个测试样例&#xff0c;看看问题在哪里&#xff0c;如下图&#xff0c;我简单画了个模型&#xff0c;生成一个房间明细表&#xff0c;如下图&#x…

【javaWeb 第三篇】Vue快速入门

VUE vue是一套前端框架&#xff0c;免除原生的js的DOM操作&#xff0c;简化书写 基于MVVM&#xff08;model-view-viewmodel&#xff09;思想&#xff0c;实现数据的双向绑定&#xff0c;将编程的关注放在数据上。 什么是框架&#xff1a; 框架相当于一个半成品&#xff0c;是一…

【Java程序设计】【C00391】基于(JavaWeb)Springboot的校园疫情防控信息管理系统(有论文)

基于&#xff08;JavaWeb&#xff09;Springboot的校园疫情防控信息管理系统&#xff08;有论文&#xff09; 项目简介项目获取开发环境项目技术运行截图 博主介绍&#xff1a;java高级开发&#xff0c;从事互联网行业六年&#xff0c;已经做了六年的毕业设计程序开发&#xff…

【SpringCloud微服务实战10】DevOps自动化部署微服务项目(Jenkins+Docker+K8s)

一、什么是 DevOps DevOps 是一种重视软件开发人员&#xff08;Developer&#xff09;和运维人员&#xff08;Operations&#xff09;之间沟通与协作的文化、运动或实践&#xff0c;目标在于快速交付高质量的软件产品和服务。DevOps 强调自动化流程、持续集成与交付&#xff08…

C语言二叉树和堆(个人笔记)

二叉树和堆 二叉树1二叉树的概念和结构1.1特殊的二叉树1.2二叉树的性质&#xff08;规定根节点的层数为1&#xff09;1.3二叉树的存储结构 2.二叉树的顺序结构和实现2.1二叉树的顺序结构2.2堆的概念和结构2.3堆的实现2.4堆的应用2.4.1堆排序 2.5TOP-K问题 3.二叉树的遍历4.二叉…

管理阿里云服务器ECS -- 网站选型和搭建

小云&#xff1a;我已经学会了如何登录云服务器ECS了&#xff0c;但是要如何搭建网站呢&#xff1f; 老王&#xff1a;目前有很多的个人网站系统软件&#xff0c;其中 WordPress 是使用非常广泛的一款&#xff0c;而且也可以把 WordPress 当作一个内容管理系统&#xff08;CMS…

Qt中QIcon图标设置(标题、菜单栏、工具栏、状态栏图标)

1 exe程序图标概述 在 Windows 操作系统中&#xff0c;程序图标一般会涉及三个地方&#xff1b; &#xff08;1&#xff09; 可执行程序&#xff08;以及对应的快捷方式&#xff09;的图标 &#xff08;2&#xff09; 程序界面标题栏图标 &#xff08;3&#xff09;程序在任务…

C语言什么是形参和实参?如何使⽤?

一、问题 在调⽤函数的时候&#xff0c;调⽤函数和被调⽤函数之间基本都会发⽣数据传递关系&#xff0c;这就要⽤到有参函数&#xff0c;⽽不传递数据的就需要⽆参函数。这样必然涉及形参和实参的概念&#xff0c;那么究竟什么是形参&#xff1f;什么又是实参呢&#xff1f;如何…

编译与链接

环境&#xff1a; 在ASCI C的任何一种实现中&#xff0c;存在两种不同的环境&#xff1a; 1.翻译环境&#xff0c;在这个环境中&#xff0c;源代码被转换为可执行的机器指令&#xff08;二进制指令&#xff09; 2.运行环境&#xff0c;用于实际执行代码。 流程:c文件->翻译…

(4)(4.3) Kogger Sonar

文章目录 前言 1 推荐硬件 2 配置回声探测仪模块 3 连接ArduPilot硬件 4 参数说明 前言 KOGGER 声纳(KOGGER Sonar)是一款结构紧凑、成本低廉的水下回声测深仪模块&#xff0c;带有 UART 接口&#xff0c;电源电压为 5-14v。 1 推荐硬件 CP210x USB->UART 转换器和安装…

脚本应使用项目的主要语言编写

原文&#xff1a;Joo Freitas - 2024.03.24 这是我长时间以来的一个深感赞同的观点。 我参与过的几乎所有项目&#xff0c;都有我们编写的用于自动化重复性过程的脚本。然而&#xff0c;大多数脚本在几周后变得过时且难以维护&#xff0c;因为我们要么不再需要它们&#xff0…

Towhee 小记

文章目录 关于 Towhee✨ 项目特点&#x1f393; 快速入门流水线预定义流水线自定义流水线 &#x1f680; 核心概念 关于 Towhee Towhee 是一个开源的 embedding 框架&#xff0c;包含丰富的数据处理算法与神经网络模型。通过 Towhee&#xff0c;能够轻松地处理非结构化数据&am…

31---JTAG电路设计

视频链接 JTAG电路设计&#xff08;JLINK&XILINX&ALTERA&#xff09;_哔哩哔哩_bilibili JTAG电路设计 1、JTAG简介 JTAG&#xff08;Joint Test Action Group&#xff09;&#xff1a;联合测试工作组&#xff0c;是在名为标准测试访问端口和边界扫描结构的IEEE的标…