Django之同时新增数据到两个数据库表与同时返回两个表的数据(插拔式)
- models:比如有以下三个模型
from django.db import models
"""
基类,其他类继承即可获得对应的字段
"""
class BaseModel(models.Model):
updated_tm = models.DateTimeField(auto_now=True)
created_tm = models.DateTimeField(auto_now_add=True)
class Meta:
abstract = True
"""
项目列表
"""
class ProjectList( BaseModel):
project_id = models.AutoField(help_text="项目ID", primary_key=True)
project_name = models.SlugField(max_length=128, help_text="项目名称", unique=True)
class Meta:
db_table = 'project_list'
verbose_name = '项目列表信息'
verbose_name_plural = verbose_name
"""
项目详情
"""
class ProjectDetail(BaseModel):
project_introduction = models.CharField(max_length=128, help_text="用户简介")
project_info = models.ForeignKey(to=ProjectList, on_delete=models.DO_NOTHING, db_constraint=False, related_name='user')
class Meta:
db_table = project_detail'
verbose_name = '项目详情信息'
verbose_name_plural = verbose_name
一、同时新增数据到两个数据库表
- views
from rest_framework import filters, mixins, generics
from rest_framework.viewsets import GenericViewSet
class ProjectListView(mixins.CreateModelMixin, GenericViewSet):
queryset = Account.objects.filter(is_delete=0).all().order_by("-created_tm")
def create(self, request, *args, **kwargs):
# 先定义两个dict
project_list_dict = {}
project_detail_dict = {}
# 使用 ._meta.get_fields() 获取数据库表的全部字段,再使用field.name获取全部的字段名称,放入各自的dict,不存在的自动忽略掉
for item in request.data.items():
if item in [field.name for field in ProjectList._meta.get_fields()]:
project_list_dict [item[0]] = item[1]
elif item in [field.name for field in ProjectDetail._meta.get_fields()]:
project_detail_dict [item[0]] = item[1]
# 从上面的models可以看到,项目详情与项目列表两张表是有关联的,所以,新增数据的时候,先现在列表,新增成功,生成ID后,再新增详情,并通过ID与列表数据关联起来
# 检查项目是否存在,项目名称唯一约束,Serializer内设置必填
try:
# 存在就直接失败
ProjectList.objects.get(project_name=request.data.get('project_ame'))
return xxx
except Account.DoesNotExist:
# 如果不存在,先调用ProjectList表新增数据
try:
project_create = ProjectList.objects.update_or_create(defaults=project_list_dict, project_name=project_list_dict["project_ame"])
# 如果ProjectList表新增数据成功,则通过project_info,在ProjectDetail新增对应的数据
if project_create:
project_id = ProjectList.objects.filter(project_name=project_list_dict["project_ame"]).values('project_id').first()
ProjectDetail.objects.update_or_create(defaults=project_detail_dict, project_info=project_id["project_id"])
return xxx
except Exception as e:
return e
二、同时返回两个表的数据(插拔式)
- 插拔式的好处:即插即用,需要时才调用,不需要则不调用
- 从ProjectDetail这个models我们可以看到,是没有定义project_id和project_name的,但我们是与ProjectList关联的,所以,我们可以通过project_info,返回ProjectList已定义的project_id和project_name
# 我们只需要把ProjectDetail改成以下这样子就可以了
class ProjectDetail(BaseModel):
project_introduction = models.CharField(max_length=128, help_text="用户简介")
project_info = models.ForeignKey(to=ProjectList, on_delete=models.DO_NOTHING, db_constraint=False, related_name='user')
class Meta:
db_table = project_detail'
verbose_name = '项目详情信息'
verbose_name_plural = verbose_name
@property
def project_id(self):
return self.project_info.project_id
@property
def project_name(self):
return self.project_info.project_name
# 然后在序列化器内直接调用project_id和project_name即可
class ProjectDetailSerializer(serializers.ModelSerializer):
class Meta:
model = ProjectDetail
fields = ('project_id', 'project_name', 'project_introduction',)
Django之同时新增数据到两个数据库表与同时返回两个表的数据(插拔式)的更多相关文章
- Oracle数据库日期范围查询的两种实现方式
参考文档:http://database.51cto.com/art/201108/288058.htm Oracle数据库日期范围查询有两种方式:to_char方式和to_date方式,接下来我们通 ...
- Django orm 中 python manage.py makemigrations 和 python manage.py migrate 这两条命令用途
生成一个临时文件 python manage.py makemigrations 这时其实是在该app下建立 migrations目录,并记录下你所有的关于modes.py的改动,比如0001_ini ...
- Django 06 Django模型基础1(ORM简介、数据库连接配置、模型的创建与映射、数据的增删改查)
Django 06 Django模型基础1(ORM简介.数据库连接配置.模型的创建与映射.数据的增删改查) 一.ORM系统 #django模型映射关系 #模型类-----数据表 #类属性-----表字 ...
- 使用Red Gate Sql Data Compare 数据库同步工具进行SQL Server的两个数据库的数据比较、同步
Sql Data Compare 是比较两个数据库的数据是否相同.生成同步sql的工具. 这一款工具由Red Gate公司出品,我们熟悉的.NET Reflector就是这个公司推出的,它的SQLTo ...
- php同步mysql两个数据库中表的数据
分别创建两个数据库和两张表study库-zone表teaching库-area表 //****SQL脚本****// 1.创建teaching数据库area数据表 create database te ...
- MVC怎么在同一个action返回两个表的数据
一般返回一个model这样 @model MvcMusicStore.Models.Album 方法: public ActionResult Details(int id) { ...
- Oracle两张表关联批量更新其中一张表的数据
Oracle两张表关联批量更新其中一张表的数据 方法一(推荐): UPDATE 表2 SET 表2.C = (SELECT B FROM 表1 WHERE 表1.A = 表2.A) WHERE EXI ...
- 运算符关键字。数据区别大小写。日期范围。判空的两种写法。NOT IN的两种写法。IN范围可含NULL,但NOT IN值范围不能含NULL。
比较:>,<,=,>=,<=,<>(!=) 逻辑:AND,OR,NOT 范围:BETWEEN...AND... 范围:IN,NOT IN 判空:IS NULL, I ...
- 用java实现操作两个数据库的数据
1.首先需要在jdbc的配置文件里面配置两个数据库的连接 数据库1的配置 driverClassName=com.mysql.jdbc.Driverurl=jdbc:mysql://地址:3306/数 ...
随机推荐
- Java面试题(四)--RabbitMQ
1.MQ有哪些使用场景?(高频) 异步处理:用户注册后,发送注册邮件和注册短信.用户注册完成后,提交任务到 MQ,发送模块并行获取 MQ 中的任务. 系统解耦:比如用注册完成,再加一个发送微信通知.只 ...
- Ray类定义
定义光线,书中已经有原理. 类声明: #ifndef __RAY_HEADER__ #define __RAY_HEADER__ #include "geometry.h" cla ...
- 什么是 DevOps?看这一篇就够了!
本文作者:Daniel Hu 个人主页:https://www.danielhu.cn/ 目录 一.前因 二.记忆 三.他们说-- 3.1.Atlassian 回答"什么是 DevOps?& ...
- CSS 布局(一):Flex 布局
主轴和纵轴 对某一盒子模型添加display: flex;属性后,称之为 Flexible Box 模型(或称之为 flexbox),即弹性盒子模型,简称弹性盒子. 弹性盒子为子元素提供了强大的空间分 ...
- SpringBoot Excel导入导出
一.引入pom.xml依赖 <dependency> <groupId>org.springframework.boot</groupId> <artifac ...
- Postfix别名邮件与SASL验证
Postfix别名邮件与SASL验证 环境简介 系统: CentOS 8.3.2011 软件包: postfix-2:3.3.1-12.el8.x86_64 cyrus-sasl-2.1.27-5.e ...
- ping: sina.cn: Name or service not known
该方法针对Ubuntu18及以后版本. 第一次遇到ping:报错Name or service not known这个问题在百度上找了很久说的都是什么修改 /etc/resolv.conf,但每次修改 ...
- 在hyper-v虚拟机中安装并配置linux
虽然都是自己写的,还是贴个原文链接吧,如果文章里的图片错乱了,可能就是我贴错了,去看原文吧. 多图警告 WSL2真香? WSL2相比于WSL1前者更类似于虚拟机,配合上Windoes Terminal ...
- MySQL InnoDB缓存
1. 背景 对于各种用户数据.索引数据等各种数据都是需要持久化存储到磁盘,然后以"页"为单位进行读写. 相对于直接读写缓存,磁盘IO的成本相当高昂. 对于读取的页面数据,并不是使用 ...
- flutter系列之:flutter中常用的ListView layout详解
目录 简介 ListView详解 ListView中的特有属性 ListView的构造函数 ListView的使用 总结 简介 ListView是包含多个child组件的widget,在ListVie ...