Python 使用池而不是关闭数据库连接的SQLAlchemy

Python 使用池而不是关闭数据库连接的SQLAlchemy,python,mysql,multithreading,sqlalchemy,Python,Mysql,Multithreading,Sqlalchemy,我发现SQLAlchemy并没有释放数据库连接(在我的例子中),所以这会导致服务器崩溃。连接由不同的螺纹制成 这是简化的代码 “”“ 测试从多个线程调用时查看数据库连接分配大小 """ 从时间上导入睡眠 从线程导入线程,当前线程 导入uuid 从sqlalchemy导入func,或 从sqlalchemy导入事件 从sqlalchemy导入ForeignKey、Column、Integer、String、DateTime、UniqueConstraint 从sqlalchemy导入创建引擎 从s

我发现SQLAlchemy并没有释放数据库连接(在我的例子中),所以这会导致服务器崩溃。连接由不同的螺纹制成

这是简化的代码

“”“
测试从多个线程调用时查看数据库连接分配大小
"""
从时间上导入睡眠
从线程导入线程,当前线程
导入uuid
从sqlalchemy导入func,或
从sqlalchemy导入事件
从sqlalchemy导入ForeignKey、Column、Integer、String、DateTime、UniqueConstraint
从sqlalchemy导入创建引擎
从sqlalchemy.orm导入sessionmaker
从sqlalchemy.orm导入作用域_会话
从sqlalchemy.orm导入关系
从sqlalchemy.orm导入作用域的_会话,会话
从sqlalchemy.ext.declarative导入声明性基础
从sqlalchemy.types导入整数、日期时间、字符串、布尔值、文本、浮点值
从sqlalchemy.engine导入引擎
从sqlalchemy.pool导入NullPool
#MySQL
SQLALCHEMY_数据库='mysql'
SQLALCHEMY_数据库_URI='mysql+pymysql://amalgam:amalgam@localhost/amalgam?字符集=utf8mb4'#https://stackoverflow.com/questions/47419943/pymysql-warning-1366-incorrect-string-value-xf0-x9f-x98-x8d-t
SQLALCHEMY_ECHO=False
SQLALCHEMY_引擎_选项={'pool_size':40,'max_overflow':0}
SQLALCHEMY\u隔离\u级别=“自动提交”
#数据库引擎
#引擎=创建引擎(SQLALCHEMY\u数据库\u URI,echo=SQLALCHEMY\u echo,池\u回收=3600,
#隔离等级=SQLALCHEMY隔离等级,
#**SQLALCHEMY\u引擎\u选项
#)#连接到服务器
引擎=创建引擎(SQLALCHEMY数据库),
echo=SQLALCHEMY\u echo,
#poolclass=NullPool,
回收池=3600,
隔离等级=SQLALCHEMY隔离等级,
**SQLALCHEMY\u引擎\u选项
)#连接到服务器
会话工厂=会话生成器(绑定=引擎)
Base=声明性_Base()
#ORM实体
类用户(基本):
级别_正常=‘正常’
级别_ADMIN='ADMIN'
__tablename_=“用户”
id=列(整数,主键=True)
name=Column(字符串(100),null=True)
email=Column(字符串(100),null=True,unique=True)
password=Column(字符串(100),null=True)
级别=列(字符串(100),默认值=级别\u正常值)
#工人
否=10
工人=[]
_作用域会话工厂=作用域会话(会话工厂)
def作业(作业id):
会话=_范围的_会话_工厂()
打印(“作业为{}”。格式(作业id))
user=user(name='user{}{}'。格式(job_id,uuid.uuid4()),email='who care{}{}'。格式(job_id,uuid.uuid4())
session.add(用户)
session.commit()
session.close()
打印(“作业{}完成”。格式(作业id))
睡眠(10)
#创建工作线程
对于范围内的i(否):
append(线程(target=job,kwargs={'job_id':i}))
#启动它们
对于工人中的工人:
worker.start()
#加入他们
对于工人中的工人:
worker.join()
#请留出一些时间查看MySQL的“showProcessList;”命令
睡眠(10)
程序到达的那一刻

睡眠(10)
我负责管理

显示进程列表;
它给出了以下结果-这意味着到DB的所有连接仍然有效

如何强制关闭这些连接?

注:我可以利用

poolclass=NullPool

但是我觉得这个解决方案限制太多了-我希望仍然可以访问数据库池,但能够在需要时以某种方式关闭连接

pool_size–要维护的池的大小,默认为5。这 是将在中持续保持的最大连接数 游泳池。请注意,池开始时没有连接;一旦这个 请求的连接数,该连接数将 保持池大小可以设置为0,表示没有大小限制;到 禁用池,请改用
空池

max_overflow–池的最大溢出大小。号码是什么时候 已签出的连接数达到池\u size中设置的大小, 其他连接将返回到此限制。当那些 其他连接将返回到池,它们将断开连接 并被丢弃。因此,同时发生的事件总数 池允许的连接是池大小+最大溢出,并且 池将允许的“休眠”连接总数为 泳池大小。max_overflow可以设置为-1,表示没有溢出 限制;对并发事件的总数不设限制 连接。默认值为10

SQLALCHEMY\u引擎\u选项={'pool\u size':40,'max\u overflow':0}
鉴于上述情况,此配置要求SQLAlchemy保持多达40个连接处于打开状态

如果您不喜欢这样,但希望保持某些连接可用,可以尝试以下配置:

SQLALCHEMY\u引擎\u选项={'pool\u size':10,'max\u overflow':30}

这将在池中保留10个持久连接,如果同时请求,则最多将突发40个连接。任何超出配置池大小的连接在签回池后都会立即关闭。

以下是

pool_size–要维护的池的大小,默认为5。这 是将在中持续保持的最大连接数 游泳池。请注意,池开始时没有连接;一旦这个 请求的连接数,该连接数将 保持池大小可以设置为0,表示没有大小限制;到 禁用池,请改用
空池

max_overflow–池的最大溢出大小。号码是什么时候 已签出的连接数达到池\u size中设置的大小, 附加连接