Robert3452
Robert3452

Reputation: 1496

Avoid Failed to read from defunct connection when using neo4j in Flask Application

I am using the following version of neo4j libraries:

neo4j==1.7.2
neobolt==1.7.9
neotime==1.7.4

I have a flask app and in development I am using the internal flask application server. (In prod I will use a docker container with uwsgi, but this quesiton is about my dev setup.)

I have encapsuated neo4j into a class and my application maintains a single instance of this class:

class ChartStoreConnectionClass():
  driver = None

  def __init__(self, configDict):
    self.driver = neo4j.GraphDatabase.driver(
      configDict["boltUri"],
      auth=(configDict["basicAuthUsername"], configDict["basicAuthPassword"]),
      encrypted=True,
      trust=neo4j.TRUST_SYSTEM_CA_SIGNED_CERTIFICATES,
      # trust=neo4j.TRUST_ALL_CERTIFICATES,
      # trust=neo4j.TRUST_CUSTOM_CA_SIGNED_CERTIFICATES, Custom CA support is not implemented
    )

  def readonlyQuery(self, queryFN):
    res = None
    with self.driver.session() as session:
      tx = session.begin_transaction()
      res = queryFN(tx)
      tx.rollback()
    return res

  def execute(self, queryFN):
    res = None
    with self.driver.session() as session:
      tx = session.begin_transaction()
      res = queryFN(tx)
      tx.commit()
    return res

This setup works for a while, but sometimes I get the following error:

neobolt.exceptions.ServiceUnavailable: Failed to read from defunct connection Address(host='127.0.0.1',
port=7687)

when I simply retry the request it works the second time. I have read around the error message and found mutiple posts talking about neo4j in multi-threaded vs multi-process environments but I do not believe they are relevant to me here.

There errors are occurring on the commit of the execute function. The queryFN I pass to it is a very simple one liner which takes next to no time to execute.

Is it wrong to have a single driver instance for my application? (I thought this was the way to do it because the driver creates a connection pool and it makes sense that my application has a connection pool.)

What is the recommended way to use neo4j with Flask? I have seen this example https://github.com/neo4j-examples/movies-python-bolt/blob/master/movies.py but they simply have a single driver object in the same way as I do. (Except that is global not inside a class, but functionally mine is the same.)

Where should I be looking to debug this issue?

Upvotes: 6

Views: 2108

Answers (0)

Related Questions