【SQLAlchemy】第二篇——连接失效及连接池

一、背景

为了节约资源,MySQL会对建立的连接进行监控,当某些连接处于不活跃状态的时间超过一个阈值时,则关闭它们。

用户可以执行show variables like '%wait_timeout%';来查看这个阈值:

请添加图片描述

可以看到,在默认的情况下,这个阈值是28800秒,即,如果一个连接处于不活跃的时间超过8小时,则该连接不再可用。

下面给出一个具体的例子。

1、为了能够快速验证,首先使用set global wait_timeout=10;语句将该阈值设置为10。

设置成功后需要通过show global variables like '%wait_timeout%';进行查看。为什么要加global?可以参考这里。

2、执行以下验证代码:

from sqlalchemy import create_engine, text
engine = create_engine('mysql+pymysql://root:123456@127.0.0.1:3306/platform')
sql = "select 1+1;"
with engine.connect() as conn:res = conn.execute(text(sql))print(res.fetchone()[0])

打印结果2

3、等待超过10秒钟后,再次执行上述代码中的with:部分,则会得到如下错误:

sqlalchemy.exc.OperationalError: (pymysql.err.OperationalError) (2013, 'Lost connection to MySQL server during query')

即无法连接到MySQL服务器。

二、问题

设想这样一个场景:通过flask启动了一个REST服务,该服务需要访问数据库,且每天被定时请求一次(除此之外无请求)。

按照上一节的讨论,由于两次请求间隔(24小时)超过了关闭阈值(8小时),因此在下一次发送请求时,会报出Lost connection的错误。

三、解决方案

一个可选的解决方案是,增加wait_timeout的值,使之超过24小时。但这样很可能导致数据库中存在大量的处于sleep状态的进程,从而造成资源的浪费。这里不考虑此种方案。

既然是连接失效,那么一种比较直观的解决方案就是在每次使用连接进行数据库操作前,先检验一下连接是否有效。有效就直接使用;无效则重新连接

SQLAlchemy提供了基于上述思路的解决方案——指定pool_pre_ping参数:

engine = create_engine('mysql+pymysql://root:123456@127.0.0.1:3306/platform', pool_pre_ping=True)

这样定义engine之后,再执行上面的验证例子可以发现,即使两次执行with:的间隔超过了阈值,仍可以执行成功。

四、更深入的分析

4.1 Engine与连接池

本系列的第一篇中说“可以将Engine对象视为连接池”,但严格来讲这是不正确的。要正确理解它们之间的关系,需要借助下面这张结构图:

请添加图片描述

最右侧是数据库,SQLAlchemy通过第三方的DBAPI与之进行连接——在上面的例子中,这个DBPAI是PyMySQL。而上述Engine对象则是通过PoolDialect来与DBPAI进行交互。

先说Dialect,这个单词的字面意思是“方言”,在这里可以引申为不同的数据库类型。在上面定义engine的url中的mysql实际上就告诉SQLAlchemy要初始化一个支持连接MySQLDialect类。

当使用create_engine函数创建Engine对象时,默认使用QueuePool来创建连接池,用户可以指定poolclass参数来选择不同的Pool。当调用Engineconnect()方法时,就会从连接池中获取一个连接对象来执行操作。

4.2 pool_pre_ping的限制

仔细分析不难看出,第三部分提供的方案是有弊端的。在使用从连接池获取的连接进行实际工作前,都需要向数据库服务器发送ping命令,这无疑会增加开销。

所谓的“发送ping命令”是一个概括的说法,有可能是通过连接向服务器发送了select 1;等简单的命令。

另外,如果服务器出现了性能瓶颈,可能导致ping命令迟迟得不到有效的相应,从而影响程序性能。

因为上述原因,pool_pre_ping方法被称为是“悲观的”。

4.3 乐观方法

上述悲观方法是被动式的——要等到连接不可用了之后,才能通过ping命令检测到。而乐观方法则是主动式的:通过在调用create_engine时设置pool_recycle参数来指定连接持续时间。这个参数的作用是,在达到pool_recycle的时间限制后,连接池将所有的连接回收,并重新进行连接。这样就保证了连接的有效性。

