解决Django transaction进行事务管理踩过的坑


Posted in Python onApril 24, 2021

概要

Transaction是django进行数据库原子性操作在python层面上的实现。

简单来说, 被transaction.atomic()包裹的代码块只在代码块顺利完成后进行数据库层面的commit。实际开发当中,遇到了一些问题。

1. transaction事务内不执行数据库的commit操作

除非手动commit

transaction最基本的功能。

代码场景:

在事务当前启动celery异步任务, 无法获取未提交的改动。

def example_view(request):
    with transaction.atomic():
        change_obj() # 修改对象变量
        obj.save()
        async_task.delay(obj.id)
def async_task(obj_id):
    obj = Model.objects.get(pk=obj_id)
    read_the_obj() # 读取对象信息

在使用transaction当中, Model.save()都不做commit,因此如果在transaction当中设置异步任务,使用get()查询数据库,将看不到对象在事务当中的改变.这也是实现”可重复读”的事务隔离级别,即同一个事务里面的多次查询都应该保持结果不变。

2.transaction只对数据库层的操作进行事务管理

不能理解为python操作的事务管理

代码如下:

def example_view(request):
    tag = False
    with transaction.atomic():
        tag = True
        change_obj() # 修改对象变量
        obj.save()
        raise DataError
    print("tag = ",tag)
tag = True #输出内容

即使事务代码块发生了DataError,事务回滚,也仅是数据库层面的回滚,针对python的操作依然已完成。

甚至是对Model.Object进行的操作会也会存在变量当中。

如:

def example_view(request):
    obj.changed = False
    with transaction.atomic():
        obj.changed = True
        change_obj() # 修改对象其他变量
        obj.save()
        raise DataError
    print("obj.changed = ",obj.changed)
obj.changed = True #输出内容

发生Dataerror异常的回滚仅在数据库层面操作,因此不可以根据model object的属性值判断是否正确完成了事务。

另外,虽然Django对数据库层面以ORM完成了很具体的抽象,但应该要清楚地意识到我们操作的model object和数据库内容本质不同,DJANGO只在查询和提交时进行数据库操作。

补充:Django 事务transaction.atomic()的使用方法

看代码吧~

from django.shortcuts import render
from django.http import HttpResponse
from django.views.generic import View
from django.db import transaction   # 导入事务 
 
# 类视图 (事务,@transaction.atomic装饰器)
class MyView(View): 
    @transaction.atomic
    # transaction.atomic装饰器可以保证该函数中所有的数据库操作都在一个事务中。
    def post(self, request):
 
        # 数据库操作1。。。
        # 数据库操作2。。。        
        return HttpResponse('ok') 
 
# 类视图 (事务,保存点的使用)
class MyView2(View):
    @transaction.atomic
    def post(self, request): 
        # 设置事务保存点
        s1 = transaction.savepoint()   # 可以设置多个保存点
 
        # 数据库操作。。。
 
        # 事务回滚 (如果发生异常,就回滚事务)
        transaction.savepoint_rollback(s1)  # 可以回滚到指定的保存点
 
        # 提交事务 (如果没有异常,就提交事务)
        transaction.savepoint_commit(s1)
 
        # 返回应答
        return HttpResponse('ok')

以上为个人经验,希望能给大家一个参考,也希望大家多多支持三水点靠木。如有错误或未考虑完全的地方,望不吝赐教。

Python 相关文章推荐
python中wx将图标显示在右下角的脚本代码
Mar 08 Python
用pywin32实现windows模拟鼠标及键盘动作
Apr 22 Python
浅谈Python中的作用域规则和闭包
Mar 20 Python
Python爬取数据并写入MySQL数据库的实例
Jun 21 Python
python+PyQT实现系统桌面时钟
Jun 16 Python
Python通过TensorFlow卷积神经网络实现猫狗识别
Mar 14 Python
Python实现微信消息防撤回功能的实例代码
Apr 29 Python
python标准库os库的函数介绍
Feb 12 Python
Python读取图像并显示灰度图的实现
Dec 01 Python
python Timer 类使用介绍
Dec 28 Python
Django与AJAX实现网页动态数据显示的示例代码
Feb 24 Python
Python中re模块的元字符使用小结
Apr 07 Python
pdf论文中python画的图Type 3 fonts字体不兼容的解决方案
Apr 24 #Python
Python使用UDP实现720p视频传输的操作
python通配符之glob模块的使用详解
Apr 24 #Python
Django debug为True时,css加载失败的解决方案
Apr 24 #Python
python 模块重载的五种方法
Apr 24 #Python
写一个Python脚本自动爬取Bilibili小视频
python实现图片批量压缩
Apr 24 #Python
You might like
PHP中使用匿名函数操作数据库的例子
2014/11/17 PHP
Laravel 数据库加密及数据库表前缀配置方法
2019/10/10 PHP
php判断某个方法是否存在函数function_exists (),method_exists()与is_callable()区别与用法解析
2020/04/20 PHP
Js的MessageBox
2006/12/03 Javascript
一个用js实现控制台控件的代码
2007/09/04 Javascript
实现checkbox全选、反选、取消JavaScript小脚本异常
2014/04/10 Javascript
使用js画图之圆、弧、扇形
2015/01/12 Javascript
JS获得选取checkbox整行数据的方法
2015/01/28 Javascript
javascript用函数实现对象的方法
2015/05/14 Javascript
jQuery实现的Tab滑动选项卡及图片切换(多种效果)小结
2015/09/14 Javascript
JS 插件dropload下拉刷新、上拉加载使用小结
2017/04/13 Javascript
详解使用angular-cli发布i18n多国语言Angular应用
2017/05/20 Javascript
详细分析单线程JS执行问题
2017/11/22 Javascript
JS基于贪心算法解决背包问题示例
2017/11/27 Javascript
如何利用@angular/cli V6.0直接开发PWA应用详解
2018/05/06 Javascript
详解使用Nuxt.js快速搭建服务端渲染(SSR)应用
2019/03/13 Javascript
Vue使用zTree插件封装树组件操作示例
2019/04/25 Javascript
利用原生JS实现data方法示例代码
2019/05/28 Javascript
基于layui内置模块(element常用元素的操作)
2019/09/20 Javascript
解决VUE双向绑定失效的问题
2019/10/29 Javascript
Python中遍历字典过程中更改元素导致异常的解决方法
2016/05/12 Python
Python的面向对象编程方式学习笔记
2016/07/12 Python
python中找出numpy array数组的最值及其索引方法
2018/04/17 Python
Python语言异常处理测试过程解析
2020/01/08 Python
Python进行特征提取的示例代码
2020/10/15 Python
印尼太阳百货公司网站:Matahari
2018/02/04 全球购物
意大利咖啡、浓缩咖啡和浓缩咖啡机:illy caffe
2019/03/20 全球购物
英国玛莎百货澳大利亚:Marks & Spencer Australia
2019/08/30 全球购物
Orlebar Brown官网:设计师泳裤和泳装
2020/12/08 全球购物
毕业生找工作推荐信
2013/11/21 职场文书
致短跑运动员广播稿
2014/01/09 职场文书
七年级生物教学反思
2014/01/30 职场文书
《蝙蝠和雷达》教学反思
2014/04/23 职场文书
谁动了我的奶酪读书笔记
2015/06/30 职场文书
600字作文之感受大自然
2019/11/27 职场文书
导游词之安徽巢湖
2019/12/26 职场文书