connection-pooling - python中的MySQL连接池?

标签 connection-pooling python-multiprocessing pymysql mysql-connector-python time-wait

我正在尝试使用Python处理大量数据并在MySQL中维护处理状态。然而,令我惊讶的是 python-mysql 没有标准连接池(如 Java 中的 HikariCP)。

我最初使用 PyMySQL,一切都很棒,直到程序运行了最初几个小时。几个小时后,事情开始失败。我收到很多错误,例如:

pymysql.err.OperationalError: (2003, "Can't connect to MySQL server on '127.0.0.1' ([Errno 99] Cannot assign requested address)")

此外,许多端口陷入 TIME_WAIT 状态,因为我由于缺乏连接池而过于频繁地打开和关闭连接

/d/p/950 ❯❯❯ netstat -nt | wc -l
84752

thisthis ,我尝试设置 tcp_fin_timeout 和 ip_local_port_range,但几乎没有任何改善。

echo 30 > /proc/sys/net/ipv4/tcp_fin_timeout
echo 15000 65000 > /proc/sys/net/ipv4/ip_local_port_range

然后我发现MySQL提供了mysql.connector,它带有pooling功能。完成所有这些之后,性能实际上下降了。更多进程开始失败。我正在使用 Python 的多处理模块在 24 核机器上同时运行 29 个进程(multiprocessing.Pool 默认选择此否)。以下是代码,当然我使用 .my.cnf 来传递所有凭据以避免将它们提交到 git :

    import mysql.connector
    from mysql.connector import pooling
    conn_pool = pooling.MySQLConnectionPool(pool_name="mypool1",
                                              pool_size=pooling.CNX_POOL_MAXSIZE,
                                              option_files=MYSQL_CONFIG,
                                              option_groups=MYSQL_GROUP_NODE1,
                                              allow_local_infile=True)
conn = conn_pool.get_connection()

最后,恢复到旧代码。仍在使用 PyMySQL,尽管错误频率较低,但它仍然会造成主要问题。我查看了 SQLAlchemy,并没有真正找到太多有关池的文档。

我想知道其他人如何处理 mysql-python 连接池问题?我真的相信应该有一些东西,这样我就不必重新发明轮子。

非常感谢任何指点。

最佳答案

DBUtils实现 MySQL(通常声称支持任意 DB-API 2 兼容数据库接口(interface))用户大小的连接池 PooledDB、thead 映射池 PersistentDBSteadyDB(参见 functionality section )。后者应该适合您的情况,其中 multiprocessing.Pool 创建每个具有托管持久数据库连接的工作进程。其描述为:

DBUtils.SteadyDB is a module implementing "hardened" connections to a database, based on ordinary connections made by any DB-API 2 database module. A "hardened" connection will transparently reopen upon access when it has been closed or the database connection has been lost or when it is used more often than an optional usage limit.

您可以将它与 PyMySQL 一起使用,如下所示:

import pymysql
from DBUtils.SteadyDB import connect

db = connect(
  creator = pymysql, # the rest keyword arguments belong to pymysql
  user = 'guest', password = '', database = 'name', 
  autocommit = True, charset = 'utf8mb4', 
  cursorclass = pymysql.cursors.DictCursor)

另请参阅this related question了解更多示例。

关于connection-pooling - python中的MySQL连接池?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49472042/

相关文章:

java - 如何将自己的连接池的初始化放在struts-config.xml中?

.net - SqlConnection的Dispose方法会干扰连接池吗?

java - HttpClient 错误 : The target server failed to respond

Python:如何共享不可拾取的对象

python - 遍历元组内的元组并使用元组内的字符串作为变量

asp.net - ODP.NET 连接池问题 - 数据库宕机后的容错

python - 导入错误 : No module named 'multiprocessing.forking'

python - 方法内的多处理回调不起作用

mysql - 使用内部查询中的列名选择要在外部查询中显示的列

Python mysql参数和加载数据命令(仍然不起作用)