文章目录
问题描述:
使用gunicorn启动flask项目,一晚上没有访问Web,第二天访问,报错连接数据库失败。
Flask-- 1.1.2
MySQL-- 5.7.30
SQLAlchemy – 1.3.16
原因:mysql自身8小时未连接,则会自动断开(默认)
解决方案:
mysql> show variables like '%timeout%';
+-----------------------------+----------+
| Variable_name | Value |
+-----------------------------+----------+
| connect_timeout | 10 |
| delayed_insert_timeout | 300 |
| have_statement_timeout | YES |
| innodb_flush_log_at_timeout | 1 |
| innodb_lock_wait_timeout | 50 |
| innodb_rollback_on_timeout | OFF |
| interactive_timeout | 28800 |
| lock_wait_timeout | 31536000 |
| net_read_timeout | 30 |
| net_write_timeout | 60 |
| rpl_stop_slave_timeout | 31536000 |
| slave_net_timeout | 60 |
| wait_timeout | 28800 |
+-----------------------------+----------+
-
方案一:
其中 interactive_timeout wait_timeout 28800 = 60 * 60 * 8 即8小时
方案一: 加这两个延时,加长时间,网上查询最大为24天,未实践 -
方案二:
方案二:_engine = create_engine(db_url=“db_url”, pool_recycle=3600)
设置pool_recycle参数,修改sqlalchemy连接池时间,小于8小时,即当连接池小于这个时间,则会断开,重新创建,不会与mysql8小时冲突。 -
方案三:
方案二:_engine = create_engine(db_url=“db_url”, poolclass=NullPool)
关闭连接池,测试失败 -
方案四:
flask 项目
@app.teardown_appcontext
def shutdown_session(exception=None):
session.remove()
SQLAlchemy session
参考链接
线程安全
session不是线程安全的,并且我们一般session对象都是全局的,那么在多线程情况下,当多个线程共享一个session时,数据处理就会发生错误。
为了保证线程安全,需使用scoped_session方法:
db_session = scoped_session(sessionmaker(bind=engine))