与悲观方法相比,乐观方法减轻了服务器的负担。

4.4 连接池

直观地查看一下连接池的作用:

# 代码由chatGPT生成
from sqlalchemy import create_engine, text
import concurrent.futures
import threading# 创建连接池引擎
# 这里限制了池中连接的数量为3,且不允许自动增加连接的数量
engine = create_engine('mysql+pymysql://root:123456@127.0.0.1:3306/test', pool_size=3, max_overflow=0)# 定义并发函数
# 为了能从数据库服务器查看连接的执行情况,执行了一个休眠命令
def run_query(query_num):print('线程:', threading.current_thread().native_id, '正在执行...')with engine.connect() as conn:ret = conn.execute(text(f'select sleep({query_num})'))print('线程:', threading.current_thread().native_id, '执行完成')return ret.one()[0]# 使用多线程并发执行查询
with concurrent.futures.ThreadPoolExecutor(max_workers=10) as executor:# 线程池中共有10个线程futures = []for i in range(10):futures.append(executor.submit(run_query, 5))for future in concurrent.futures.as_completed(futures):print(future.result())

执行上述代码,首先在控制台上打印出类似如下的内容:

线程: 517317 正在执行...
线程: 517318 正在执行...
线程: 517319 正在执行...
线程: 517321 正在执行...
线程: 517322 正在执行...
线程: 517320 正在执行...
线程: 517323 正在执行...
线程: 517325 正在执行...
线程: 517326 正在执行...
线程: 517324 正在执行...

这说明,10个线程已经开始执行。但由于连接池中只有3个连接,此时通过show processlist可以看到有三个连接在执行操作:

请添加图片描述

结合控制台打印的输出,当有线程执行完成时,数据库中对应连接的Time字段又从0开始计时,这说明改连接被复用了。

当所有的线程执行完成后,上述三个连接消失。

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

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

一个程序员的意想流

Readme:记录生活、工作、学习中自己的思考和想法,但是可能很杂乱的。目的为了提升自己BB的能力。 2023.3.9: 作为一个嵌入式(底层)开发者,通过对Linux内核的不断深入,包括VFS、内存管理、进程管…

ChatGPT提示词工程师 | prompt engineering | 吴恩达教你写提示词 课程笔记

Lecture1 引言 两种大语言模型(LLMs,Large Language Models): Base LLM: Predicts next word, based on text training dataInstruction Tuned LLM: Tries to follow instructions Lecture2 指南 使用C…

chatgpt提示词学习指南,提示词工程,提示词汇总

这篇gpt提示词指南我会随着我的学习一直更新。 结构 好的提示词角色(能力)上下文详细的指令说明风格输出格式 角色(必填):可以给模型提供特定的能力,让它更好的解决我们的问题,在声明角色后,…

股票入门基础知识之投资家有哪些?股票入门基础知识中的投资角色

《量化分析海龟训练营》课程学员:一般来说哪些人投资做得好呢? 同济桥博士:投资是一门科学,有很多研究投资的人拿到过诺贝尔经济学奖,投资做得好有五类人:科学家、哲学家、神学家、交易员、民间高手。最后…

投资理财启蒙之理财入门必看?

投资基金股票是怎么赚钱的 ? 公司上市就是为了融资扩大规模,需要在上海/深圳证券交易所去审批,现在国家注册制落实后,现在企业要上市很严格的需要公开公司的各方面情况的 ,投资渠道也正规,比如支付宝/微信&…

金融业务知识(2):股票交易的基本流程

股票交易的基本流程 (一)开户 需要开立证券账户和资金账户 证券账户用来记载投资者所持有的证券种类、数量和相应的变动情况 资金账户则用来记载和反映投资者买卖证券的货币收付和结存数额。 开立证券账户和资金账户后,投资者买卖证券所涉…

基金投资入门3:中外常见金融指数类型说明

在每天的新闻及财经类文章中,经常听到当日的上证综指、深证成指、沪深300指数是多少点、涨跌幅是多少。 大家潜意识中认为指数点、涨跌幅越高越好,至于各指数代表的是什么意思并不清楚,但是对于刚接触投资理财的朋友,只有搞懂各指…

