Well my previous attempt to utilize CONN_HEALTH_CHECKS also gave no fruits… Why this must be so complicated?
However I god deeper and deeper in to a rabbit hole… in fact it’s quiet easy to debug this… you start your long running process and then you restart your postgres server, which in result causes this exception. So by doing that I was able to finally figure out how to fight this back. My solution is custom database backend, whyou you define in your DATABASE settings.
from django.contrib.gis.db.backends.postgis.base import (
DatabaseWrapper as PostGisPsycopg2DatabaseWrapper
)
from django.db import close_old_connections, connection as db_connection
class DatabaseWrapper(PostGisPsycopg2DatabaseWrapper):
@async_unsafe
def create_cursor(self, name=None):
if not self.is_usable():
close_old_connections()
db_connection.connect()
return super().create_cursor(name=name)
Apparently there is .is_usable()
check in standard Postgresql database wrapper… which happens to be not used anywhere… Well done!
I am not sure if close_old_connections()
is necessary here, but I do it anyway if the cursor is no longer usable.
Now this is really well tested and works great! It however does cursor.execute("SELECT 1")
to check if database cursor is usable… so it’s adding a little bit of an overhead, but its super marginal and you won’t notice any difference in real life performance unless you are making hundreds of db requests at a very fast pace.