如何解決MySQL server has gone away報錯問題

在使用python+Django寫項目時,需要用到定時任務(wù)apscheduler,但服務(wù)在長時間運行時,定時任務(wù)會報錯pymysql.err.OperationalError: (2006, "MySQL server has gone away (BrokenPipeError(32, 'Broken pipe'))")

如下圖所示,此時,我們可以通過如下方法解決,一共有三個地方。

圖一


這個報錯出現(xiàn)的原因:操作MySQL數(shù)據(jù)庫的時候,連接超時或者連接的session已經(jīng)被MySQL拋棄,因為使用了定時任務(wù)apscheduler,方式是持久層的框架sqlalchemy,所以,通過3方面來解決。

圖二


第一、MySQL,MySQL默認的wait_timeout時間28800秒,即8小時,超過8小時,MySQL就會放棄連接??梢钥匆幌伦约旱腗ySQL設(shè)置的時間是多少,運行show variables like '%timeout%';這個SQL即可查看到,時間根據(jù)自己業(yè)務(wù)而定,我在這里就保持8小時不變。

圖三


第二、需要修改apscheduler持久層連接時間,設(shè)置時間小于8小時,即,還沒有到MySQL放棄session的時間,apscheduler就主動回收了連接,這樣在使用的時候,可以解決由于超時,MySQL主動拋棄session導致的MySQL server has gone away錯誤。如下圖所示,設(shè)置連接時間為7小時。并且pool_pre_ping為True,即每次從連接池中取連接的時候,都會驗證一下與數(shù)據(jù)庫是否連接正常,如果沒有連接,那么該連接會被回收。

圖四


第三、在Django中操作數(shù)據(jù)庫時,有兩種情況,一種是使用Django的ORM方式操作數(shù)據(jù)庫,即Model.objects.filter()這種方式,我們在報錯之前,即操作數(shù)據(jù)庫之前,先關(guān)閉連接,再重連數(shù)據(jù)庫,即可解決這種方式的報錯情況,引入

from django.db import close_old_connections

在操作數(shù)據(jù)庫之前,加上close_old_connections(),如下圖所示。

圖五


第四、另外一種方式是自定義執(zhí)行SQL,原理一樣,只需要在操作數(shù)據(jù)庫前,關(guān)閉連接即可,引入

from django.db import connection

在操作數(shù)據(jù)庫前,加上connection.close(),如下圖所示。

圖六


至此,通過上面的修改:

1、MySQL超時時間設(shè)置;

2、定時任務(wù)持久層設(shè)置;

3、Django的ORM形式與自定義SQL兩種方式操作前關(guān)閉連接;

就徹底解決了MySQL server has gone away這個報錯。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容