最新FRM一级二级handbook官方教材原版书

最新FRM一级二级教材囊括了FRM考试需要掌握的所有要点和难点,并进行了深入细致地讲解。本教材紧扣GARP协会新版教材的章节编排,加入了编著者多本同类教材的编写经验和一线教学经验的总结,并关注了国际国内**的风控热点。

证券交易金融知识学习(1)

学习目标: 需要做一些关于投资交易软件的测试,需要了解操作背后的交易意义,需要学习一些金融基础知识。本人是金融证券交易的小白,从0开始学习。故记录一些金融知识学习的笔记,比较零散,目的是为了让自己复…

【转】投资从入门到精通,七本经典书籍

http://www.create.hk/archives/158 随着我国股市的复苏、资本市场的规律,却去研究一些“技术分析”之类的理论,是不科学的。“技术分析”属于玄学,也就是形而上学。目前在我国东部沿海地区,由于投资者知识和经验的日益增多&…

投资学翻译1

生产网络与股票回报:垂直创造性破坏的作用 本文从实证和理论两方面研究了生产网络中企业风险与企业与消费者距离之间的关系。我们记录了两个新事实:离消费者越远的企业,其风险溢价越高,对总生产率的影响也越大。我们用一个具有多层生产过程的一般均衡模…

电商设计师(美工)必备的素材网站|优图!

平时我们再做设计的时候,时间长了也很苦恼,而甲方或者老班总是要求我们要做高大上或者有灵感的作品。而灵感不是说来就来的呀~~~ 电商大致的素材类型你知道么? 首焦海报、PC促销海报、M端海报、大促首页、M端大促页面、页面设计、详情页、电…

电商设计师(美工)必备|模板素材网站!

优图网:站内的分类特别清新,每日都有新的素材图片更新,韩国清新风比较明显,是难得的符 合国情的素材网站! 网址:www.uppsd.com 素材路上: 大量针对淘宝设计这一块的素材,前段时间刚…

【电商】电商后台设计—售后流程

在电商系统中,订单售后是整个平台系统最为重要的组成部分之一,好的售后产品能够极大提升用户对于整个电商产品的用户体验,提高口碑。产生售后的原因很多,处理平台本身的问题还有其他物流时效、配送员服务态度等因素,产…

【电商】电商后台系统整体介绍

电商后台系统支撑了电商企业亿万级的交易量,其重要性不言而喻。本文章将从电商后台系统的的各个模块来分析,让大家的后台真正”硬“起来。 当前关于产品经理的文章主要偏向方法论、业界动向、产品分析、用户体验、交互等,关于后台系统的文章比…

跨境电商必备:SS客服聊天机器人,无需再逐一回复消息,彻底解放你的双手,SaleSmartly让你的营销变得更加简单

跨境电商必备:SS客服聊天机器人,无需再逐一回复消息,彻底解放你的双手,SaleSmartly让你的营销变得更加简单 关键词:跨境电商、聊天机器人、智能客服 AI在近年来的发展十分迅速,人工智能和自动化成为科技发…

电商设计师(美工)必备的素材网站!

优图网 站内的分类特别清新,每日都有新的素材图片更新,韩国清新风比较明显,是难得的符合国情的素材网站! 网址:www.uppsd.com MaterialUp —— 每日 Material Design 设计案例 Material Design, Daily – MaterialU…

【电商】电商后台设计—优惠券

优惠券是每一个电商平台必备的模块,是吸引和留住用户的重要部分。让我们一起来了解电商平台的优惠券模块是怎么设计的吧,也希望能给各位小伙伴带来干货知识,助力成长。 各位小伙伴好,本文是电商后台设计系列文章的第五篇&#xff…

电商后台设计

一、电商后台系统到底是怎么回事儿?二、如何设计实用的商品中心(前端显示篇) 一、 商品常用概念介绍二、商品基础资料设计三、复盘 三、如何设计实用的商品中心 (后台设计篇) 一、商品类目、商品基本信息二、商品属性三、规格、价…